我想显示SQL Server的SP的返回值。我试过用这种方法,但没有成功。
我正在使用PHP PDO进行数据库连接,我正在执行SQL Server存储过程。
$feesObj = new FeesConfig('config/fees.ini');
$feesConfig = $feesObj->getFeesConfig();
$studentId = $user->getSyStudentId();
$statement = $conn->prepare('exec ?= usp_GetStudentDegreeLevel ?');
$statement->bindParam(1, $retval, PDO::PARAM_STR|PDO::PARAM_INPUT_OUTPUT);
$statement->bindParam(2, $studentId, PDO::PARAM_INT);
$statement->execute();
$row = $statement->fetch(PDO::FETCH_ASSOC);
var_dump("return value". $retval);exit;
SP执行的输出
NULL
预期的结果
1
我对这段代码的错误。我正在呼叫SQL Server SP.
原始答案(使用我通常获取可能输出参数的返回值和存储过程的返回值的方法):
您可以考虑以下内容:
- 存储过程的返回值是整数,因此需要使用适当的绑定。
- 如果是
OUTPUT
参数,需要在PDOStatement::bindParam
呼叫中设置maxLength
参数。如文档中所述,要…如果参数是存储过程中的OUT参数,则必须显式设置长度。 - 您需要获取所有可能的结果集(使用
PDOStatement::nextRowset
)以获得输出参数的值。或者,在INSERT
或UPDATE
语句的情况下,作为一个选项,将SET NOCOUNT ON
作为存储过程中的第一行。正如文档中所解释的,这个语句…停止显示受Transact-SQL语句或存储过程影响的行数计数的消息作为结果集的一部分返回。
下面是一个使用SQL Server 2017, PHP 7.4.8和PHP Driver for SQL Server 5.8的简化示例:
存储过程:
CREATE PROCEDURE usp_GetStudentDegreeLevel
@StudentId INT
AS
BEGIN
SELECT 'Information about the student' AS StudentInfo;
RETURN 1;
END
PHP代码:
<?php
$server = 'serverinstance,port';
$database = 'database';
$username = 'username';
$password = 'password';
try {
$conn = new PDO("sqlsrv:server=$server;Database=$database", $username, $password);
$conn->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
$conn->setAttribute(PDO::SQLSRV_ATTR_ENCODING, PDO::SQLSRV_ENCODING_SYSTEM);
} catch( PDOException $e ) {
die( "Error connecting to SQL Server".$e->getMessage());
}
try {
//
$sql = "EXEC ? = usp_GetStudentDegreeLevel ?";
$statement = $conn->prepare($sql);
if ($statement === false) {
echo print_r($conn->errorInfo(), true);
exit;
}
// Execution
$retval = 0;
$studentId = 1;
$statement->bindParam(1, $retval, PDO::PARAM_INT | PDO::PARAM_INPUT_OUTPUT, PDO::SQLSRV_PARAM_OUT_DEFAULT_SIZE);
$statement->bindParam(2, $studentId, PDO::PARAM_INT);
if ($statement->execute() === false) {
echo print_r($conn->errorInfo(), true);
exit;
}
// Fetch data.
do {
if ($statement->columnCount() > 0) {
while ($row = $statement->fetch(PDO::FETCH_ASSOC)) {
echo print_r($row, true);
};
};
} while ($statement->nextRowset());
//
var_dump("Return value: " . $retval);
$statement = null;
} catch (PDOException $e) {
echo $e->getMessage();
exit;
}
$conn = null;
?>
结果:
Array ( [StudentInfo] => Information about the student ) string(15) "Return value: 1"
更新(一个示例,它再现了意外的返回值):
我能重现这个错误的唯一方法是:- 使用
PDO::ERRMODE_SILENT
作为默认错误处理模式 - 存储过程错误和/或SQL语句错误。
- No检查
PDO::prepare
和/或PDOStatement::execute
呼叫的结果是否成功。 PHP代码:
// PDO object with default error handling (PDO::ERRMODE_SILENT, but for PHP version before 8.0.0)
$conn = new PDO("sqlsrv:server=$server;Database=$database", $username, $password);
$conn->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_SILENT);
$conn->setAttribute(PDO::SQLSRV_ATTR_ENCODING, PDO::SQLSRV_ENCODING_SYSTEM);
// SQL statement with error
$sql = "EXEC ? = usp_GetStudentDegreeLevel ,?";
$statement = $conn->prepare($sql);
$statement->bindParam(1, $retval, PDO::PARAM_STR | PDO::PARAM_INPUT_OUTPUT, 1);
$statement->bindParam(2, $studentId, PDO::PARAM_INT);
$statement->execute();
$row = $statement->fetch(PDO::FETCH_ASSOC);
//
var_dump($retval);
结果:
NULL