HTTP请求头怎么改?User-Agent、Referer和自定义Header的配置方法

Python requests默认UA暴露脚本身份。本文覆盖User-Agent、Referer等请求头的作用和修改方法,含Python requests、aiohttp和curl的配置示例和合理边界。鲸云IP国内独享住宅IP,客服微信x31471626改价月付6元起。
发布于
1

你用Python requests发了一个请求,目标网站返回403。同样的URL在浏览器里打开就正常。不是你代理IP的问题——是请求头暴露了你不是一个正常的浏览器。服务器通过User-Agent判断客户端类型,通过Referer判断来源页面,通过Accept-Language判断语言偏好。代码发出的请求头通常只有寥寥几行,和浏览器的几十个头部比起来,一眼就能识别出是程序而不是人。

本文覆盖HTTP请求头的作用、常用头部的修改方法、在Python requests和curl中的配置、以及请求头修改的合理边界。鲸云IP全系为国内独享住宅IP,配好请求头后的请求更接近真实用户行为。客服微信x31471626改价月付6元起。

HTTP请求头是什么

每次HTTP请求都包含两部分:请求行(GET /index.html HTTP/1.1)和请求头(一系列的Key: Value键值对)。请求头告诉服务器关于客户端的信息:

  • User-Agent:客户端的软件类型和版本。浏览器、爬虫、命令行工具各有不同的UA字符串
  • Referer:当前请求的来源页面URL。比如从百度搜索结果点进一个网站,Referer就是百度的搜索URL
  • Accept-Language:客户端偏好的语言。服务器可能根据这个返回不同语言的内容
  • Accept-Encoding:客户端支持的压缩算法(gzip、br等),影响响应体积和速度
  • Cookie:服务器之前在客户端存储的数据,用于会话保持和身份识别
  • Content-Type:请求体的格式(POST请求时),如application/json
  • Authorization:认证凭据,Bearer Token或Basic Auth
  • Host:请求的目标域名(HTTP/1.1必须发送)

除了这些标准头,服务器也可以自定义任意头部。常见的自定义头部包括X-Forwarded-For(记录原始客户端IP)、X-Requested-With(标识AJAX请求)等。

Python requests中修改请求头

requests库默认的User-Agent是 python-requests/2.x.x,这等于直接告诉服务器「我是一个Python脚本」。第一步就是把UA改成常见浏览器的值:

import requests

headers = {
    "User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/126.0.0.0 Safari/537.36",
    "Accept": "text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8",
    "Accept-Language": "zh-CN,zh;q=0.9,en;q=0.8",
    "Accept-Encoding": "gzip, deflate, br",
    "Referer": "https://www.google.com/",
    "Connection": "keep-alive",
    "Cache-Control": "max-age=0",
}

proxies = {
    "http": "http://代理IP:端口",
    "https": "http://代理IP:端口",
}

response = requests.get(
    "https://目标网站",
    headers=headers,
    proxies=proxies,
    timeout=10
)

常见浏览器的User-Agent字符串(2026年参考):

  • Chrome Windows: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/126.0.0.0 Safari/537.36
  • Chrome macOS: Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/126.0.0.0 Safari/537.36
  • Firefox Windows: Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:128.0) Gecko/20100101 Firefox/128.0
  • Safari macOS: Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/605.1.15 (KHTML, like Gecko) Version/17.5 Safari/605.1.15
  • Edge Windows: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/126.0.0.0 Safari/537.36 Edg/126.0.0.0

注意:仅修改User-Agent是不够的。一个真实的Chrome浏览器会发送20-30个请求头,而你的Python脚本只发了3-5个。头部数量本身也是一个指纹信号。但也别把Chrome的所有头部原封不动复制过来——有些头部(如sec-ch-ua)是浏览器自动生成的,手动写反而会暴露。

curl中修改请求头

curl默认的User-Agent是 curl/x.x.x,同样会暴露:

# 修改单个头部
curl -H "User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) Chrome/126.0.0.0" https://目标网站

# 修改多个头部
curl -H "User-Agent: Mozilla/5.0 ..." 
     -H "Accept-Language: zh-CN,zh;q=0.9" 
     -H "Referer: https://www.google.com/" 
     -x 代理IP:端口 
     https://目标网站

curl的 -A 参数是 -H "User-Agent: ..." 的简写:

