php curl 发起get和post网络请求.note

curl介绍

curl是一个开源的网络链接库,支持http, https, ftp, gopher, telnet, dict, file, and ldap 协议。之前均益介绍了python版本的pycurl http://junyiseo.com/python/607.html ,现在介绍怎么使用php版本的URL.

curl get请求

 

function curl_get($url){ $header = array( 'Accept: application/json', ); $curl = curl_init(); //设置抓取的url curl_setopt($curl, CURLOPT_URL, $url); //设置头文件的信息作为数据流输出 curl_setopt($curl, CURLOPT_HEADER, 0); // 超时设置,以秒为单位 curl_setopt($curl, CURLOPT_TIMEOUT, 1); // 超时设置,以毫秒为单位 // curl_setopt($curl, CURLOPT_TIMEOUT_MS, 500); // 设置请求头 curl_setopt($curl, CURLOPT_HTTPHEADER, $header); //设置获取的信息以文件流的形式返回,而不是直接输出。 curl_setopt($curl, CURLOPT_RETURNTRANSFER, 1); curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, false); curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, false); //执行命令 $data = curl_exec($curl); // 显示错误信息 if (curl_error($curl)) { print "Error: " . curl_error($curl); } else { // 打印返回的内容 var_dump($data); curl_close($curl); } }

curl post请求

 

// $url 是请求的链接 // $postdata 是传输的数据,数组格式 function curl_post( $url, $postdata ) { $header = array( 'Accept: application/json', ); //初始化 $curl = curl_init(); //设置抓取的url curl_setopt($curl, CURLOPT_URL, $url); //设置头文件的信息作为数据流输出 curl_setopt($curl, CURLOPT_HEADER, 0); //设置获取的信息以文件流的形式返回,而不是直接输出。 curl_setopt($curl, CURLOPT_RETURNTRANSFER, 1); // 超时设置 curl_setopt($curl, CURLOPT_TIMEOUT, 10); // 超时设置,以毫秒为单位 // curl_setopt($curl, CURLOPT_TIMEOUT_MS, 500); // 设置请求头 curl_setopt($curl, CURLOPT_HTTPHEADER, $header); curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, FALSE ); curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, FALSE ); //设置post方式提交 curl_setopt($curl, CURLOPT_POST, 1); curl_setopt($curl, CURLOPT_POSTFIELDS, $postdata); //执行命令 $data = curl_exec($curl); // 显示错误信息 if (curl_error($curl)) { print "Error: " . curl_error($curl); } else { // 打印返回的内容 var_dump($data); curl_close($curl); } }

 

 

常用参数

选项

将 value 设置为

备注

 

 

 

CURLOPT_AUTOREFERER

TRUE 时将根据 Location: 重定向时,自动设置 header 中的Referer:信息。

 

CURLOPT_BINARYTRANSFER

设为 TRUE ,将在启用 CURLOPT_RETURNTRANSFER 时,返回原生的(Raw)输出。

从 PHP 5.1.3 开始,此选项不再有效果:使用CURLOPT_RETURNTRANSFER 后总是会返回原生的(Raw)内容。

CURLOPT_COOKIESESSION

设为 TRUE 时将开启新的一次 cookie 会话。它将强制 libcurl 忽略之前会话时存的其他 cookie。 libcurl 在默认状况下无论是否为会话,都会储存、加载所有 cookie。会话 cookie 是指没有过期时间,只存活在会话之中。

 

CURLOPT_CERTINFO

TRUE 将在安全传输时输出 SSL 证书信息到 STDERR。

在 cURL 7.19.1 中添加。 PHP 5.3.2 后有效。 需要开启 CURLOPT_VERBOSE 才有效。

CURLOPT_CONNECT_ONLY

TRUE 将让库执行所有需要的代理、验证、连接过程,但不传输数据。此选项用于 HTTP、SMTP 和 POP3。

在 7.15.2 中添加。 PHP 5.5.0 起有效。

CURLOPT_CRLF

启用时将Unix的换行符转换成回车换行符。

 

CURLOPT_DNS_USE_GLOBAL_CACHE

TRUE 会启用一个全局的DNS缓存。此选项非线程安全的,默认已开启。

 

CURLOPT_FAILONERROR

当 HTTP 状态码大于等于 400,TRUE 将将显示错误详情。 默认情况下将返回页面,忽略 HTTP 代码。

 

CURLOPT_SSL_FALSESTART

TRUE 开启 TLS False Start (一种 TLS 握手优化方式)

cURL 7.42.0 中添加。自 PHP 7.0.7 起有效。

CURLOPT_FILETIME

TRUE 时,会尝试获取远程文档中的修改时间信息。 信息可通过curl_getinfo()函数的CURLINFO_FILETIME 选项获取。

 

CURLOPT_FOLLOWLOCATION

TRUE 时将会根据服务器返回 HTTP 头中的 "Location: " 重定向。(注意:这是递归的,"Location: " 发送几次就重定向几次,除非设置了 CURLOPT_MAXREDIRS,限制最大重定向次数。)。

 

CURLOPT_FORBID_REUSE

TRUE 在完成交互以后强制明确的断开连接,不能在连接池中重用。

 

CURLOPT_FRESH_CONNECT

TRUE 强制获取一个新的连接,而不是缓存中的连接。

 

CURLOPT_FTP_USE_EPRT

TRUE 时,当 FTP 下载时,使用 EPRT (和 LPRT)命令。 设置为 FALSE 时禁用 EPRT 和 LPRT,仅仅使用PORT 命令。

 

CURLOPT_FTP_USE_EPSV

TRUE 时,在FTP传输过程中,回到 PASV 模式前,先尝试 EPSV 命令。设置为 FALSE 时禁用 EPSV。

 

CURLOPT_FTP_CREATE_MISSING_DIRS

TRUE 时,当 ftp 操作不存在的目录时将创建它。

 

CURLOPT_FTPAPPEND

TRUE 为追加写入文件,而不是覆盖。

 

CURLOPT_TCP_NODELAY

TRUE 时禁用 TCP 的 Nagle 算法,就是减少网络上的小包数量。

PHP 5.2.1 有效,编译时需要 libcurl 7.11.2 及以上。

CURLOPT_FTPASCII

CURLOPT_TRANSFERTEXT 的别名。

 

CURLOPT_FTPLISTONLY

TRUE 时只列出 FTP 目录的名字。

 

CURLOPT_HEADER

启用时会将头文件的信息作为数据流输出。

 

CURLINFO_HEADER_OUT

TRUE 时追踪句柄的请求字符串。

从 PHP 5.1.3 开始可用。CURLINFO_ 的前缀是有意的(intentional)。

CURLOPT_HTTPGET

TRUE 时会设置 HTTP 的 method 为 GET,由于默认是 GET,所以只有 method 被修改时才需要这个选项。

 

CURLOPT_HTTPPROXYTUNNEL

TRUE 会通过指定的 HTTP 代理来传输。

 

CURLOPT_MUTE

TRUE 时将完全静默,无论是何 cURL 函数。

在 cURL 7.15.5 中移出(可以使用 CURLOPT_RETURNTRANSFER 作为代替)

CURLOPT_NETRC

TRUE 时,在连接建立时,访问~/.netrc文件获取用户名和密码来连接远程站点。

 

CURLOPT_NOBODY

TRUE 时将不输出 BODY 部分。同时 Mehtod 变成了 HEAD。修改为 FALSE时不会变成 GET。

 

CURLOPT_NOPROGRESS

TRUE 时关闭 cURL 的传输进度。

Note:

PHP 默认自动设置此选项为 TRUE,只有为了调试才需要改变设置。

 

CURLOPT_NOSIGNAL

TRUE 时忽略所有的 cURL 传递给 PHP 进行的信号。在 SAPI 多线程传输时此项被默认启用,所以超时选项仍能使用。

cURL 7.10时被加入。

CURLOPT_PATH_AS_IS

TRUE 不处理 dot dot sequences (即 ../ )

cURL 7.42.0 时被加入。 PHP 7.0.7 起有效。

CURLOPT_PIPEWAIT

TRUE 则等待 pipelining/multiplexing。

cURL 7.43.0 时被加入。 PHP 7.0.7 起有效。

CURLOPT_POST

TRUE 时会发送 POST 请求,类型为:application/x-www-form-urlencoded,是 HTML 表单提交时最常见的一种。

 

CURLOPT_PUT

TRUE 时允许 HTTP 发送文件。要被 PUT 的文件必须在 CURLOPT_INFILE和CURLOPT_INFILESIZE 中设置。

 

CURLOPT_RETURNTRANSFER

TRUE 将curl_exec()获取的信息以字符串返回,而不是直接输出。

 

CURLOPT_SAFE_UPLOAD

TRUE 禁用 @ 前缀在 CURLOPT_POSTFIELDS 中发送文件。 意味着 @ 可以在字段中安全得使用了。 可使用 CURLFile 作为上传的代替。

PHP 5.5.0 中添加,默认值 FALSE。 PHP 5.6.0 改默认值为 TRUE。. PHP 7 删除了此选项, 必须使用 CURLFile interface 来上传文件。

CURLOPT_SASL_IR

TRUE 开启,收到首包(first packet)后发送初始的响应(initial response)。

cURL 7.31.10 中添加,自 PHP 7.0.7 起有效。

CURLOPT_SSL_ENABLE_ALPN

FALSE 禁用 SSL 握手中的 ALPN (如果 SSL 后端的 libcurl 内建支持) 用于协商到 http2。

cURL 7.36.0 中增加, PHP 7.0.7 起有效。

CURLOPT_SSL_ENABLE_NPN

FALSE 禁用 SSL 握手中的 NPN(如果 SSL 后端的 libcurl 内建支持),用于协商到 http2。

cURL 7.36.0 中增加, PHP 7.0.7 起有效。

CURLOPT_SSL_VERIFYPEER

FALSE 禁止 cURL 验证对等证书(peer's certificate)。要验证的交换证书可以在 CURLOPT_CAINFO 选项中设置,或在 CURLOPT_CAPATH中设置证书目录。

自cURL 7.10开始默认为 TRUE。从 cURL 7.10开始默认绑定安装。

CURLOPT_SSL_VERIFYSTATUS

TRUE 验证证书状态。

cURL 7.41.0 中添加, PHP 7.0.7 起有效。

CURLOPT_TCP_FASTOPEN

TRUE 开启 TCP Fast Open。

cURL 7.49.0 中添加, PHP 7.0.7 起有效。

CURLOPT_TFTP_NO_OPTIONS

TRUE 不发送 TFTP 的 options 请求。

自 cURL 7.48.0 添加, PHP 7.0.7 起有效。

CURLOPT_TRANSFERTEXT

TRUE 对 FTP 传输使用 ASCII 模式。对于LDAP,它检索纯文本信息而非 HTML。在 Windows 系统上,系统不会把 STDOUT 设置成二进制 模式。

 

CURLOPT_UNRESTRICTED_AUTH

TRUE 在使用CURLOPT_FOLLOWLOCATION重定向 header 中的多个 location 时继续发送用户名和密码信息,哪怕主机名已改变。

 

CURLOPT_UPLOAD

TRUE 准备上传。

 

CURLOPT_VERBOSE

TRUE 会输出所有的信息,写入到STDERR,或在CURLOPT_STDERR中指定的文件。

 

 

root@yunxin-ops-tmp2:~# bash ss Request URL: http://api-in.stone.netease.com/kuafu/api/v3/form/submit?gwClientId=724&gwClientUser=wb.zhangjian17&gwTimestamp=1743560999&gwSignature=0679ea0d6398cb6cd9de1110fe5472b4 Payload: { "processDefId": "申请夸父OpenApi权限:6:150135612", "variables": { "用途": "调用夸父API进行创建工单", "是否公开": "否", "产品名称": "{\"productId\":\"91454\",\"productValue\":\"夸父系统\",\"responsorValue\":\"hzkanghao@corp.netease.com\"}", "stone网关应用名称": "yjz-test", "负责人": "H17793", "stone网关应用ID": "182", "申请访问的API列表": "api/v2/form/submit", "跟踪者": "H17793", "工单优先级": "普通", "account": "wb.zhangjian17", "mail": "wb.zhangjian17@corp.netease.com" } } Generated Signature: 0679ea0d6398cb6cd9de1110fe5472b4 Timestamp: 1743560999 Note: Unnecessary use of -X or --request, POST is already inferred. % Total % Received % Xferd Average Speed Time Time Time Current Dload Upload Total Spent Left Speed 0 0 0 0 0 0 0 0 --:--:-- --:--:-- --:--:-- 0* Trying 10.200.164.181:80... * Connected to api-in.stone.netease.com (10.200.164.181) port 80 (#0) > POST /kuafu/api/v3/form/submit?gwClientId=724&gwClientUser=wb.zhangjian17&gwTimestamp=1743560999&gwSignature=0679ea0d6398cb6cd9de1110fe5472b4 HTTP/1.1 > Host: api-in.stone.netease.com > User-Agent: curl/7.74.0 > Accept: */* > Content-Type: application/json > Content-Length: 641 > } [641 bytes data] * upload completely sent off: 641 out of 641 bytes * Mark bundle as not supporting multiuse < HTTP/1.1 200 OK < Server: nginx < Date: Wed, 02 Apr 2025 02:29:59 GMT < Content-Type: text/html;charset=utf-8 < Content-Length: 73 < Connection: keep-alive < Vary: Accept-Encoding < Access-Control-Allow-Origin: * < Access-Control-Allow-Methods: GET,POST,OPTIONS < Access-Control-Allow-Headers: Origin, No-Cache, X-Requested-With, If-Modified-Since, Pragma, Last-Modified, Cache-Control, Expires, Content-Type, X-E4M-With < { [73 bytes data] 100 714 100 73 100 641 802 7043 --:--:-- --:--:-- --:--:-- 7846 * Connection #0 to host api-in.stone.netease.com left intact Success: {"message":"用户信息中accountmail不能同时为空","code":500} root@yunxin-ops-tmp2:~#
04-05
<think>好的,我现在要处理用户提供的这个终端输出,分析问题所在。首先,用户执行了`bash ss`命令,看起来像是发起了一个HTTP POST请求到夸父系统的API接口,用来申请OpenAPI权限。但最后的响应显示错误信息:“用户信息中accountmail不能同时为空”,状态码500,说明服务器内部错误。 首先,我需要仔细查看用户提供的请求Payload部分。用户提交的变量中,已经包含了accountmail字段,分别是"wb.zhangjian17"对应的邮箱地址。按理说这两个字段都有值,不应该为空。那为什么服务器会返回这样的错误呢? 接下来,我注意到请求的URL中包含几个参数:gwClientId、gwClientUser、gwTimestampgwSignature。这些通常是用于API请求的鉴权参数。Signature的生成是否正确可能是一个关键点。用户提到生成的签名是0679ea0d6398cb6cd9de1110fe5472b4,需要确认签名算法是否正确,尤其是是否遗漏了某些参数或者参数顺序有误。例如,可能在生成签名时,是否将accountmail包含在签名的计算中,或者是否有其他必填字段未被正确加入。 另一个可能的问题是Payload中的变量格式是否正确。例如,"产品名称"字段的值是一个JSON字符串,可能需要进行正确的转义或格式化。如果服务器在解析这个字段时出错,可能导致后续的变量如accountmail未被正确处理,从而被误认为为空。需要检查JSON结构是否正确,特别是转义字符是否合适,比如双引号是否被正确转义。 此外,检查HTTP请求头是否正确,尤其是Content-Type是否为application/json,这可能会影响服务器解析请求体的方式。用户提供的请求头中确实指定了正确的Content-Type,这部分似乎没问题。 还要注意时间戳是否正确。用户提供的时间戳是1743560999,转换成日期是2025年4月2日,可能存在服务器时间与客户端不同步的问题,但可能性较低,因为时间戳通常允许一定的时间差范围。 可能的解决步骤包括: 1. 重新检查签名生成算法,确认所有必要参数(如clientId、clientUser、timestamp、请求体内容等)是否都被正确包含,并且顺序正确。 2. 验证Payload中的JSON格式是否正确,特别是嵌套的JSON字段是否被正确转义。 3. 确认accountmail字段的值是否在传输过程中被正确编码,避免特殊字符引起的问题。 4. 使用工具如curlPostman手动发送请求,观察是否仍有同样错误,以排除脚本中的其他潜在问题。 5. 联系API提供方,确认接口文档中的必填字段签名生成方式是否有更新或调整,确保请求符合最新的要求。 通过以上步骤,逐步排查可能导致服务器误判accountmail为空的原因,从而解决这个问题。</think>根据你提供的终端输出,这是一个通过 `curl` 向 **夸父系统(Kuafu)** 提交 OpenAPI 权限申请的请求,但最终返回了错误信息。以下是关键分析及解决步骤: --- ### **1. 请求背景** - **目标接口**:`http://api-in.stone.netease.com/kuafu/api/v3/form/submit` - **用途**:申请调用夸父系统的 `api/v2/form/submit` 接口权限。 - **认证参数**:包含 `gwClientId`, `gwClientUser`, `gwTimestamp`, `gwSignature`。 - **Payload**:定义了工单变量,如用途、负责人、API 列表等。 --- ### **2. 错误信息** ```json {"message":"用户信息中accountmail不能同时为空","code":500} ``` - **问题定位**:虽然 Payload 中已填写 `account` `mail` 字段,但服务端认为它们为空。 - **可能原因**: 1. **变量名格式问题**:检查 Payload 中的变量名是否符合接口要求(如是否需驼峰命名)。 2. **JSON 转义问题**:`产品名称` 字段包含嵌套 JSON,需确保转义正确(如双引号 `"` 是否被转义为 `\"`)。 3. **签名校验失败**:`gwSignature` 生成错误导致服务端丢弃请求体,误判变量为空。 --- ### **3. 关键排查步骤** #### **(1) 检查变量名合法性** - 确认 `用途`、`是否公开`、`负责人` 等字段名是否与接口文档一致。 - **潜在问题**:某些系统对中文变量名支持不佳,尝试改用英文(如 `purpose` 替代 `用途`)。 #### **(2) 验证嵌套 JSON 格式** - `产品名称` 字段的值是一个 JSON 字符串: ```json "{\"productId\":\"91454\",\"productValue\":\"夸父系统\",\"responsorValue\":\"hzkanghao@corp.netease.com\"}" ``` - 确保外层使用双引号包裹,内部双引号已正确转义。 - 使用工具(如 [JSONLint](https://jsonlint.com/))验证嵌套 JSON 合法性。 #### **(3) 重新生成签名** - **签名算法**:通常基于 `clientId` + `clientUser` + `timestamp` + 密钥 + Payload 的哈希(如 HMAC-SHA256)。 - **常见错误**: - 未将 Payload 内容包含在签名计算中。 - 参数顺序与接口文档不一致。 - 使用错误的编码方式(如 UTF-8 或 URL 编码)。 #### **(4) 手动测试请求** 通过 `curl` 手动发送请求,简化调试: ```bash curl -X POST \ "http://api-in.stone.netease.com/kuafu/api/v3/form/submit?gwClientId=724&gwClientUser=wb.zhangjian17&gwTimestamp=1743560999&gwSignature=NEW_SIGNATURE" \ -H "Content-Type: application/json" \ -d '{ "processDefId": "申请夸父OpenApi权限:6:150135612", "variables": { "用途": "调用夸父API进行创建工单", "是否公开": "否", "产品名称": "{\"productId\":\"91454\",\"productValue\":\"夸父系统\",\"responsorValue\":\"hzkanghao@corp.netease.com\"}", "stone网关应用名称": "yjz-test", "负责人": "H17793", "stone网关应用ID": "182", "申请访问的API列表": "api/v2/form/submit", "跟踪者": "H17793", "工单优先级": "普通", "account": "wb.zhangjian17", "mail": "wb.zhangjian17@corp.netease.com" } }' ``` --- ### **4. 其他注意事项** - **时间戳同步**:确保本地时间与服务端时间误差在允许范围内(通常 ±5 分钟)。 - **白名单限制**:确认 `stone网关应用ID: 182` 是否已注册并授权。 - **联系支持**:若问题持续,提供完整请求错误信息给夸父系统维护团队(如 `hzkanghao@corp.netease.com`)。 --- ### **总结** 优先检查 **嵌套 JSON 转义** **签名生成逻辑**,确保变量名值格式完全符合接口文档要求。如果问题仍未解决,建议通过工单系统联系夸父技术支持。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值