自学内容网 自学内容网

Scrapy爬虫实战——某瓣250

# 按照我个人的习惯,在一些需要较多的包作为基础支撑的项目里,习惯使用虚拟环境,因为这样能极大程度的减少出现依赖冲突的问题。依赖冲突就比如A、B、C三个库,A和B同时依赖于C,但是A需要的C库版本大于N,而B库在C库版本大于N时会有依赖错误。如果是在同一个项目里三者都需要,那么我们必然要想办法解决,但是如果是在不同项目里,但是使用同一环境所引起的,那么只需要使用不同环境即可,能省去不少时间和精力。

一、新建项目

(一)新建python项目并创建虚拟环境

使用pycharm (社区版即可),新建一个项目,解释器就选新建虚拟环境。等待python解释器制作好虚拟环境后,在界面左下角找到终端,点击进入新建好的虚拟环境。

如果进入失败的话直接在终端找到该文件夹,进入到进入到当前创建虚拟目录的\env_demo\Scripts下,使用命令activate激活虚拟环境。

无论你是如何进入的终端,在命令行的最前面只要出现了虚拟环境名称,例如

(.venv) D:\pythonProject\scrapy\myscrapy>

那么就证明虚拟环境创建成功。

(二)安装scrapy库并新建一个scrapy项目

使用pip命令安装scrapy

pip install scrapy

在安装过程中可以看到安装了众多的依赖包,这就是为什么要使用虚拟环境的主要原因了——易于管理。

使用startproject新建scrapy项目,例如项目就叫douban

scrapy startproject douban

执行之后应该会提示两个命令,依次执行即可。

cd douban
scrapy genspider example example.com

scrapy genspider example example.com中example和example.com写哈

例如本次案例,就是scrapy genspider scrapydouban  https://movie.douban.com/top250

新建完成之后就可以看到如下项目结构。

二、完善项目

(一)准备工作

打开scrapydouban.py,代码如下。

import scrapy


class ScrapydoubanSpider(scrapy.Spider):
    name = "scrapydouban"
    allowed_domains = ["movie.douban.com"]
    start_urls = ["https://movie.douban.com/top250"]

    def parse(self, response):
        pass

name 就是我们的scrapy项目名字,这里改的话要到setting等文件里也要改哟!因为豆瓣250的请求网址的参数是每次递增25,所以我们需要重写一下start_requests,还有就是parse函数可能会报一个警告,需要加一个参数。重写之后的代码如下。

import scrapy
from scrapy import Request
from typing import Iterable
class ScrapydoubanSpider(scrapy.Spider):
    name = "scrapydouban"
    allowed_domains = ["movie.douban.com"]
    start_urls = ["https://movie.douban.com/top250"]

    def start_requests(self) -> Iterable[Request]:
        for i in range(10):
            url = f'https://movie.douban.com/top250?start={i * 25}&filter='
            yield scrapy.Request(url=url, callback=self.parse)

    def parse(self, response, **kwargs):
        pass

注意在start-requests中必须要有一个yield一下,将网址返回给引擎。

在parse中,response就是返回的response对象,初学时我们主要工作就是在这里。

(二)目标网页Xpath提取目标元素

首先定位到包含一整页的包含所有信息的li标签组成的集合。选中的xpath为

//*[@id="content"]/div/div[1]/ol//li

我们选取四个字段进行提取,标题、导演等信息文本、评分、评价人数和短评,提取相当于上述所提取的每个li的xpath。

出于规范管理,我们还可以在item文件里定义一下我们的字段,并且在scrapydouban中引用。

import scrapy


class DoubanItem(scrapy.Item):
    title = scrapy.Field()
    text = scrapy.Field()
    rating = scrapy.Field()
    review = scrapy.Field()
    quote = scrapy.Field()

完善后的parse函数如下。

    def parse(self, response, **kwargs):
        lis = response.xpath('//*[@id="content"]/div/div[1]/ol//li')  # 获取所有li标签
        for i in lis:
            item = DoubanItem()
            item['title'] = i.xpath('./div/div[2]/div[1]/a/span[1]/text()').extract_first()  # 标题
            item['text'] = i.xpath('./div/div[2]/div[2]/p[1]/text()[1]').extract_first().replace('\n',
                                                                                                 '').strip().replace(
                ' ', '')  # 文本
            item['rating'] = i.xpath('./div/div[2]/div[2]/div/span[2]/text()').extract_first()  # 评分
            item['review'] = i.xpath('./div/div[2]/div[2]/div/span[4]/text()').extract_first()  # 评价人数
            item['quote'] = i.xpath('./div/div[2]/div[2]/p[2]/span[1]/text()').extract_first()  # 短评
            print(item)
            yield item

三、运行项目

使用命令运行该项目

scrapy crawl scrapydouban

在终端就会输出很多的日志信息,但是我们希望的元素信息并没有打印出来。仔细看看日志信息。

响应是403,为什么?好像忘了加请求头了,那不就明摆着告诉目标服务器我是一个爬虫程序嘛,所以需要在setting.py中打开头部信息。

默认头部信息,建议完善更改

DEFAULT_REQUEST_HEADERS = {
   "Accept": "text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8",
   "Accept-Language": "en",
}

再次使用命令启动项目

到此我们就已经可以得到目标元素了。后续章节还会介绍其他组件,包括中间件,数据库入库,js逆向调用等。


原文地址:https://blog.csdn.net/yj2094632273/article/details/142370701

免责声明:本站文章内容转载自网络资源,如本站内容侵犯了原著者的合法权益,可联系本站删除。更多内容请关注自学内容网(zxcms.com)!