2011-03-29 111 views
2

我已經在PHP中設置了REST服務和客戶端,並且我在PUT中遇到了一些問題。如何使用PHP發送帶有文件和數據陣列的PUT請求

這是我的情況: 我正在編碼一個REST資源,它應該接受一個數據和圖像的數組。 REST資源應該更新現有記錄,所以我使用了PUT。我使用我寫的PHP curl客戶端發送數據。所以 - 幾乎相同的情況,就像你發送一個HTML多部分表單到一個PHP腳本一樣,文件上傳並接受一些額外的POST字段 - 除PUT和PHP curl外。

'直到現在我'去過發送PUT請求是這樣的(僞代碼):

$a_some_data = array('name' => 'test', 'user_id' => 4); 
$body = http_build_query($a_data); 

$fh = fopen('php://memory', 'rw'); 
fwrite($body); 
rewind($fh); 

$ch = curl_init(); 
curl_setopt_array($ch, array(
    CURLOPT_URL => 'http://myapi/resource/someid', 
    CURLOPT_PUT => TRUE, 
    CURLOPT_INFILE => $fh, 
    CURLOPT_INFILESIZE => strlen($body) 
)); 
curl_exec($ch); 

和讀取數據的服務器上,像這樣:

parse_str(file_get_contents('php://input'), $put_data); 

..這工作得很好。

所以現在我想添加一個(二進制)文件到混合中。 - 我如何在客戶端實現這一點? - 我將如何處理服務器上的文件?

對於測試,我使用文件輸入設置了一個HTML表單,複製了它發送的原始多部分/表單數據請求,並嘗試將該數據作爲捲曲在PUT請求中的文件發送。這種工作,但我將不得不手動解析服務器上的原始數據,我不知道是最好的主意。或者,我想我可以將該文件作爲PUT請求的主體發送,並將URL中的其他參數作爲查詢字符串添加 - 但我想這種蔑視PUT REST資源的點。

請分享你的想法。 謝謝!

回答

2

至少有兩種其他的方式,除非你的原始版本不夠用(因爲libcurl應該用二進制文件處理該腳本)。請注意,你如何決定在接收端收到PUT並不是一個捲曲問題,所以我會把它放在這個響應之外。

1 - 就像你剛開始時那樣,但是提供了一個CURLOPT_READFUNCTION,用它將數據提供給它將發送的libcurl。

2 - 使用CURLOPT_POSTFIELDS(一個字符串),使它看起來像一個帖子,然後您更改與CURLOPT_CUSTOMREQUEST HTTP方法「把」

+0

感謝丹尼爾。我喜歡第二個版本,它看起來像要走的路 - 因爲請求仍然作爲PUT發送,但是帶有多部分內容。現在我在php://輸入的服務器上獲得的數據幾乎是我用HTML表單發送的所有內容。你知道解析這個的最好方法是什麼嗎?有沒有從這個原始數據中提取數據和文件的好方法,還是我必須手動解析它? – Chris 2011-03-30 06:48:02

相關問題