PHP和cURL -文件和文本的多表单请求


PHP and cURL - Multiform request with file and text

我需要发送一个cURL请求,其中包含一个要上传的文件以及一个JSON字符串。当发送JSON时,我可以得到一个正确格式化的请求,但文件将其丢弃。

    $postData = array(
        'JSON'=> json_encode($jsonParams),
        $reference => '@'.$tmp_file_path
    );
    //Borrowed function from: http://scraperblog.blogspot.com/2013/07/php-curl-multipart-form-posting.html
    function multipart_build($fields, $boundary){
        $retval = '';
        foreach($fields as $key => $value){
            $retval .= "--$boundary'nContent-Disposition: form-data; name='"$key'"'n'n$value'n";
        }
        $retval .= "--$boundary--";
        return $retval;
    }
    $boundary = "--requestboundary-xxx";
    $request = $this->multipart_build($postData,$boundary);
    $curl = curl_init();
    curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, false); // stop verifying certificate
    curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
    curl_setopt($curl, CURLOPT_HTTPHEADER, array("Content-Type: multipart/form-data; boundary=$boundary"));
    curl_setopt($curl, CURLOPT_URL, $target);
    curl_setopt($curl, CURLOPT_POST, true);
    curl_setopt($curl, CURLOPT_POSTFIELDS, $request);
    $response = curl_exec($curl);
    $info = curl_getinfo($curl);
    curl_close($curl);

$引用需要绑定到$jsonParams中的值,以便接收服务器可以确保上传的文件附加到相应的数据字符串包。

////////////////////////////////////////////////////////////

Marc B评论后更新

////////////////////////////////////////////////////////////

所以我的第一个方法不是使用我自己的multipart。我选择multipart的原因是至少我能从服务器得到响应。这是原始代码。

    $curl_file_object = curl_file_create($attachmentFile['tmp_name'], $attachmentFile['type'], $reference);
    $postData= array(
        'JSON'=> json_encode($jsonParams),
        $reference => $curl_file_object,
    );
    $curl = curl_init();
    curl_setopt($curl, CURLOPT_URL, $target);
    curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, false); // stop verifying certificate
    curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
    curl_setopt($curl, CURLOPT_HEADER, true);
    curl_setopt($curl, CURLOPT_HTTPHEADER, array("Content-Type: multipart/form-data;"));
    curl_setopt($curl, CURLOPT_POST, true); // enable posting
    curl_setopt($curl, CURLOPT_POSTFIELDS, $postData); // post data
    curl_setopt($curl, CURLOPT_FOLLOWLOCATION, true); // if any redirection after upload
    $response = curl_exec($curl);
    $info = curl_getinfo($curl);
    curl_close($curl);
    debug($info);

我得到:

[url] => --------
[content_type] => 
[http_code] => 0
[header_size] => 0
[request_size] => 0
[filetime] => -1
[ssl_verify_result] => 0
[redirect_count] => 0
[total_time] => 0.031
[namelookup_time] => 0
[connect_time] => 0.031
[pretransfer_time] => 0
[size_upload] => 0
[size_download] => 0
[speed_download] => 0
[speed_upload] => 0
[download_content_length] => -1
[upload_content_length] => -1
[starttransfer_time] => 0
[redirect_time] => 0
[redirect_url] => 
[primary_ip] => --------
[certinfo] => Array
    (
    )
[primary_port] => --------
[local_ip] => --------
[local_port] => --------

我至少得了400分。

不要构建自己的multipart。Curl完全有能力为您做到这一点:

curl_setopt($curl, CURLOPT_POSTFIELDS, $postData);

它将取一个数组,并自动执行任何需要的操作。

如果你是PHP 5.5+,你也可以使用curlfile作为文件部分,而不需要@的hack。

使用CURLFile代替curl_file_create()修复了这个问题。尽管它们应该是相同的…