m.weibo.cn:大厂接口里的一股清流
在各厂疯狂堆签名、堆设备指纹的今天,微博 H5 站 m.weibo.cn 的接口防护朴素得令人感动:没有客户端签名,没有设备指纹,核心就是标准的 XSRF 双 cookie 校验 + 频率限制。它是协议爬虫入门的最佳练手目标,也是理解"限流型防护"和"签名型防护"本质差异的好样本。
XSRF 流程:标准到可以写进教科书
import requests
session = requests.Session()
session.headers.update({'User-Agent': 'Mozilla/5.0 (iPhone; CPU iPhone OS 16_0 like Mac OS X) ...'})
# 第一步:访问任意页面,拿 XSRF-TOKEN cookie
session.get('https://m.weibo.cn/')
xsrf = session.cookies.get('XSRF-TOKEN')
# 第二步:后续请求把 cookie 值原样放进请求头
headers = {'X-XSRF-TOKEN': xsrf, 'Referer': 'https://m.weibo.cn/'}
resp = session.get(
'https://m.weibo.cn/api/container/getIndex?containerid=100103type%3D1%26q%3D逆向',
headers=headers
)服务端比对 cookie 里的 XSRF-TOKEN 和请求头的 X-XSRF-TOKEN 一致即放行。这是防 CSRF 的标准方案,对爬虫来说等于没有门槛。
接口体系:containerid 一把梭
m.weibo.cn 的接口设计高度统一,几乎所有数据都走 container/getIndex,区别只在 containerid 参数:
| 数据 | containerid 格式 |
|---|---|
| 用户资料 | 100505{uid} |
| 用户微博列表 | 107603{uid} |
| 搜索综合 | 100103type=1&q={关键词} |
| 搜索用户 | 100103type=3&q={关键词} |
| 评论 | 100808{mid} 系列 |
分页用 page 参数或 since_id 游标,响应 json 里的 cardlistInfo 字段带分页状态,结构清晰。
未登录的访客体系
很多人以为 m.weibo.cn 必须登录,其实微博有一套访客令牌体系:未登录时访问会引导你生成一个访客 SUB cookie。流程:
- 访问接口被拦,返回里有
login相关跳转 - 请求
https://passport.weibo.com/visitor/genvisitor拿访客凭证 - 请求
https://passport.weibo.com/visitor/visitor?a=incarnate&...换取访客态的SUB和SUBPcookie - 带着访客 SUB 访问接口,权限介于未登录和登录之间
访客态能覆盖大部分公开数据接口,但频率阈值比登录态低。
频率控制:真正的防护在这里
微博的防护哲学是"行为限流",实测阈值(单 IP):
- 未登录/访客态:每分钟 30 次左右开始返回 418 状态码(I'm a teapot,微博拿它当限流码用),触发后冷却 10-30 分钟
- 登录态(真实 SUB):阈值高 5-10 倍,但触发后惩罚更重——可能直接要求账号验证
风控升级路径:418 限流 → 强制登录 → 账号手机验证。所以批量场景的标准架构是:账号池 + IP 池 + 令牌桶控速,单账号每分钟 10-15 次是长期安全线。
精髓:三个工程细节
- cookie 的域和有效期。
XSRF-TOKEN是会话级 cookie,session 重启要重拿;SUB是长期的,但异地 IP 使用会触发安全验证。账号池里每个号的 SUB 要和常用 IP 段绑定。 - 响应的 ok 字段。微博接口业务层用
{"ok": 1, "data": ...}表示成功,ok: 0时看msg——"请先登录"是访客态掉了,"操作频繁"是限流了,两者处理策略不同,别混为一谈。 - 移动端 ua 是隐形校验。m.weibo.cn 校验 ua 是否为移动端,桌面 ua 会被重定向到 weibo.com(那是另一套接口体系)。ua 一旦选定就固定,别在会话中途换。
总结
- m.weibo.cn 无签名无指纹,XSRF 双 cookie 是全部门槛
- containerid 体系统一,一套代码吃遍所有数据类型
- 访客体系可以免登录拿公开数据
- 真正的防护是 418 限流,解法是账号池+控速,不是技术对抗