2016-10-03 85 views
0

我正在編寫代碼以使用PHP PDO從頭開始創建MSSQL數據庫。我已經創建了數據庫,現在需要執行一幫從.SQL文件加載語句來創建表格,數據等的前幾行是通過PDO執行批量語句時出現語法錯誤,但通過SSMS正常執行

EXEC sp_dbcmptlevel 'myDbName', 120 
GO 
IF (1 = FULLTEXTSERVICEPROPERTY('IsFullTextInstalled')) 
BEGIN 
EXEC [myDbName].[dbo].[sp_fulltext_database] @action = 'enable' 
END 
GO 
ALTER DATABASE [myDbName] SET ANSI_NULL_DEFAULT OFF 
GO 
EXEC sp_dbcmptlevel 'myDbName', 120 

... 

如果我直接運行.SQL文件在SSMS中,它運行完美。如果我加載它,並通過PHP PDO執行它,我得到

Fatal error: Uncaught exception 'PDOException' with message 'SQLSTATE[42000]: [Microsoft][ODBC Driver 11 for SQL Server][SQL Server]Incorrect syntax near 'GO'.' in ... 

在剖析來看,我的查詢被前綴/與

declare @p1 int 
set @p1=NULL 
exec sp_prepexec @p1 output,NULL,N'EXEC sp_dbcmptlevel ''myDbName', 120 
... 

包裹,看來,與準備好的執行包裝,服務器不喜歡它。我執行,我從SQL文件加載與

$db = new PDO('sqlsrv:Server='.$serverName.';Database='.$databaseName, $username, $password); 
$db->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION); 
$db->setAttribute(PDO::SQLSRV_ATTR_ENCODING, PDO::SQLSRV_ENCODING_UTF8); 
$db->prepare($mySqlScript)->execute(); 

如何解決語法錯誤從SQL文件執行整個命令集PHP負載的腳本?

回答

1

您必須將「GO」子句中的腳本分成多個語句,然後逐個運行它們。

喜歡的東西:

$script = file_get_contents('script.sql'); 
$statements = explode('GO', $script); 
foreach($statements as $statement) { 
    // here execute the $statement 
    $sth = $dbh->prepare($statement); 
    $sth->execute(); 
} 

這是SSMS內部完成,通過「走出去的」前執行它們分裂的語句。

+0

太好了,謝謝。它把我的想法當成了黑客,但並不是所需的方式。你知道不能拋棄整個腳本的原因是什麼嗎?我會考慮性能問題,能夠一次處理所有內容會更好。 – walshy002000

+0

也許它不是圖書館的目標之一,它的行爲很容易實現,所以我們只好處理它。你可以像函數execScript($ scriptPath){//執行拆分和執行}那樣對其進行編碼,並且在你的代碼中處理它就好像是原始庫的一部分。這是圖書館將以任何方式做(或多或少)的。 – espino316