微博数据采集:API申请与认证、频率控制、字段解析
微博的数据采集,说白了就是跟微博服务器「要数据」。但人家不会白给你,得先证明你是谁、想干嘛。我刚开始做舆情监控那会儿,光申请API就折腾了两天,后来发现其实流程挺固定的。今天我把这些坑都给你填平。
一、微博API申请与认证
要调用微博API,第一步是注册成为开发者。去 open.weibo.com 创建一个应用,选「网页应用」或「移动应用」都行。我个人习惯选网页应用,因为调试起来方便。
创建完成后,你会拿到两个关键参数:
- App Key:应用的唯一标识,相当于你的身份证号
- App Secret:应用的密钥,千万别泄露,相当于你的银行卡密码
认证方式主要有两种:
| 认证方式 | 适用场景 | 有效期 |
|---|---|---|
| OAuth 2.0 授权码模式 | 需要用户授权,获取用户数据 | 7天(Access Token) |
| Client Credentials | 只获取公开数据,不需要用户授权 | 长期(需定期刷新) |
我建议做舆情监控用第二种。为什么呢?因为你不需要模拟某个用户去发微博,只需要抓公开的帖子就行。代码实现也很简单:
import requests
# 你的应用凭证
app_key = '你的App Key'
app_secret = '你的App Secret'
# 获取Access Token
url = 'https://api.weibo.com/oauth2/access_token'
data = {
'client_id': app_key,
'client_secret': app_secret,
'grant_type': 'client_credentials'
}
response = requests.post(url, data=data)
access_token = response.json().get('access_token')
print(f'获取到的Token: {access_token}')
⚠️ 注意:Access Token 有有效期,过期后需要重新获取。我曾经因为没做Token自动刷新,半夜监控程序挂了,第二天才发现。建议写个定时任务,每小时检查一次Token状态。
二、API调用频率控制
微博API不是你想调就能随便调的。每个应用都有频率限制,超了就会被封IP或者封应用。我见过有人一天调了10万次,结果应用直接被拉黑。
官方频率限制大概是这样的:
| 接口类型 | 限制频率 |
|---|---|
| 获取用户信息 | 150次/小时 |
| 搜索微博 | 200次/小时 |
| 获取微博详情 | 150次/小时 |
| 获取评论 | 100次/小时 |
嗯,这里要注意:不同等级的开发者,频率限制不一样。普通开发者就是上面这个数,高级开发者会高一些。但咱们做舆情监控,普通开发者够用了。
怎么控制频率呢?我常用的方法是「令牌桶算法」。说白了就是:
- 准备一个桶,里面放令牌
- 每次调用API,从桶里拿一个令牌
- 桶空了就等着,等令牌慢慢补充
代码实现也不复杂:
import time
import threading
class RateLimiter:
def __init__(self, max_calls, period):
self.max_calls = max_calls # 最大调用次数
self.period = period # 时间窗口(秒)
self.calls = [] # 调用时间戳列表
self.lock = threading.Lock()
def allow(self):
with self.lock:
now = time.time()
# 移除过期的时间戳
self.calls = [t for t in self.calls if now - t < self.period]
if len(self.calls) < self.max_calls:
self.calls.append(now)
return True
return False
# 使用示例:每小时最多150次
limiter = RateLimiter(150, 3600)
def call_api():
if limiter.allow():
# 调用微博API
print('API调用成功')
else:
print('频率超限,等待中...')
time.sleep(60) # 等一分钟再试
💡 小技巧:我一般会在每次API调用后打印剩余次数,方便监控。比如:
print(f'剩余调用次数: {150 - len(limiter.calls)}')。这样出了问题能第一时间发现。
三、数据字段解析
拿到数据后,怎么提取有用信息?微博API返回的是JSON格式,结构挺清晰的。我拿搜索微博接口举个例子:
# 搜索微博
search_url = 'https://api.weibo.com/2/search/statuses.json'
params = {
'access_token': access_token,
'q': '舆情监控', # 搜索关键词
'count': 50 # 每页返回数量
}
response = requests.get(search_url, params=params)
data = response.json()
# 解析返回的数据
for status in data.get('statuses', []):
print(f"微博ID: {status['id']}")
print(f"作者: {status['user']['screen_name']}")
print(f"内容: {status['text']}")
print(f"发布时间: {status['created_at']}")
print(f"转发数: {status['reposts_count']}")
print(f"评论数: {status['comments_count']}")
print(f"点赞数: {status['attitudes_count']}")
print('---')
关键字段我整理了一下:
| 字段名 | 含义 | 用途 |
|---|---|---|
| id | 微博唯一ID | 去重、关联评论 |
| text | 微博正文 | 情感分析、关键词提取 |
| created_at | 发布时间 | 时间序列分析 |
| user.screen_name | 作者昵称 | 用户画像 |
| reposts_count | 转发数 | 传播热度 |
| comments_count | 评论数 | 讨论热度 |
| attitudes_count | 点赞数 | 认可度 |
这里有个坑:text 字段里可能包含HTML标签,比如 <br /> 换行符。我建议用 re.sub(r'<[^>]+>', '', text) 清洗一下。另外,微博内容可能包含表情符号,比如 [微笑],这些在情感分析时要注意处理。
📌 核心逻辑总结:微博数据采集的流程就是「申请凭证 → 获取Token → 控制频率 → 调用接口 → 解析字段」。每一步都有坑,但踩过一次就记住了。
最后,我用一张图把整个流程串起来:
你看,整个流程其实不复杂。关键是把每一步的细节处理好。尤其是频率控制,很多人栽在这上面。我建议你刚开始做的时候,先写个简单的demo,只调10次API试试水,确认没问题了再上生产环境。
🔧 实用建议:调试阶段可以用微博的「测试接口」,频率限制宽松很多。等代码稳定了再切换到正式接口。另外,记得把Token存到配置文件里,别硬编码在代码中——我曾经把Token提交到GitHub,结果被微博官方警告了。