You need to enable JavaScript to run this app.
最新活动
大模型
产品
解决方案
定价
生态与合作
支持与服务
开发者
了解我们

Playwright登录会话Cookie迁移至Python requests调用受保护API返回403 Forbidden问题求助

解决Playwright Cookie迁移至requests时返回403 Forbidden的问题

我之前也碰到过一模一样的糟心事——明明Playwright登录成功了,把Cookie移去requests就直接403,折腾了好久才找到几个关键的排查方向,你可以挨个试试:


1. 不要只传递Cookie的name/value,要完整导入Cookie属性

浏览器里的Cookie不止有名称和值,还有DomainPathSameSite这些关键属性,requests直接传字典的话会丢失这些信息,服务器很可能因此不认你的会话。试试用requests.utils.add_dict_to_cookiejar把Playwright的完整Cookie对象导入到requests会话里:

import requests
from requests.utils import add_dict_to_cookiejar

# Playwright登录后获取完整Cookie列表(不是只取name:value)
playwright_cookies = context.cookies()

# 创建requests会话并导入Cookie
session = requests.Session()
for cookie in playwright_cookies:
    add_dict_to_cookiejar(session.cookies, cookie)

# 发起请求时不用再手动传cookies参数
response = session.get(
    "https://example.com/api/data",
    headers={
        "accept": "application/json",
        "csrf-token": session.cookies.get("CSRF_COOKIE", ""),
        "user-agent": page.evaluate("navigator.userAgent"),  # 直接用Playwright的UA,避免不一致
        "referer": "https://example.com/"  # 很多网站会校验Referer头
    }
)

2. 确认CSRF Token的来源是否正确

你现在是直接取Cookie里的CSRF_COOKIE当请求头,但很多网站的CSRF Token其实是存在页面的meta标签或者JS全局变量里的,不是Cookie值。比如:

# 登录后从页面meta标签提取CSRF Token
csrf_token = page.locator('meta[name="csrf-token"]').get_attribute('content')

# 或者如果是存在window对象里的情况
csrf_token = page.evaluate("window.csrfToken")

# 再把这个值放到请求头里
HEADERS["csrf-token"] = csrf_token

3. 严格对齐请求头的所有细节

服务器可能会校验请求头的细微差异,比如:

  • User-Agent: 直接用Playwright页面的UA,不要手动写(毕竟手动写的可能和浏览器实际发送的有差别)
  • Referer: 必须是网站的首页或当前页面地址,很多API会拒绝无Referer的请求
  • 其他自定义头: 打开浏览器F12的Network面板,找到登录后正常请求API的请求头,把所有非默认的头都加到requests里

4. 检查Cookie值的格式问题

你写了清理引号的函数,但还要注意:

  • 有些Cookie值是URL编码的,Playwright返回的是解码后的,而requests可能需要编码后的?可以试试用urllib.parse.quote处理值
  • 不要随意修改Cookie值,先直接用Playwright返回的原始值测试,排除格式问题

5. 对比浏览器和requests的请求差异

最有效的排查方法是:

  1. 在浏览器里登录后,打开Network面板,找到正常调用API的请求,右键「复制为cURL」
  2. 把cURL转换成Python requests代码(可以用在线工具或者手动转)
  3. 对比你自己的代码,看哪里缺少了头信息、Cookie属性或者参数

内容的提问来源于stack exchange,提问作者P K

火山引擎 最新活动