PowerShell调用API返回403错误但Postman/Python/cURL可正常访问
Invoke-WebRequest、Invoke-RestMethod返回403但Postman/cURL/Python可正常访问,均为PowerShell默认请求配置和常规客户端存在差异,被API侧WAF拦截导致,按以下优先级排查修复:
替换默认User-Agent
PowerShell 5.x默认请求携带的User-Agent包含WindowsPowerShell特征字段,绝大多数公开API的WAF规则会直接拦截该类UA标识。
修复方式:请求时手动指定通用浏览器/常规客户端UA即可,示例:# 模拟Chrome桌面端UA $requestUA = "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/125.0.0.0 Safari/537.36" $response = Invoke-RestMethod '目标API地址' -Method GET -Headers $headers -UserAgent $requestUA强制使用高版本TLS协议
PowerShell 5.1默认仅启用TLS 1.0协议,当前几乎所有公开API均要求TLS 1.2及以上版本建立连接,协议协商失败时部分服务不会返回明确协议错误,直接返回403状态码。
修复方式:执行请求前先配置当前会话的安全协议支持:[Net.ServicePointManager]::SecurityProtocol = [Net.SecurityProtocolType]::Tls12 -bor [Net.SecurityProtocolType]::Tls13 # 配置完成后再执行API请求命令补充必要校验请求头
部分API的WAF会校验Accept请求头,PowerShell默认Accept值为*/*,少数接口要求必须匹配application/json等明确值才会放行,在原有头字典中补充即可:$headers.Add("Accept", "application/json")跳过系统代理干扰
PowerShell默认读取系统代理配置,若系统代理规则对PowerShell进程请求做了拦截篡改,也会触发403,请求时添加-NoProxy参数即可跳过代理:$response = Invoke-RestMethod '目标API地址' -Method GET -Headers $headers -NoProxy
快速定位技巧:抓包对比Postman正常请求与PowerShell失败请求的原始报文,逐行对比协议版本、请求头字段差异,可100%定位具体拦截规则。
内容的提问来源于stack exchange,提问作者Python Developer

