php模拟post请求发送文件代码
发布时间:2020-05-25 07:37:07 所属栏目:PHP 来源:互联网
导读:php模拟post请求发送文件代码
|
下面是脚本之家 jb51.cc 通过网络收集整理的代码片段。 脚本之家小编现在分享给大家,也给大家做个参考。 $params1 = "test";
$params2 = "@".$absolute_path;//如果是文件 则参数为"@"+绝对路径
$post_data = array(
'params1' => $params1,'params2' => $params2,);
function postData($url,$data){
$ch = curl_init();
$timeout = 300;
curl_setopt($ch,CURLOPT_URL,$url); //请求地址
//curl_setopt($ch,CURLOPT_REFERER,$ip);//构造来路
curl_setopt($ch,CURLOPT_POST,true); //post请求
curl_setopt($ch,CURLOPT_BINARYTRANSFER,true);//二进制流
curl_setopt($ch,CURLOPT_POSTFIELDS,$data); //数据
curl_setopt($ch,CURLOPT_RETURNTRANSFER,1); //当CURLOPT_RETURNTRANSFER设置为1时 $head 有请求的返回值
curl_setopt($ch,CURLOPT_CONNECTTIMEOUT,$timeout); //设置请求超时时间
$handles = curl_exec($ch);
curl_close($ch);
return $handles;
}
对方是java服务器,我只知道接口,并不知道对方如何处理文件接收的。上面这种方式在win7 wamp环境下是成功的,但是将代码放到centOS+Nginx服务器上却失败,返回的消息是文件接收失败。经过抓包分析,发现在win7 wamp下发的包和centos nginx下发的http包格式有区别。一般情况下curl默认把content_type设为了multipart/form-data,在我的机器上 win7 wamp下是如此,但是centos nginx下却是application/x-www-form-urlencoded。当然这也可能是服务器配置问题,只是我并不知道问题在哪。然后我 又查看了下PHP版本,同是PHP5.3.X,但是有细微差别。也不排除是PHP版本的问题。之后添加代码: $header = array(
'Content-Type: multipart/form-data',);
curl_setopt( $ch,CURLOPT_HTTPHEADER,$header);
设置header,但是在centos下依旧无效。居然无法改变content-type,简直坑爹。 function postData($url,$data = array(),$data1 = array()){
$header = array(
'Content-Type: multipart/form-data',);
$ch = curl_init();
curl_setopt ($ch,$url);
curl_setopt( $ch,$header);
curl_setopt ($ch,1);
curl_setopt ($ch,10);
curl_setopt ($ch,true);
//curl_setopt ($ch,$data);
curl_custom_postfields($ch,$data,$data1);
$dxycontent = curl_exec($ch);
curl_close($ch);
return $dxycontent;
}
/**
* For safe multipart POST request for PHP5.3 ~ PHP 5.4.
*
* @param resource $ch cURL resource
* @param array $assoc "name => value"
* @param array $files "name => path"
* @return bool
*/
function curl_custom_postfields($ch,array $assoc = array(),array $files = array()) {
// invalid characters for "name" and "filename"
static $disallow = array(" ",""","r","n");
// build normal parameters
foreach ($assoc as $k => $v) {
$k = str_replace($disallow,"_",$k);
$body[] = implode("rn",array(
"Content-Disposition: form-data; name="{$k}"","",filter_var($v),));
}
// build file parameters
foreach ($files as $k => $v) {
switch (true) {
case false === $v = realpath(filter_var($v)):
case !is_file($v):
case !is_readable($v):
continue; // or return false,throw new InvalidArgumentException
}
$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("rn",array(
"Content-Disposition: form-data; name="{$k}"; filename="{$v}"","Content-Type: application/octet-stream",));
}
// generate safe boundary
do {
$boundary = "---------------------" . md5(mt_rand() . microtime());
} while (preg_grep("/{$boundary}/",$body));
// add boundary for each parameters
array_walk($body,function (&$part) use ($boundary) {
$part = "--{$boundary}rn{$part}";
});
// add final boundary
$body[] = "--{$boundary}--";
$body[] = "";
// set options
return @curl_setopt_array($ch,array(
CURLOPT_POST => true,CURLOPT_POSTFIELDS => implode("rn",$body),CURLOPT_HTTPHEADER => array(
"Expect: 100-continue","Content-Type: multipart/form-data; boundary={$boundary}",// change Content-Type
),));
}
参数传递无影响,若是文件则在绝对路径前+"@"。唯一的区别就是将文件数据和普通数据用不同的数组区分开来,在模拟http的body部分时对其进行不同的处理。最终成功上传文件。 以上是脚本之家(jb51.cc)为你收集整理的全部代码内容,希望文章能够帮你解决所遇到的程序开发问题。 如果觉得脚本之家网站内容还不错,欢迎将脚本之家网站推荐给程序员好友。 (编辑:安卓应用网) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |
