Scrapy爬取Docker Hub分页异常:仅爬一页,如何获取所有符合规则页面?
解决Scrapy爬取Docker Hub分页仅爬取一页的问题
问题分析与调整方案
1. 修正LinkExtractor的正则匹配规则
你当前的正则r'\?q=.*&page=\d+'未包含完整的路径前缀,可能无法匹配页面上的分页链接(比如实际链接是/search?q=python&page=2这种带前缀的格式)。调整正则以覆盖完整路径:
rules = ( Rule(LinkExtractor(allow=r'/search\?q=.*&page=\d+'), follow=True, process_request=set_playwright_true, callback='parse_page' # 使用字符串形式的回调函数名,避免未定义问题 ), )
2. 确保初始请求触发分页跟进
如果爬虫的初始请求是不带page参数的https://hub.docker.com/search?q=python,页面内的分页链接可能无法被正确捕获。可以直接从第一页发起初始请求:
def start_requests(self): yield scrapy.Request( url='https://hub.docker.com/search?q=python&page=1', callback=self.parse_page, meta={'playwright': True} )
3. 处理动态加载的分页元素
Docker Hub的分页栏是动态渲染的,使用Playwright时需要确保等待页面完全加载及分页元素出现,可在set_playwright_true函数中添加等待逻辑:
def set_playwright_true(self, request, spider): request.meta['playwright'] = True request.meta['playwright_kwargs'] = { 'wait_until': 'networkidle', 'wait_for_selector': 'nav[aria-label="Pagination"]', # 等待分页导航栏加载完成 } return request
4. 手动构造分页请求(备选方案)
若自动跟进分页链接失效,可在parse_page中手动检测并构造下一页请求:
def parse_page(self, response): self.logger.info("Parsing page: %s", response.url) # 数据提取逻辑 for result in response.css('div#searchResults div.some-class'): yield { 'title': result.css('h2 a::text').get(), 'link': result.css('h2 a::attr(href)').get(), } # 判断是否存在下一页 has_next_page = response.css('nav[aria-label="Pagination"] a[rel="next"]').exists() if has_next_page: current_page = int(response.url.split('page=')[-1]) next_page_url = f'https://hub.docker.com/search?q=python&page={current_page + 1}' yield scrapy.Request( url=next_page_url, callback=self.parse_page, meta={'playwright': True} )
5. 调整爬虫基础设置
确保反爬相关设置合理,避免被拦截:
# settings.py ROBOTSTXT_OBEY = False # 根据需求调整,Docker Hub的robots.txt可能限制爬取 DOWNLOAD_DELAY = 2 # 添加下载延迟,降低被反爬识别的概率
内容的提问来源于stack exchange,提问作者Vlajic Stevan
相关产品推荐
相关产品推荐

