接口测试:Postman与Python Requests对比及请求失败问题排查
这种情况我之前踩过好几次坑,太懂这种Postman能跑但代码不行的挫败感了!其实核心原因是Postman和Requests在处理POST请求的细节上有不少容易被忽略的差异,我给你拆解几个最常见的可能性:
1. XML数据的编码不一致
Postman默认会用UTF-8编码发送XML数据,但Python的requests.post如果直接传字符串类型的xml给data参数,会用系统默认编码(比如GBK)发送,这会导致服务端解析XML时出错。
解决办法:把XML字符串手动编码成UTF-8的字节流再发送:
headers = {'Content-Type': 'application/xml'} r = requests.post(url, data=xml.encode('utf-8'), headers=headers)
2. 请求头缺失关键字段
Postman在发送请求时,会自动帮你添加很多默认请求头(比如User-Agent、Accept),但你的Python代码只设置了Content-Type。很多服务端会校验这些头信息,缺失的话直接拒绝请求。
解决办法:打开Postman的「请求控制台」,把所有请求头复制到Python代码里:
headers = { 'Content-Type': 'application/xml', 'User-Agent': 'PostmanRuntime/7.32.3', # 换成你Postman里的实际值 'Accept': '*/*', 'Cache-Control': 'no-cache', # 其他Postman里显示的请求头 } r = requests.post(url, data=xml.encode('utf-8'), headers=headers)
3. SSL证书验证差异
Postman默认可能关闭了SSL证书验证(或者你手动设置了忽略证书),但Requests默认是强制验证证书的。如果目标网站的证书不被系统信任,Requests会直接报错,而Postman能正常请求。
解决办法:临时关闭验证(生产环境不建议,最好指定合法证书路径):
r = requests.post(url, data=xml.encode('utf-8'), headers=headers, verify=False)
4. 代理设置不匹配
如果你在Postman里配置了代理才能访问目标接口,但Python代码里没设置代理,自然会请求失败;反之亦然。
解决办法:按照Postman的代理配置,在Requests里添加代理参数:
proxies = { 'http': 'http://your-proxy-address:port', 'https': 'https://your-proxy-address:port', } r = requests.post(url, data=xml.encode('utf-8'), headers=headers, proxies=proxies)
5. XML格式的细微差异
Postman在你输入XML时,可能会自动帮你转义特殊字符(比如把&转成&),或者规范化换行符/空格。但你的Python字符串里的XML可能存在格式不规范的问题,导致服务端无法解析。
排查技巧:把Python里要发送的XML字符串打印出来,和Postman里的原始XML对比,看看有没有格式差异。
最后教你一个终极排查方法:用requests.utils.dump_request(r.request)把Python发送的原始请求内容打印出来,和Postman控制台里的原始请求做对比,就能精准定位差异点了!
内容的提问来源于stack exchange,提问作者TheNone

