2017-07-30 207 views
1

我想查詢大量數據到服務器,這裏是我的代碼:MySQL查詢執行失敗

$queryString = ""; 

$connect = mysqli_connect("localhost", "username", "password", "database"); 

$loopLength = 20; 
$currentGroup = 1; 
$currentLoopAmount = 0; 
$queryAmount = 5; 

for($v = 0; $v < ceil($loopLength/$queryAmount); $v++){ 
    //echo "Looping Main: " . $v . "<br>"; 
    //echo $loopLength - (($currentGroup - 1) * 10) . "<br>"; 
    if($loopLength - (($currentGroup - 1) * $queryAmount) >= $queryAmount){ 
     $currentLoopAmount = $queryAmount; 
    } 
    else{ 
     $currentLoopAmount = $loopLength - (($currentGroup - 1) * $queryAmount); 
    } 

    //echo $currentLoopAmount; 

    $queryString = ""; 

    for($q = (($currentGroup - 1) * $queryAmount); $q < $currentLoopAmount + (($currentGroup - 1) * $queryAmount); $q++){ 
     //echo "&nbsp;&nbsp;Looping Sub: " . $q . "<br>"; 
     $tempVariable = grabPageData($URLs[$q], $q); 

     $queryString .= $tempVariable; 
     if($q < $loopLength-1){ 
      $queryString .= ","; 
     } 
     else{ 
      $queryString .= ";"; 
     } 
    } 

    echo $queryString; 

    $query = "INSERT INTO PublicNoticesTable (url, county, paperco, date, notice, id) VALUES " . $queryString; 
    $result = mysqli_query($connect, $query); 

    if($result){ 
     echo "Success"; 
    } 
    else{ 
     echo "Failed : " . mysqli_error($connect) . "<br>"; 
    } 

    $currentGroup += 1; 
} 

$loopLength變量是動態的,可以在數千或潛在十萬。我設計了這個功能,將這個龐大的數字劃分爲一批較小的查詢,因爲我無法一次性通過GoDaddy在我的共享託管服務上傳所有數據。變量$queryAmount代表較小的查詢有多大。

下面是插入到表中的其中一個值集的示例: 這是公告中的數據,表示我的代碼在grabPageData()函數中檢索到。

('http://www.publicnoticeads.com/az/search/view.asp?T=PN&id=37/7292017_24266919.htm','Pima','Green Valley News and Sun','2017/07/30',' ___________________________ARIZONA SUPERIOR COURT, PIMA COUNTYIn the Matter of the Estate of:JOSEPH T, DILLARD, SR.,Deceased.DOB: 10/09/1931No. PB20170865NOTICE TO CREDITORS(FOR PUBLICATION)NOTICE IS HEREBY GIVEN that DANA ANN DILLARD CALL has been appointed Personal Representative of this Estate. All persons having claims against the Estate are required to present their claimswithin four months after the date of the firat publication of this notice or the claims will be forever barred. Claims must be presented by delivering or mailing a written statement of the claim to the Personal Representative at the Law Offices of Michael W. Murray, 257 North Stone Avenue, Tucson, Arizona 85701.DATED this 17th day of July, 2017./S/ Micahel W. MurrayAttorney for the Personal RepresentativePub: Green Valley News & SunDate: July 23, 30, August 6, 2017 Public Notice ID: 24266919',' 24266919'), 

爲了獲得這些數據,我通過抓取頁面並抓取它的函數來運行它。然後我通過這個功能把網頁html代碼:

function cleanData($data){ 
    $data = strip_tags($data); 
    //$data = preg_replace("/[^a-zA-Z0-9]/", "", $data); 
    //$data = mysql_real_escape_string($data); 
    return $data; 
} 

這給了我沒有標籤的內容,如你所見。這是問題。

該函數執行,一切似乎只是丹迪。然後(我不保持在10題的緣故取決於$queryAmount變量)的輸出,你可以看到它會在功能類似的功能...

