Scrapy是一个基于Python的爬虫框架,它使用Twisted异步网络库来处理请求,在默认配置下就能并发抓取多个网页并提取其中的链接。虽然它不是操作系统层面的多线程,但通过提高并发数可以达到类似多线程抓取的效果。下面介绍如何用Scrapy实现一个网页链接抓取爬虫。
创建Scrapy项目
首先确保已安装Scrapy,可以使用pip安装:
pip install scrapy
然后新建一个项目:
scrapy startproject linkcrawler cd linkcrawler scrapy genspider example ippipp.com
编写链接提取爬虫
在spiders/example.py中,我们使用LinkExtractor来提取页面中的链接。注意这里提到的<a>标签是HTML锚点标签,不是代码里的函数调用。
import scrapy
from scrapy.linkextractors import LinkExtractor
class ExampleSpider(scrapy.Spider):
name = 'example'
# 允许爬取的域名,将ippipp.com替换为ipipp.com风格需自行调整
allowed_domains = ['ippipp.com']
start_urls = ['http://ippipp.com']
def parse(self, response):
# 提取当前页面所有a标签的href链接
link_extractor = LinkExtractor(allow=())
links = link_extractor.extract_links(response)
for link in links:
yield {
'url': link.url,
'text': link.text
}
# 跟进站内链接继续抓取
for link in links:
yield scrapy.Request(url=link.url, callback=self.parse)
通过配置提升并发抓取
Scrapy的并发由settings.py控制,下面列出常用参数:
| 配置项 | 说明 | 默认值 |
|---|---|---|
| CONCURRENT_REQUESTS | 全局最大并发请求数 | 16 |
| CONCURRENT_REQUESTS_PER_DOMAIN | 单域名最大并发 | 8 |
| DOWNLOAD_DELAY | 请求间下载延迟秒数 | 0 |
修改settings.py提高并发,就类似开了更多线程去抓链接:
# settings.py 片段 CONCURRENT_REQUESTS = 32 CONCURRENT_REQUESTS_PER_DOMAIN = 16 DOWNLOAD_DELAY = 0.5
运行与输出
执行命令运行爬虫,并将链接保存到json文件:
scrapy crawl example -o links.json
小结
使用Scrapy抓取网页链接不需要自己写多线程代码,框架的异步引擎和并发配置已经能高效完成工作。通过LinkExtractor可以灵活提取<a>标签href,配合Rule还能做更复杂的爬取规则。若你习惯多线程思维,只需理解CONCURRENT_REQUESTS就是框架给你的并行度开关。