在 multipart POST 请求中存在 "@" 问题。
PHP 5.5 或更高版本的解决方案
- 启用 CURLOPT_SAFE_UPLOAD。
- 使用 CURLFile 而不是 "@"。
PHP 5.4 或更早版本的解决方案
- 自己构建 multipart 内容主体。
- 自己更改 "Content-Type" 标头。
以下代码片段将帮助你:D
<?php
function curl_custom_postfields($ch, array $assoc = array(), array $files = array()) {
static $disallow = array("\0", "\"", "\r", "\n");
foreach ($assoc as $k => $v) {
$k = str_replace($disallow, "_", $k);
$body[] = implode("\r\n", array(
"Content-Disposition: form-data; name=\"{$k}\"",
"",
filter_var($v),
));
}
foreach ($files as $k => $v) {
switch (true) {
case false === $v = realpath(filter_var($v)):
case !is_file($v):
case !is_readable($v):
continue; }
$data = file_get_contents($v);
$v = call_user_func("end", explode(DIRECTORY_SEPARATOR, $v));
$k = str_replace($disallow, "_", $k);
$v = str_replace($disallow, "_", $v);
$body[] = implode("\r\n", array(
"Content-Disposition: form-data; name=\"{$k}\"; filename=\"{$v}\"",
"Content-Type: application/octet-stream",
"",
$data,
));
}
do {
$boundary = "---------------------" . md5(mt_rand() . microtime());
} while (preg_grep("/{$boundary}/", $body));
array_walk($body, function (&$part) use ($boundary) {
$part = "--{$boundary}\r\n{$part}";
});
$body[] = "--{$boundary}--";
$body[] = "";
return @curl_setopt_array($ch, array(
CURLOPT_POST => true,
CURLOPT_POSTFIELDS => implode("\r\n", $body),
CURLOPT_HTTPHEADER => array(
"Expect: 100-continue",
"Content-Type: multipart/form-data; boundary={$boundary}", ),
));
}
?>