使用Requests+BeautifulSoup爬取Reddit子板块遇到的问题求解
问题解答
问题1:仅能获取10条帖子的原因
- 核心原因是Reddit官网默认采用懒加载逻辑,首次请求返回的静态HTML仅包含前10条左右的帖子内容,剩余内容需要用户滚动页面时才会异步加载,requests只能获取首次请求的静态内容,不属于代码错误、请求限制或者lxml兼容性问题。
- 解决方案:可以改用Selenium、Playwright等自动化工具模拟页面滚动触发异步加载,或者直接调用Reddit官方开放的接口获取数据,稳定性远高于硬爬静态页面。
问题2:parsecomments函数失效的原因
代码存在3处明显错误:
- 响应对象属性拼写错误:requests请求返回的响应对象没有
c.u属性,正确属性为c.url,该处错误会直接触发异常分支跳过后续逻辑。 - 链接拼接重复:你选中的帖子链接
href本身已经携带https://www.reddit.com前缀,额外拼接前缀会生成无效的重复前缀URL,导致请求地址错误。 - 选择器适配错误:一是你使用的类名是Reddit前端动态生成的hash类名,会不定期更新失效;二是评论页的DOM结构和列表页不同,用
.Post选择器无法匹配到评论内容节点。
修正后可运行参考代码
import requests from bs4 import BeautifulSoup import lxml headers = {'User-Agent':'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/605.1.15 (KHTML, like Gecko) Version/17.0 Safari/605.1.15'} def parsecomments(u): c = requests.get(u, headers=headers) # 先打印状态码确认请求是否成功 print('评论页请求状态码:', c.status_code) s = BeautifulSoup(c.text, 'lxml') # 用Reddit官方自定义标签匹配评论,比动态类名更稳定 for comment in s.find_all('shreddit-comment'): try: comment_text = comment.find('div', {'slot': 'comment'}).get_text(strip=True) print('评论内容:', comment_text) except Exception as e: continue url = 'https://www.reddit.com/r/JuJutsuKaisen/' r = requests.get(url, headers=headers) print('列表页请求状态码:', r.status_code) soup = BeautifulSoup(r.text, 'lxml') for item in soup.find_all('shreddit-post'): try: print('----------------------------------------') # 用自定义标签的内置属性获取内容,适配性更强 likes = item.get('score') title = item.get('post-title') comment_count = item.get('comment-count') post_link = item.get('content-href') print('点赞数:', likes) print('标题:', title) print('评论数:', comment_count) print('帖子链接:', post_link) parsecomments(post_link) except Exception as e: print('单条帖子解析错误', str(e))
注:Reddit的前端结构会不定期更新,若选择器失效可自行打开浏览器调试工具更新对应节点的匹配规则。
内容的提问来源于stack exchange,提问作者Gummy Ocean
相关产品推荐
相关产品推荐

