PHP - 无法将图像发布到我的restful服务

时间:2014-08-23 20:51:03

标签: php rest curl

我正在尝试使用cURL将图像发布到我的REStful服务的图片上传方法。

宁静的服务需要以下格式的请求: -

Accept: application/json
Accept-Encoding: gzip,deflate,sdch
Accept-Language: en-US,en;q=0.8

Content-Length: 782
Content-Type: multipart/form-data; boundary=----WebKitFormBoundary5dQ1ta4rvOvWtjff

它还使用授权令牌字符串。

这是我的PHP代码: -

$ _ FILES ['file']作为$ data传递给它作为旁注。

move_uploaded_file($data["tmp_name"], "../uploaded_files/images/".$data["name"]);
$data_string = "@".realpath("../uploaded_files/images/".$data["name"]).";type=image/png";
$ch = curl_init($url);
curl_setopt($ch, CURLOPT_POST, 1); 
curl_setopt($ch, CURLOPT_POSTFIELDS, $data_string);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_CERTINFO, true);
curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false);

$boundary = md5(date('U'));
$http_headers = array(
    'Authorization: Bearer '.$_SESSION['Auth'],
    'Accept: application/json',
    'Accept-Encoding: gzip,deflate,sdch',
    'Content-Length: '.$data['size'],
    "Content-Type: multipart/form-data; boundary=$boundary"."\r\n"              
);

curl_setopt($ch, CURLOPT_HTTPHEADER, $http_headers);

$result = curl_exec($ch);
$info = curl_getinfo($ch);

据我所知,这应该匹配并且有效,但事实并非如此。当我包含Content-Length时(因为它是必需的并且将生成411代码),服务器会冻结,然后很长一段时间后会产生此错误: -

SSL read: error:00000000:lib(0):func(0):reason(0), errno 0

有谁知道我可能做错了什么?我能够使用上面的代码成功发布JSON和其他内容类型,它似乎只是特定于我尝试以这种方式发布图像。

编辑:我被告知不推荐使用@方法进行文件上传,所以我将代码调整为: -

$path = realpath("../upload_files/images/".$data["name"]);
$cfile = curl_file_create($path, 'image/png','file_upload');
$data_string = array('file_upload' => $cfile);

但是现在它为“错误请求”生成400状态代码。我使用这种方法是错误的,还是我缺少的东西?我也尝试了下面的面向对象版本,但它产生了同样的问题。

$cfile = new CURLFile($path,'image/png','file_upload');

2 个答案:

答案 0 :(得分:0)

问题很可能与您的请求Content-Type有关。判断给定格式时,应将其设置为multipart/form-data,即发送的数据应编码为multipart/form-data。根据{{​​3}},为了将Content-Type标题设置为multipart/form-data,您必须将CURLOPT_POSTFIELDS选项设置为array(而不是像您的网址编码字符串)码)。在这种情况下,数据将自动编码为multipart/form-data

所以你的代码应该是这样的:

move_uploaded_file($data["tmp_name"], "../uploaded_files/images/".$data["name"]);
$path = realpath("../uploaded_files/images/".$data["name"]);
$data = array('file' => "@$path;type=image/png");
$ch = curl_init($url);
curl_setopt($ch, CURLOPT_POST, 1); 
curl_setopt($ch, CURLOPT_POSTFIELDS, $data_string);
...

BTW: @前缀仅自PHP 5.5.0起弃用。

答案 1 :(得分:0)

我在这里发现了这个问题。

我的cURL尝试连接的restful服务需要设置Content Disposition标头,这是cURL故意忽略的,因为它设置了自己的边界。

在这种情况下,用PHP完成我尝试使用这种API方法所做的事情是不可能的。

也就是说,除非有人知道可以设置内容处置的不同php库。