爬虫是什么:原理、边界与合规

爬虫的五步链路与合规检查点

爬虫就是一段自动化的 HTTP 客户端:代替人在浏览器里点击、翻页、复制,把公开网页或接口返回的数据按规则提取并保存下来。技术上它不神秘,真正决定一个采集项目能不能长期跑下去的是边界意识——抓什么、抓多少、以什么身份抓、抓完能用来做什么。

一个爬虫的三步循环

无论用 requests 脚本、Selenium 还是 Scrapy,骨架永远是这三步:

请求(Request) → 解析(Parse) → 存储(Store)
     ↑                                    │
     └────── 发现新 URL,回到队列 ←────────┘
  • 请求:构造 URL 与请求头,发起 HTTP 请求,拿到 HTML、JSON 或文件。
  • 解析:提取结构化字段,同时发现下一页与详情页链接,形成待抓队列。
  • 存储:写入 CSV、JSONL 或数据库,并记录已处理状态,便于断点续爬。

requests 负责第一步,BeautifulSouplxmlparsel 负责第二步,csvsqlite3 或数据库负责第三步;Selenium / Playwright 只是把第一步换成"驱动真实浏览器",Scrapy 则把三步装进一个自带调度与限速的框架。

能做什么,不能做什么

可以做不可以做
采集无需登录即可访问的公开数据抓取需要登录或付费才能看到的内容
读取开放数据、政府公开信息采集他人隐私信息(手机号、身份证、位置轨迹)
按官方开放 API 与配额调用数据绕过验证码、付费墙、IP 封禁等访问控制
用于个人学习、学术研究与内部效率工具原样转卖抓取内容、二次分发受版权保护的作品
合理频率下访问,像正常读者一样高并发式抓取,实质性影响对方服务

先问有没有官方接口,再考虑写爬虫

动手写代码之前先花十分钟做这件事,往往能省掉几天的活:

1. 找官方开放平台或 API 文档,申请 API Key(有配额、有文档、有授权依据)
2. 找开放数据集(政府开放数据、数据交易所、公开数据集社区)
3. 找站点主动提供的 RSS、sitemap.xml 或结构化数据
4. 联系站点商务或数据合作,购买授权数据
5. 以上都没有,再评估自写爬虫,并接受它随时可能因改版而失效

官方接口比爬虫稳得多:字段有文档、版本可控、不怕改版,还省掉整条反爬对抗的链路。爬虫是最后手段,不是第一选择。

robots.txt 怎么读

robots.txt 是站点放在根目录(例如 https://example.com/robots.txt)的访问约定,用 User-agent 分组声明哪些路径允许或禁止抓取,部分站点还会给出 Crawl-delaySitemap

User-agent: *            # 对所有爬虫生效的默认分组
Disallow: /search        # 禁止抓取 /search 开头的路径
Allow: /search/about     # 更具体的允许规则优先
Disallow: /private/
Crawl-delay: 1           # 建议的请求间隔(秒)
Sitemap: https://example.com/sitemap.xml

读法的三个要点:

  • 分组按 User-agent 匹配,最具体者优先;Disallow: / 是全站禁止,Disallow:(空值)是全站允许。
  • 它只约束"抓取",不授权"使用"。允许抓取不等于允许转载、商用或再分发。
  • 它没有强制力,但它是站点表达意愿的方式。无视它,意味着在明知对方不同意的情况下继续访问。

Python 标准库自带解析器,把判断交给它,比自己用字符串硬拼可靠:

from urllib.parse import urljoin
from urllib.robotparser import RobotFileParser

import requests  # pip install requests

UA = "RuilinToolsBot/1.0 (+https://example.com/bot; contact@example.com)"

def load_robots(base: str) -> RobotFileParser:
    """下载并解析 robots.txt;取不到就按禁止处理,宁可保守。"""
    rp = RobotFileParser()
    rp.set_url(urljoin(base, "/robots.txt"))
    try:
        resp = requests.get(rp.url, headers={"User-Agent": UA}, timeout=(3, 10))
        resp.raise_for_status()
        rp.parse(resp.text.splitlines())
    except requests.RequestException as exc:
        print(f"robots.txt 获取失败:{exc},按禁止处理")
        rp.disallow_all = True
    return rp

if __name__ == "__main__":
    site = "https://example.com"
    parser = load_robots(site)
    for path in ("/", "/search?q=python", "/api/list"):
        target = urljoin(site, path)
        print(target, "允许" if parser.can_fetch(UA, target) else "禁止")
    print("Crawl-delay:", parser.crawl_delay(UA))  # 可据此设置请求间隔

频率控制与身份标识

把请求间隔与并发上限写进代码,而不是靠"我抓得不多"的直觉:

控制项建议起点说明
请求间隔单线程 1~3 秒站点声明了 Crawl-delay 时取两者较大值
单域名并发不超过 4~5并发是给别人的服务器加压力,不是给自己刷分
单轮总量先小批量试跑 50~100 条字段与频率确认正常后再放开
抓取时段避开对方业务高峰凌晨抓取对双方都更友好
失败退避429/5xx 时指数退避并暂停对方在说"慢一点",不要硬顶
身份标识带联系方式的自定义 UA出问题时能被联系,也便于对方按组放行

合规判断的三个问题

动手前依次回答,任何一个是"不确定",就先停下来弄清楚:

问题判断依据答"是"怎么办
数据是公开的吗不登录、不付费、不猜参数就能看到仍需遵守 robots.txt 与站点条款
会影响对方服务吗并发与频率是否显著高于正常用户降频、错峰、改用官方接口
涉及个人信息吗是否含可识别到具体自然人的字段不采集;确需采集则取得同意并最小化

法律边界:三部法律

法律与数据采集相关的要点
《个人信息保护法》处理个人信息需有合法性基础与告知同意,遵循最小必要原则,禁止非法买卖个人信息
《数据安全法》数据分类分级保护,重要数据的交易与出境受限,不得以窃取等非法方式获取数据
《著作权法》作品受法律保护,复制与传播需授权,合理使用范围有限,不覆盖大规模转载

再叠加上刑法中侵犯公民个人信息、非法获取计算机信息系统数据的相关条款,可以概括成一句话:突破访问控制去拿本不该看到的数据,事情就从技术问题变成了法律问题。

常见误区

误区后果正确做法
能打开页面就等于能抓忽略条款与 robots 约定,风险自担先看 robots.txt 与用户协议
伪装成浏览器 UA 就安全只隐去了身份,不改变行为性质用可识别的自定义 UA,并控制频率
并发越高效率越高触发限流,甚至被临时封禁先测单请求耗时,再定并发上限
抓到的数据可以直接商用侵权风险,图文与付费内容尤甚找授权、买数据,或只用开放数据
robots.txt 没强制力就可以无视民事乃至刑事风险由自己承担把它当作对方明确的意愿声明

小结:爬虫只是把「请求—解析—存储」自动化,技术门槛不高,真正决定项目寿命的是边界——先找官方 API 与开放数据,读 robots.txt 与站点条款,控制频率并标明身份,不碰个人隐私与付费内容,不绕过任何访问控制。

笔记加载中…