curl -A "Mozilla/5.0 (Windows NT 10.0; Win64; x64) Chrome/126.0.0.0" https://目标网站

aiohttp(Python异步)中修改请求头

import aiohttp
import asyncio

async def fetch():
    headers = {
        "User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) Chrome/126.0.0.0",
        "Accept": "text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8",
        "Accept-Language": "zh-CN,zh;q=0.9",
    }
    async with aiohttp.ClientSession(headers=headers) as session:
        async with session.get(
            "https://目标网站",
            proxy="http://代理IP:端口"
        ) as resp:
            return await resp.text()

asyncio.run(fetch())

ClientSession(headers=headers) 设置的头部会自动应用到该Session的所有请求。如果某个请求需要不同的头部,可以在单次请求中覆盖:

async with session.get(url, headers={"Referer": "https://specific-referer.com/"}) as resp:
    ...

请求头的合理边界

修改请求头是合法的HTTP客户端配置,但有几个边界需要注意:

  • 不要伪造来源做欺诈:把Referer改成银行网站去请求其他服务,可能构成欺诈
  • 尊重robots.txt:Crawler的User-Agent如果被robots.txt禁止,不应强行访问
  • 不要隐藏真实身份做恶意操作:伪造UA去撞库、刷接口属于违法行为
  • 面向合规场景可以正常配置:企业授权的数据采集、API测试、自动化巡检中修改请求头是标准的开发实践

很多网站会通过请求头的一致性来识别爬虫。比如UA说自己是Chrome但Accept-Language写的是en-US而其他头部暗示是中文用户——这些不一致本身就是识别信号。追求「完美伪装」通常得不偿失,保持头部的基本合理和适度即可。

查看请求实际发送的头部

调试时想知道自己到底发了什么头部,用 httpbin.org/headers 回显:

curl -x 代理IP:端口 -H "User-Agent: MyCustomAgent/1.0" https://httpbin.org/headers

返回的JSON会列出服务器接收到所有头部。对比你发送的和服务器实际收到的,确认代理没有添加或删除头部。

用requests库时也可以这么做:

resp = requests.get(
    "https://httpbin.org/headers",
    headers={"User-Agent": "MyCustomAgent/1.0"},
    proxies=proxies
)
print(resp.json()["headers"])

检查返回结果中是否有代理服务器额外添加的头部(如Via、X-Forwarded-For),这些头部有时会暴露你使用了代理。

合规声明

HTTP请求头的配置属于HTTP协议的正常使用范畴。在合法授权范围内修改请求头用于API调试、自动化测试和合规数据采集是标准的开发实践。使用代理IP和HTTP客户端时应遵守《网络安全法》《个人信息保护法》《数据安全法》及相关网站的服务条款和robots协议。

常见问题(FAQ)

只改User-Agent就够了吗?
不够。虽然改UA是第一步,但真实浏览器会发送20-30个请求头,脚本通常只有几个。头部数量本身就是一个指纹信号。建议至少加上Accept、Accept-Language、Accept-Encoding、Connection等常见头部。但不要盲目填所有头部——有些是浏览器自动生成的,手动写反而暴露。
修改请求头会让代理IP更隐蔽吗?
请求头和代理IP是两个独立的维度。代理IP改的是网络出口地址,请求头改的是客户端行为特征。两者配合使用能让请求更接近真实用户行为,但不能保证一定不被检测到。更关键的是行为模式(请求频率、页面跳转路径)。
怎么查看我实际发送了哪些请求头?
用httpbin.org/headers回显:curl -x 代理IP:端口 https://httpbin.org/headers。返回的JSON显示服务器收到的所有头部。对比你设置的和服务器实际收到的,确认代理没有添加或删除头部。
鲸云IP的住宅IP配合修改请求头效果更好吗?
鲸云IP是国内独享住宅IP,归属地和ISP数据稳定,配合合理的请求头配置能让整体行为更接近真实用户。但语言偏好、时区、请求节奏等信号也需要保持一致。客服微信x31471626改价月付6元起。

本文由作者原创/授权发布于极跃圈(jiyueip.com)未经许可,禁止转载。题图来自Unsplash,基于CC0协议。

声明:极跃圈(JIYUEIP.com)内网友所发表的所有内容及言论仅代表其本人,并不反映任何极跃圈(JIYUEIP.com)之意见及观点。

0 讨论
热门最新
总结
暂无总结
0 / 600

暂无数据