Failed : You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near '' at line 1 

怪異的是,當我有大量的數據,比如說$loopLength變量就像116.結果會輸出,「失敗:(錯誤)失敗:(錯誤)輝...(錯誤)成功所以它只是實際查詢最後一組數據???不確定

我不知道如何解決這個問題,我想要一個新鮮的眼睛,有人可以幫助我,我一直在努力解決這個問題...幾個小時,試圖找到解決方案

對不起,讓這個問題的一個痛苦的對接:(

編輯:

我改變了代碼從以前用mysql準備語句並沒有什麼...見下文:

$grabDataResults = [ 
     "url" => "", 
     "county" => "", 
     "paperco" => "", 
     "date" => "", 
     "notice" => "", 
     "id" => "", 
    ]; 

$connect = mysqli_connect("localhost", "bwt_admin", "Thebeast1398", "NewCoDatabase"); 

if($stmt = mysqli_prepare($connect, "INSERT INTO PublicNoticesTable (url, county, paperco, date, notice, id) VALUES (?, ?, ?, ?, ?, ?)")){ 

mysqli_stmt_bind_param($stmt, 'ssssss', $grabDataResults["url"], $grabDataResults["county"], $grabDataResults["paperco"], $grabDataResults["date"], $grabDataResults["notice"], $grabDataResults["id"]); 

$loopLength = 1; 

for($v = 0; $v < $loopLength; $v++){ 
    $grabDataResults = grabPageData($URLs[$v], $v); 
    mysqli_stmt_execute($stmt); 
    printf("%d Row inserted.\n", mysqli_stmt_affected_rows($stmt)); 
    printf("Error:\n", mysqli_stmt_error($stmt)); 
    echo "(" . $grabDataResults["url"] . "," . $grabDataResults["county"] . "," . $grabDataResults["paperco"] . "," . $grabDataResults["date"] . "," . $grabDataResults["notice"] . "," . $grabDataResults["id"] . ")"; 
} 

mysqli_stmt_close($stmt); 

mysqli_close($connect); 
} 

不幸的是,這是我從輸出獲得:

1 Row inserted. 0 Error: 

沒有錯誤實際打印出來,該行是在serted。但是,當我導航到我的數據庫,並查看已存儲的值..他們都是空的。 echo語句輸出這樣的:

(http://www.publicnoticeads.com/az/search/view.asp?T=PN&id=31/7292017_24266963.htm,Yuma,Sun (Yuma), The,2017/07/30,, 24266963) 

所以我知道所有變量包含除$notice變量,它得到由我cleanData()功能出於某種原因被破壞的東西。

+1

FRO對目前爲止的問題的評論 - 我肯定會使用準備好的語句並綁定這些值。如果您的數據來自網頁,那麼如果直接插入數據會導致您的SQL發生中斷的可能性非常高,https://stackoverflow.com/questions/9629328/how-to-use-mysqli-prepared-statements-in -php可能會有幫助。 –

+0

我做了一些關於創建預處理語句的研究,併爲了不直接插入而對值進行了綁定......看起來像是我的代碼試圖動態生成查詢語句和東西將是一個巨大的混亂。我想我可以嘗試一下,但就像我說過的,我可能會產生成千上萬的數據行,不知道綁定語句會是什麼樣子,更不用說查詢本身了。 – Pixelknight1398

+0

您可以使用1行插入來準備語句,然後每行數據只需執行準備好的語句和一行數據。 –

回答

0

你需要提取後的數據綁定,防止它和之前執行它...

$loopLength = 1; 

for($v = 0; $v < $loopLength; $v++){ 
    $grabDataResults = grabPageData($URLs[$v], $v); 

    mysqli_stmt_bind_param($stmt, 'ssssss', $grabDataResults["url"], 
      $grabDataResults["county"], $grabDataResults["paperco"], 
      $grabDataResults["date"], $grabDataResults["notice"], 
      $grabDataResults["id"]); 

    mysqli_stmt_execute($stmt); 
    printf("%d Row inserted.\n", mysqli_stmt_affected_rows($stmt)); 
    printf("Error:\n", mysqli_stmt_error($stmt)); 
    echo "(" . $grabDataResults["url"] . "," . $grabDataResults["county"] . "," . $grabDataResults["paperco"] . "," . $grabDataResults["date"] . "," . $grabDataResults["notice"] . "," . $grabDataResults["id"] . ")"; 
} 
+0

謝謝你,你的建議解決了我的問題! :)感謝幫助我,花了一分鐘纔開始。 – Pixelknight1398

0

我在查詢中看到的主要錯誤是查詢本身。您正在使用帶有分隔字段和值的INSERT INTO。但是你忘記在價值觀上使用pharentesis。

記住,使用INSERT INTO的如下:

First option: 
INSERT INTO table field1 = value1, field2 = value2; 

Second option: 
INSERT INTO table (field1, field2) VALUES (value1, value2); 

還有,記得逃脫各個領域和價值避免更多的錯誤:例:

First option: 
INSERT INTO `table` `field1` = 'value1', `field2` = 'value2'; 

Second option: 
INSERT INTO `table` (`field1`, `field2`) VALUES ('value1', 'value2'); 

如果您在使用mysqli驅動程序,爲了更安全,您可以使用準備好的語句,讓您的值自動轉義。在這種情況下,查詢的語法如下:

First option: 
INSERT INTO `table` `field1` = ?, `field2` = ?; 

Second option: 
INSERT INTO `table` (`field1`, `field2`) VALUES (?, ?); 

而且,而是採用mysqli_query(),你需要使用mysqli_prepare(),mysqli_bind_param()和mysqli_execute()。您可以在這裏查看更多關於它們語法的數據:http://php.net/manual/en/mysqli.prepare.php

至少,您可以使用mysqli_real_escape_string()函數來正確地轉義和檢查輸入。您可以點擊這裏這個函數的文檔:http://php.net/manual/en/mysqli.real-escape-string.php

+0

我很抱歉,我一定是誤解你在說什麼?我的插入代碼是INSERT INTO PublicNoticesTable(url,county,paperco,date,notice,id)VALUES「。$ queryString',你可以看到我將括號中的字段包圍起來,最後我不想複製和粘貼$ queryString變量的例子,但你可以參考我的問題來看一個例子,它在一行中很混亂,但它顯示的值設置爲(值,價值,價值,價值,價值),然後最終設置以分號結尾,我會嘗試將括號添加到$ queryString中,看看是否有效。 – Pixelknight1398

+0

您已經包圍了字段名稱,但沒有字段值,正如我在所有示例中所建議的。 –

+0

我按照你的建議做了,你可以在B的評論中看到查詢字符串的結果。Desai的回答 – Pixelknight1398

0

你的代碼是正確的。只需要添加()周圍查詢字符串 阿克索你需要從查詢字符串結束刪除;。 SO刪除以下else條件您查詢像

else{ 
    $queryString .= ";"; 
} 

變化:

$query = "INSERT INTO PublicNoticesTable (url, county, paperco, date, notice, id) VALUES (" . $queryString . ")"; 

此外,它建議使用準備語句從SQL注入

+0

好吧,我做了你所建議的改變,我得到一個新的錯誤,顯示爲'失敗:你的SQL語法有錯誤;檢查與您的MySQL服務器版本相對應的手冊,以查找正確的語法,以便在每行失敗的查詢的第1行'''附近使用。然後,最終不再有成功值,現在失敗,出現此錯誤:'失敗:操作數應該包含1列(s)' – Pixelknight1398

+0

您是否刪除了這個其他部分? 'else {$ queryString。=「;」; }'? –

+0

是的,我已經這樣做了,我評論了一下。 – Pixelknight1398