Php 具有主键和作用域标识的Insert语句

Php 具有主键和作用域标识的Insert语句,php,sql,sql-server-2008,pdo,Php,Sql,Sql Server 2008,Pdo,我想获取最新记录的主键自动增量,以便将其用作另一个表中的外键。当我使用SCOPE_标识作为pdo参数时,我得到错误: 调用未定义的函数作用域\u标识 当我使用它作为直接值时,语句总是回滚 我的代码正确吗 if (empty($errors)) { $sqlconnection = new SqlConnection(); $conn = $sqlconnection->db_connect(); if ($conn) { if (sqlsrv_b

我想获取最新记录的主键自动增量,以便将其用作另一个表中的外键。当我使用SCOPE_标识作为pdo参数时,我得到错误:

调用未定义的函数作用域\u标识

当我使用它作为直接值时,语句总是回滚

我的代码正确吗

if (empty($errors)) {
    $sqlconnection = new SqlConnection();

    $conn = $sqlconnection->db_connect();

    if ($conn) {
        if (sqlsrv_begin_transaction($conn) === false ) {
            $errors[] = "Cant start transaction.";
        } else {
            // Query1
            $query1 = "INSERT INTO [RC.table1] (terminname, datum) VALUES (?, ?)";
            $params1 = array($eventname, $eventdate);
            $stmt1 = sqlsrv_query($conn, $query1, $params1);

            //Query2
            $query2 = "INSERT INTO [RC.table2] (appointment_id, mandant_id) VALUES ((SELECT SCOPE_IDENTITY()), ?)";
            $params2 = array($_SESSION['mandant_id']);
            $stmt2 = sqlsrv_query($conn, $query2, $params2);

            if($stmt1 && $stmt2) {
                 sqlsrv_commit( $conn );
                 echo "Transaction committed.<br />";
            } else {
                 sqlsrv_rollback( $conn );
                 echo "Transaction rolled back.<br />";
            }
        }
    } else {
        $errors[] = "Cant connect to database.";
    }
}

顺便说一句,虽然代码可能有效,但我建议进行以下更改

   $query1 = "INSERT INTO [RC.table1] (terminname, datum) VALUES (?, ?);select @@identy"
现在,检索将作为新添加的键的结果,并将其作为参数传递给下一个SQL调用

BEGIN TRAN T1;
INSERT INTO [RC.table1] (terminname, datum) VALUES ('alibaba', '24.02.2014');
BEGIN TRAN T22
INSERT INTO [RC.table2] (appointment_id, mandant_id) VALUES ((SELECT SCOPE_IDENTITY()), '0200')
COMMIT TRAN T1;
COMMIT TRAN T2;

在演播室里效果很好。不知道,为什么我无法在php事务中获取标识。

尝试以下解决方案:替换

    $query2 = "INSERT INTO [RC.table2] (appointment_id, mandant_id) VALUES ((SELECT SCOPE_IDENTITY()), ?)";
为此:

    $query2 = "DECLARE @LastID INT; SET @LastID = SCOPE_IDENTITY(); INSERT INTO [RC.table2] (appointment_id, mandant_id) VALUES (@LastID, ?)";
另外,对于@LastID变量定义DECLARE@LastID INT,请使用与约会id列数据类型相同的数据类型。在这个例子中,我假设@LastID的类型是INT

编辑:您可以使用创建以下内容:


注意:应使用合适的类型和长度替换每种类型和最大长度

尝试使用@标识instead@Sparky:如果要插入的表上有触发器,则不建议使用@@IDENTITY为什么不在问题的第二个查询中使用SELECT SCOPE\u IDENTITY?问题中的代码真的在这样做吗?它实际上从哪里开始传输T1;然后开始传输T22?同时回滚。当我从表中读取最新的id并添加+1并将其用于id时,这是正确的解决方案吗?否。为什么不使用存储过程?我将使用存储过程来执行这些插入。我可以使用参数调用存储过程吗?对于第二次插入,我有一个会话变量。@mnlfischer:请参见编辑1。
CREATE PROCEDURE dbo.Insert_Table1Table2 
(
    @terminname NVARCHAR(50), 
    @datum DATE,
    @mandant_id INT 
)
AS
BEGIN
    BEGIN TRANSACTION;

    BEGIN TRY
        INSERT INTO [RC.table1] (terminname, datum) VALUES (@terminname, @datum)
        DECLARE @appointment_id INT; 
        SET @appointment_id = SCOPE_IDENTITY(); 
        INSERT INTO [RC.table2] (appointment_id, mandant_id) VALUES (@appointment_id, @mandant_id)
    END TRY
    BEGIN CATCH
    SELECT 
        DECLARE @ErrorMessage NVARCHAR(2048);
        SET @ErrorMessage = ERROR_MESSAGE();
        RAISERROR(@ErrorMessage, 16, 1)

        IF @@TRANCOUNT > 0
            ROLLBACK TRANSACTION;
    END CATCH;

    IF @@TRANCOUNT > 0
        COMMIT TRANSACTION;
END