使用 PHP PDO 获取 MSSQL 存储的过程结果


Getting MSSQL Stored Proc Results with PHP PDO

我在 MSSQL 2008 R2 中有一个相当复杂的存储过程,最终导致返回一个小表。PHP将从javascript调用,我希望它将数组作为JSON返回,以便在javascript的表中使用。

我正在使用 PHP 访问它,并且使用探查器可以看到我正在调用 SP 并将正确的参数传递给它。

我的PHP看起来像这样:

try {
    $dbh = new PDO("sqlsrv:Server=(local);Database=cddDispo");
    $dbh->setAttribute( PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
} catch (PDOException $e) {
    echo json_encode("Error connecting to the server.");
    die ();
}
$lot = $_POST["lot-input"];
$layerAdder = $_POST["layer-input"];
$adder = substr($layerAdder,-3,3);
$adder = str_replace('=','',$adder);
$layer = substr($layerAdder,0,strpos($layerAdder,' '));
$sth = $dbh->prepare('EXEC dbo.pullDispo ?,?,?');
$sth->bindParam(1,$lot,PDO::PARAM_STR);
$sth->bindParam(2,$layer,PDO::PARAM_STR);
$sth->bindParam(3,$adder,PDO::PARAM_STR);
$array = array();
try {
    $sth->execute();
    while($row = $sth->fetch(PDO::FETCH_ASSOC)) {
        //I want to build my output array here
   }
}catch (PDOException $e) {
    echo "Error getting data, please try again.";
    die();
}
header('Content-type: application/json');
echo json_encode($array);

这是我第一次尝试从存储过程返回表结果,即使进行了几次PHP手册/Google搜索,我也没有弄清楚如何在PHP中捕获表。 我有一个不太优雅的解决方法(将 SP 表写入静态表并稍后在 PHP 中调用该表),但宁愿弄清楚我是否可以以更优雅的方式完成。 任何建议都非常感谢。

我认为如果我发布我的最终代码可能会很有用:

function array_push_assoc($array,$key,$value) {
    $array[$key] = $value;
    return $array;
}
header('Content-type: application/json');
try {
    $dbh = new PDO('sqlsrv:Server=(local);Database=cddDispo');
    $dbh->setAttribute( PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
} catch (PDOException $e) {
    echo json_encode('Error connecting to the server.');
    die ();
}
$lot = $_POST['lot'];
$layer = $_POST['layer'];
$adder = $_POST['adder'];
$sth = $dbh->prepare('EXEC dbo.pullDispo ?,?,?');
$sth->bindParam(1,$lot,PDO::PARAM_STR);
$sth->bindParam(2,$layer,PDO::PARAM_STR);
$sth->bindParam(3,$adder,PDO::PARAM_STR);
$results = array();
$combinedArray = array();
$array = array();
$count = 0;
try {
    $sth->execute();
    do {
        $results[] = $sth->fetchAll(PDO::FETCH_ASSOC);
    }while ($sth->nextRowset());
    foreach($results as $row) {
        if($count == 0) {
            $headerArray =
                [
                    'Lot'               =>$row['Lot'],
                    'Layer'             =>$row['Measured Layer'],
                    'Product'           =>$row['MES Product'],
                    'Adder'             =>$row['Adder Chart']
                ];
            $combinedArray = array_push_assoc($combinedArray,'header',$headerArray);
        }
        $count++;
        //This is for formatting of final table
        if($row['UDL'] == 0) {
            $udl = 'NA';
        } else {
            $udl = round($row['UDL'],4);
        }
        $infoArray =
            [
                'Wafer'             =>$row['Wafer'],
                'Type'              =>$row['Type'],
                'Count'             =>$row['Count'],
                'CDD'               =>round($row['CDD'],3),
                'UCL'               =>round($row['UCL'],4)
            ];
        array_push($array,$infoArray);
    }
    $combinedArray = array_push_assoc($combinedArray,'detail',$array);
}catch (PDOException $e) {
    echo json_encode('Error running stored procedure.');
    die();
}
echo json_encode($combinedArray);

可能是您的存储过程返回了多个结果集吗?这包括警告消息或受影响的行数等输出。尝试在存储过程的顶部添加SET ANSI_WARNINGS OFFSET NOCOUNT ONAS 之后。您也可以尝试在 PHP 中前进到下一个结果集,然后再尝试通过在 $sth->fetchAll() 之前调用 $stg->nextRowset() 来获取结果。

使用 fetchAll() 获取结果集,然后将该数组编码为 json 响应:

$array = array();
try {
    if($sth->execute()){
        $array = $sth->fetchAll(PDO::FETCH_ASSOC);
    }else{
        $array = array('error'=>'failed to execute()')
    }
}catch (PDOException $e) {
    echo "Error getting data, please try again.";
    die();
}
header('Content-type: application/json');
echo json_encode($array);

调用具有多个结果集的存储过程时,可能不希望将SET NOCOUNT ON添加到您拥有的每个过程中;您始终可以添加

$dbh->setAttribute(constant('PDO::SQLSRV_ATTR_DIRECT_QUERY'), true);
$dbh->query("SET NOCOUNT ON"); 

之前

$dbh->prepare($query);

它会起作用。