2015-05-27 102 views
-2

我寫了一個函數,它將包含PDF字段數據的字符串傳遞到preg_match_all()作爲主題。然而,無論我做什麼,我都無法得到預期的輸出,因爲我在這裏得到http://www.phpliveregex.com/p/bjN。在我的開發環境,我得到這個:PHP pdftk ASCII編碼問題

陣列(1){[0] =>陣列(0){}}

我已經能夠得到這個唯一的辦法工作是通過調用我的字符串輸入的var_dump(),將其分配給函數中的一個變量,並用反斜槓轉義雙引號。然而,這個解決方案不起作用,因爲我想動態地傳遞不同的字符串。

我已經嘗試過的函數包括preg_replace(),preg_quote(),addslashes(),addcslashes()和htmlentities()來轉義或編碼可能導致問題的任何字符。到目前爲止沒有任何工作。

下面引用是我在輸入中調用var_dump()時得到的輸出。正如我上面所說的,將它分配給一個變量並傳遞給preg_match_all()對我來說是有效的。所以這個問題似乎正在下降到這樣的程度:什麼可能會阻止我的輸入字符串與preg_match_all()正常工作,這不是我在調用var_dump()時得到的字符串的問題?

串(3277)「---的FieldType:文本字段名: FC-INT01-generateAppearances FieldFlags:5 FieldJustification:左 ---的FieldType:文本字段名:蛋糕的大小,形狀,和Pricing_edit; _aKGrUPU76IVzjjqnxACWRA FieldNameAlt :請說明 定製的蛋糕大小和特殊要求。FieldFlags:0 FieldFusion:Left --- FieldType:Text FieldName:Todays Date FieldNameAlt:Today's date FieldFlags:0 FieldJustification:Left --- FieldType:Button FieldName:Type FieldFlags :49152 欄位理由:Left FieldStateOption:用於交付 FieldStateOption:用於提貨F ieldStateOption:Off --- FieldType: FieldName:Name FieldNameAlt:Name FieldFlags:0 FieldJustification:Left --- FieldType:Text FieldName:Event Date of Event FieldNameAlt:事件日期FieldFlags:0 FieldJustification:Left --- 的FieldType:文本字段名:在 事件FieldFlags的時間:事件FieldNameAlt的時間0 FieldJustification:左---的FieldType:文本 字段名:事件FieldNameAlt類型:事件FieldFlags類型:0 FieldJustification:左---的FieldType :文本字段名稱:事件位置 (如果需要傳遞)FieldNameAlt:事件位置(如果要求傳遞 )FieldFlags:0 FieldJustification:Left --- FieldType: Text FieldName:Pick Up Time FieldName Alt:接機時間FieldFlags:0 FieldJustification:Left --- FieldType:Text FieldName:Number of Guests FieldNameAlt:客人人數FieldFlags:0 FieldJustification:Left --- FieldType:Text FieldName:Phone Number FieldNameAlt:Phone FieldFlags:0 FieldJustification:Left --- FieldType:Button FieldName:蛋糕大小,形狀和價格FieldFlags: 49152 FieldJustification:Left FieldStateOption:Custom FieldStateOption:Off FieldStateOption:Rectangle 1/2 Sheet($ 60.00) 送達到12 FieldStateOption:矩形1/3工作表($ 40.00)服務 最多8 FieldStateOption:矩形1/4工作表($ 30.00)服務多達6 FieldStateOption:矩形工作表($ 100.00)服務最多24 FieldStateOption:第6輪「($ 40。00)服務多達8 FieldStateOption:第9輪「(50.00美元)最多可服務16個 FieldStateOption:Square 1/6 Sheet($ 20.00)最多可提供4個 FieldStateOption:Square 2/3 Sheet($ 50.00) - 的FieldType:按鈕字段名:蛋糕口味FieldFlags:49152 FieldJustification:左FieldStateOption:胡蘿蔔FieldStateOption: 巧克力FieldStateOption:檸檬FieldStateOption:關 FieldStateOption:紅色天鵝絨FieldStateOption:香草---的FieldType: 鍵字段名:蛋糕餡料FieldFlags :49152 FieldJustification: Left FieldStateOption:Buttercream FieldStateOption:奶酪 FieldStateOption:黑巧克力FieldStateOption:檸檬凝乳 Fi eldStateOption:關FieldStateOption:草莓慕斯--- 的FieldType:按鈕字段名:蛋糕蒙砂FieldFlags:49152 FieldJustification:左FieldStateOption:巧克力奶油 FieldStateOption:奶油奶酪FieldStateOption:關FieldStateOption: 草莓奶油FieldStateOption:香草奶油 FieldStateOption:鞭打奶油---字段類型:文本字段名稱:蛋糕 寫字的題字和顏色FieldNameAlt:蛋糕題字和 寫字的顏色FieldFlags:4096 FieldJustification:Left --- FieldType:Text FieldName:澆頭和特殊裝飾 FieldNameAlt:澆頭和特殊裝飾品FieldFlags:4096 FieldJustification:Left「

