Python请求getfpv站点sitemap.xml返回403,网站如何区分浏览器与Python请求?
我之前也碰到过这种头疼的情况——明明把浏览器的请求头抄得一丝不差,结果用Python请求还是被403拒了,后来才搞清楚,网站识别“是不是浏览器”,可不止看请求头这么简单,这里面有好几个门道:
请求头的顺序可能露馅了
浏览器发送请求头是有固定顺序的,比如一般先传Host,接着是User-Agent,再是Accept这类,但Python的requests库(尤其是旧版本)会按字典的键排序来发送请求头,和浏览器的顺序完全不一样。有些网站会把请求头的顺序作为验证项,只要顺序不对,直接就判定是爬虫。你可以试试用collections.OrderedDict来指定headers的顺序,或者换用httpx这种更贴近浏览器行为的库。可能漏了浏览器自动加的关键字段
你复制的headers看起来挺全,但浏览器会自动添加一些你没注意到的隐性字段,比如Sec-Fetch-User: ?1(这个字段用来标记是用户主动发起的导航请求,不是脚本自动触发的),还有Upgrade-Insecure-Requests: 1、Connection: keep-alive这些。你可以打开浏览器开发者工具的“网络”面板,查看完整的请求头,把那些漏掉的字段补上再试试。TLS指纹差异才是核心原因(最大概率)
这是现在很多反爬的杀手锏!浏览器和Python的requests在建立TLS连接时,握手过程中的细节完全不同——比如支持的加密套件顺序、TLS版本的优先级、扩展字段的类型等,这些细节会形成一个独特的“TLS指纹”。网站只要检测这个指纹,就能轻松区分出是真实浏览器还是脚本,哪怕你的请求头完全一致。这种情况下,单纯改headers没用,得用专门的工具模拟浏览器的TLS指纹,比如curl_cffi(用法和requests类似,能模拟Chrome、Firefox的指纹),或者直接用playwright这种无头浏览器,完全复刻浏览器的行为,肯定能绕过检测,就是速度会慢一点。其他小细节
比如requests默认会自动处理重定向,但浏览器处理重定向的逻辑可能略有不同;或者你的请求里有没有带一些浏览器自动处理的编码信息?不过这种情况比较少见,可以最后再排查。
备注:内容来源于stack exchange,提问作者Fab49er