如果將此字符串分配給臨時變量並轉義引號,則preg_match_all()將按預期工作。當我使用分配的字符串在這個變量上調用var_dump()時,長度爲3268個字符,而我的直接輸入爲3277(上面)。所以也許有一些奇怪的事情與輸入字符串。

任何幫助,將不勝感激!

這裏是我已經修改,以加強對這裏的可讀性我的類文件:

class Pdf_form { 

    public function get_pdf_fields($pdf) { 
     $cmd = "pdftk $pdf dump_data_fields output -"; 

     $descriptorspec = array(
      1 => array("pipe", "w") 
     ); 

     $process = proc_open($cmd, $descriptorspec, $pipes); 

     if(!is_resource($process)) { 
      return FALSE; 
     } 

     $dump_data = stream_get_contents($pipes[1]); 
     fclose($pipes[1]); 

     $status = proc_close($process); 

     return $this->parse_fields($dump_data); 
    } 

    private function parse_fields($dump_data) { 
     preg_match_all('/FieldType: .+?(?= ---|$)/', $dump_data, $field_data); 

     return $field_data; 
    } 
} 
+0

_「由於存在$和」(雙引號)字符,因此無法將其作爲輸入傳遞到preg_match_all「_你爲什麼會這麼想?這顯然是主題而不是模式,並且這些字符不會呈現一個問題。 – AbraCadaver

+0

你說得對,我引用的字符串是主題。我不認爲會有任何問題,我自己直到preg_match_all()返回此「陣列(1){[0] =>陣列(0){} }「。只有在我逃過$和」用反斜線preg_match_all()返回我的預期。 - 編輯:對於不需要轉義的美元符號,您是正確的,因爲我剛剛測試了這一點,但雙引號在逃脫之前仍然存在問題。 –

+0

你可以發佈你如何在'preg_match_all'或'preg_replace'中運行這個字符串嗎? – chris85

回答

0

您可以使用Newdoc語法我想。

文檔中的示例。

echo <<<'EOT' 
My name is "$name". I am printing some $foo->foo. 
Now, I am printing some {$foo->bar[1]}. 
This should not print a capital 'A': \x41 
EOT; 

https://php.net/language.types.string#language.types.string.syntax.nowdoc11

編輯 如果你只是想取代你可以使用str_replace函數所有雙qoutes。

$a = str_replace('"', '\"', $a);

+0

我看不出這將如何工作,除非有一個辦法,我以某種方式將我的動態輸入字符串轉換成nowdoc格式。 –

+0

我錯過了這個問題。但是,這應該與\更換所有雙qoutes「'$字符串= str_replace函數(「」」,「\」「,$字符串);' – Karl

+0

的問題之前,應進行首次發現。‘修復’沒有理由雙引號 – chris85

-1

如果您使用的mysqli連接 傳中,PHP函數

mysqli_real_escape_string(); 

的字符串,如果用mysql然後用

mysql_real_escape_string(); 
+0

什麼?沒有數據庫在這裏談論。 – chris85

+0

即使您不想將記錄保存在數據庫中,也可以使用此功能。我的意思是無論你想插入數據庫還是存儲變量,它都會返回相同的結果。 –

+0

沒有第一個它會發出警告。 '警告:mysql_real_escape_string():[2002]沒有這樣的文件或目錄(試圖通過unix連接:///var/mysql/mysql.sock)'''警告:mysql_real_escape_string():到服務器的鏈接不能建立在',等等。如果目標只是爲了逃避報價爲什麼不http://php.net/addslashes?但即便如此,這也不是問題。 – chris85

0

原來一些,也許甚至所有在我的輸入中似乎都是空格的字符實際上都被編碼爲ASCII換行符(ASCII十進制代碼10)。因此,在調用pdftk的dump_data_fields操作和通過stream_get_contents()將數據管道傳輸到我的php腳本之間,以這種方式編碼數據。

我的解決方案是調用我的輸入上的preg_replace()以用空格替換所有換行符。這是它看起來像:

$dump_data = preg_replace('/\n/', ' ', $dump_data); 

preg_match_all('/FieldType:.+?(?=.---|$)/', $dump_data, $field_data); 

希望這可以幫助別人!