Scrapy命令行用法精讲
前面的例子中已经演示了一些用法,如创建项目、创建爬虫等,本节将做一个比较系统的介绍。
Scrapy 命令其实就是一个 Python 脚本,其内容如下所示:
# -*- coding: utf-8 -*- import re # 正则表达式 import sys # 用来得到命令行参数信息 from scrapy.cmdline import execute if __name__ == '__main__': sys.argv[0] = re.sub(r'(-script.pyw?|.exe)?$', '', sys.argv[0]) sys.exit(execute())
比较常见的用法是创建一个项目,该项目包含有配置文件、爬虫文件以及结果数据的定义等。也可以使用 Scrapy 命令来创建一个项目的基本框架,方法如下:
scrapy startproject 项目名称 [目录名称]
其中目录名称是可选的,如果没有指定,目录名称就是项目名称。下面是两个简单的例子,演示了两个常用的用法。
$ scrapy startproject ex1 #ex1是项目的名称
New Scrapy project 'ex1', using template directory
'/usr/local/lib/python2.7/site-packages/scrapy/templates/project', created in:
/Users/py/work/scrapy/ex1
You can start your first spider with:
cd ex1
scrapy genspider example example.com [u'text1', u'text2']
# 指定项目目录名称,如果没有指定就是项目的名称
$ scrapy startproject ex2 ex2Folder
New Scrapy project 'ex2', using template directory
'/usr/local/lib/python2.7/site-packages/scrapy/templates/project',
created in:
/Users/py/work/scrapy/ex2Folder
You can start your first spider with:
cd ex2Folder
scrapy genspider example example.com
在创建项目后,需要创建爬虫。默认情况下是不会自动创建爬虫的,所以这一步是必须要做的。可以使用下面命令格式来创建一个爬虫:
scrapy genspider [选项参数] 爬虫名 域名
常见的选项参数如表 1 所示。
参 数 | 说 明 |
---|---|
–force | 强制创建爬虫,即使该爬虫已经存在了 |
-t 模板名 –template=模板名 |
指定模板,如果没有指定,就使用 basic 模板 |
下面的例子演示了常见的爬虫创建方法:
# 使用basic模板来创建爬虫
$ scrapy genspider spider1 domain1.com
Created spider 'spider1' using template 'basic' in module:
ex1.spiders.spider1
# 查看这个爬虫的内容
$ cat ex1/spiders/spider1.py
# -*- coding: utf-8 -*-
import scrapy
class Spider1Spider(scrapy.Spider):
name = 'spider1'
allowed_domains = ['domain1.com']
start_urls = ['http://domain1.com/']
def parse(self, response):
pass
# 如果再次创建同名爬虫会出现错误
$ scrapy genspider spider1 domain2.com
Spider 'spider1' already exists in module:
ex1.spiders.spider1
# 如果带上-force,那么就可以覆盖原来的内容
$ scrapy genspider –force spider1 domain2.com
Created spider 'spider1' using template 'basic' in module:
ex1.spiders.spider1
# 指定模版,前面没有指定模版,所以使用basic模版
$ scrapy genspider -t crawl spider2 domain3.com
Created spider 'spider2' using template 'crawl' in module:
ex1.spiders.spider2
我们也通过 Scrapy 命令行来查看当前系统存在哪些爬虫模板,下面是该命令的格式:
scrapy genspider -l
下面例子演示了如何查看当前系统存在的爬虫模板。
# 列出所有的爬虫模板
$ scrapy genspider -l
Available templates:
basic
crawl
csvfeed
xmlfeed
在 Ubuntu Linux 下,安装完 Scrapy 之后就存在目录 /usr/local/lib/python3.5/dist-packages/scrap y/templates/spiders,在该目录下可以看到这些爬虫模板文件。
# 列出模板文件
$ ls -l /usr/local/lib/python3.5/dist-packages/scrapy/templates/spiders
total 16
-rw-r–r– 1 root staff 208 Mar 10 17:52 basic.tmpl
-rw-r–r– 1 root staff 657 Mar 10 17:52 crawl.tmpl
-rw-r–r– 1 root staff 571 Mar 10 17:52 csvfeed.tmpl
-rw-r–r– 1 root staff 565 Mar 10 17:52 xmlfeed.tmpl
下面是 basic 模板的内容:
# 查看basic模板文件的内容
$ cat /usr/local/lib/python3.5/dist-packages/scrapy/templates/spiders/ basic.tmpl
# -*- coding: utf-8 -*-
import scrapy
class $classname(scrapy.Spider): # 自定义的爬虫
name = '$name'
allowed_domains = ['$domain']
start_urls = ['http://$domain/']
def parse(self, response):
pass
在前面章节中,我们通过 cat 命令来查看某个模板的内容。Scrape 也提供了相关的命令来查看模板的内容,其优点是不需要记住模板的位置。
这个查看模板内容的命令格式如下:
scrapy genspider -d 模板名称
下面的例子演示了如何查看 basic 模板内容:
# 查看basic模板文件的内容
$ scrapy genspider -d basic
# -*- coding: utf-8 -*-
import scrapy
class $classname(scrapy.Spider):
name = '$name'
allowed_domains = ['$domain']
start_urls = ['http://$domain/']
def parse(self, response):
pass
下面查看另外一个模板 crawl 的内容:
# 查看crawl模板文件的内容
$ scrapy genspider -d crawl
# -*- coding: utf-8 -*-
import scrapy
from scrapy.linkextractors import LinkExtractor
from scrapy.spiders import CrawlSpider, Rule
class $classname(CrawlSpider):
name = '$name'
allowed_domains = ['$domain']
start_urls = ['http://$domain/']
rules = (
Rule(LinkExtractor(allow=r'Items/'), callback='parse_item',
follow=True),
)
def parse_item(self, response):
item = {}
#item['domain_id'] = response.xpath('//input[@id="sid"]/@value').
get()
#item['name'] = response.xpath('//div[@id="name"]').get()
#item['description'] = response.xpath('//div[@id="description"]').
get()
return item
可以使用模板创建自己的爬虫,这样会比从零开始创建一个完整的爬虫要节省一些时间。如果对从模板创建出来的爬虫不是很满意,也可以手动修改生成出来的爬虫。
Scrapy 自带了 basic、crawl、csvfeed 和 xmlfeed 4 种模板,我们可以使用命令来创建基于它们的爬虫,命令格式如下:
scrapy genspider -t 模板名 爬虫名 域名
这里的爬虫名会替代模板中的变量 $name,而域名会替代模板中的变量 $domain。
下面基于 crawl 模板来创建我们的爬虫 templateSpider,域名为 stackoverflow.com:
# 基于模板crawl创建爬虫templateSpider
# $domain=stackoverflow.com
$ scrapy genspider -t crawl templateSpider stackoverflow.com
Created spider 'templateSpider' using template 'crawl' in module:
ex1.spiders.templateSpider
$ scrapy list # 查看该爬虫
templateSpider. # 这就是我们新建的爬虫
$ cat ex1/spiders/templateSpider.py # 查看文件
# -*- coding: utf-8 -*-
… # 省略6行常规代码
class TemplatespiderSpider(CrawlSpider):
name = 'templateSpider'
allowed_domains = ['stackoverflow.com']
start_urls = ['http://stackoverflow.com/']
… # 省略11行常规代码
在定义完爬虫后可以通过命令行来将其启动,命令格式如下:
scrapy crawl 爬虫名
下面是某个爬虫启动的过程:
$ scrapy crawl spider1 # 启动爬虫spider1
# 显示一些系统版本信息
2019-03-28 02:51:54 [scrapy.utils.log] INFO: Scrapy 1.6.0 started (bot:
ex1)
2019-03-28 02:51:54 [scrapy.utils.log] INFO: Versions: lxml 4.3.2.0,
libxml2 2.9.9, cssselect 1.0.3, parsel 1.5.1, w3lib 1.20.0, Twisted
18.9.0,
Python 2.7.15 (default, Oct 2 2018, 11:47:18) –
[GCC 4.2.1 Compatible Apple LLVM 10.0.0 (clang-1000.11.45.2)],
pyOpenSSL 19.0.0 (OpenSSL 1.1.0j 20 Nov 2018), cryptography 2.4.2,
Platform Darwin-17.7.0-x86_64-i386-64bit
2019-03-28 02:51:54 [scrapy.crawler] INFO: # 爬虫信息
Overridden settings: {'NEWSPIDER_MODULE': 'ex1.spiders', '
SPIDER_MODULES': ['ex1.spiders'], 'ROBOTSTXT_OBEY': True, 'BOT_NAME': 'ex1'}
# 扩展信息
2019-03-28 02:51:54 [scrapy.middleware] INFO: Enabled extensions:
['scrapy.extensions.memusage.MemoryUsage',
… # 省略扩展信息
# 爬虫爬取内容的信息
2019-03-28 02:51:56 [scrapy.downloadermiddlewares.retry]
DEBUG: Retrying <GET http://domain2.com/>
… # 省略详细爬取过程信息
# 统计信息
2019-03-28 02:51:56 [scrapy.statscollectors] INFO: Dumping Scrapy stats:
… # 省略详细统计信息
# 关闭爬虫
2019-03-28 02:51:56 [scrapy.core.engine] INFO: Spider closed (finished)
可以通过爬虫列表命令来查看当前项目下全部的爬虫,命令格式如下:
scrapy list
下面的例子演示了爬虫列表命令的用法:
$ scrapy list # 显示当前所有的爬虫
settingUsageDemoSpider
spider1
spider2
templateSpider
# 创建一个新的爬虫new_spider_1
$ scrapy genspider new_spider_1 stackoverflow.com
Created spider 'new_spider_1' using template 'basic' in module:
ex1.spiders.new_spider_1
$ scrapy list # 再次查看当前所有的爬虫
new_spider_1 # 这就是刚才新建的爬虫
settingUsageDemoSpider
spider1
spider2
templateSpider
需要注意的是,必须在项目目录下面使用该命令,否则命令会失败。
$ scrapy list # 不在项目目录下,显示没有活动的项目
Scrapy 1.6.0 – no active project
Unknown command: list
Use "scrapy" to see available commands
爬取指定命令可以直接指定一个页面地址,让爬虫使用当前配置或者系统配置来爬取内容,这样便可以查看页面内容,或者 http 的头部信息。该命令格式如下:
scrapy fetch 页面地址
页面内容是在标准输出显示的。
下面的例子演示了仅输出 html 和仅输出 header 信息的用法。
# 得到http://www.example.com/l的页面信息
$ scrapy fetch http://www.example.com/
… # 省略一些系统信息内容
2019-03-21 08:42:01 [scrapy.middleware] INFO: Enabled item pipelines:
[] # pipelines
2019-03-21 08:42:01 [scrapy.core.engine] INFO: Spider opened
2019-03-21 08:42:01 [scrapy.extensions.logstats] INFO:
Crawled 0 pages (at 0 pages/min), scraped 0 items (at 0 items/min)
2019-03-21 08:42:01 [scrapy.extensions.telnet] INFO:
Telnet console listening on 127.0.0.1:6024
2019-03-21 08:42:02 [scrapy.core.engine] DEBUG:
Crawled (404) <GET http://www.example.com/robots.txt> (referer: None)
2019-03-21 08:42:02 [scrapy.core.engine] DEBUG: Crawled (404)
<GET http://www.example.com/> (referer: None)
<!doctype html> # 页面内容
… # 省略页面内容
2019-03-21 08:42:02 [scrapy.core.engine] INFO: Closing spider (finished)
2019-03-21 08:42:02 [scrapy.statscollectors] INFO: Dumping Scrapy
stats:
… # 省略统计信息
2019-03-21 08:42:02 [scrapy.core.engine] INFO: Spider closed (finished)
# 仅显示页面内容
$ scrapy fetch –nolog http://www.example.com/
<!doctype html>
<html>
… # 省略页面内容
</html>
# 仅显示http的头部信息
$ scrapy fetch –nolog –headers http://www.example.com/
> Accept-Language: en
> Accept-Encoding: gzip,deflate
> Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;
q=0.8
> User-Agent: Scrapy/1.6.0 (+https://scrapy.org)
>
< X-Cache: HIT
< Accept-Ranges: bytes
< Expires: Thu, 28 Mar 2019 00:52:14 GMT
< Vary: Accept-Encoding
< Server: ECS (oxr/830A)
< Last-Modified: Fri, 09 Aug 2013 23:54:35 GMT
< Etag: "1541025663"
< Cache-Control: max-age=604800
< Date: Thu, 21 Mar 2019 00:52:14 GMT
< Content-Type: text/html; charset=UTF-8
# 我们希望指定USER-AGENT,不用默认的Scrapy/1.6.0 (+https://scrapy.org)
$ scrapy fetch –nolog –headers
–set=USER_AGENT='MyUA' http://www.example.com/
> Accept-Language: en
> User-Agent: MyUA # 这就是我们设置的USER-AGENT
… # 省略其他的输出
如果希望查看某个页面的内容,可以使用 scrapy view 这个命令。该命令会启动系统默认的浏览器来打开指定的页面,并且使用的是 Scrapy 项目的配置信息。该命令的格式如下:
scrapy view 页面地址
由于使用的是项目的配置,所有其显示的内容可能和直接在浏览器中输入的网页地址不同。可以使用 scrapy view 命令来查看不同,并且可以在浏览器中检视内容,或者做一些调试操作。
下面的例子演示了该命令的用法:
# 启动view命令来打开页面http://stackoverflow.com/questions?sort=votes
$ scrapy view http://stackoverflow.com/questions?sort=votes
2019-03-21 08:28:54 [scrapy.utils.log] INFO: Scrapy 1.6.0 started (bot:
ex1)
… # 省略一些系统信息内容
5 2019-03-21 08:28:54 [scrapy.middleware] INFO: Enabled extensions:
… # 省略一些middlewares的输出
2019-03-21 08:28:54 [scrapy.middleware] INFO: Enabled item pipelines:
[]
2019-03-21 08:28:54 [scrapy.core.engine] INFO: Spider opened
2019-03-21 08:28:54 [scrapy.extensions.logstats] INFO:
Crawled 0 pages (at 0 pages/min), scraped 0 items (at 0 items/min)
2019-03-21 08:28:54 [scrapy.extensions.telnet] INFO:
Telnet console listening on 127.0.0.1:6024
2019-03-21 08:28:55 [scrapy.downloadermiddlewares.redirect] DEBUG:
Redirecting (301) to <GET https://stackoverflow.com/robots.txt>
from <GET http://stackoverflow.com/robots.txt>
2019-03-21 08:28:56 [scrapy.core.engine] DEBUG: Crawled (200)
# 得到爬虫协议文件
<GET https://stackoverflow.com/robots.txt> (referer: None)。
2019-03-21 08:28:56 [scrapy.downloadermiddlewares.redirect] DEBUG:
Redirecting (301) to <GET https://stackoverflow.com/questions?sort=
votes> from
<GET http://stackoverflow.com/questions?sort=votes>
2019-03-21 08:28:57 [scrapy.core.engine] DEBUG: Crawled (200)
<GET https://stackoverflow.com/questions?sort=votes> (referer: None)
2019-03-21 08:28:57 [scrapy.core.engine] INFO: Closing spider
(finished)
2019-03-21 08:28:57 [scrapy.statscollectors] INFO: Dumping Scrapy
stats:
… # 省略统计信息
2019-03-21 08:28:57 [scrapy.core.engine] INFO: Spider closed (finished)
其将页面下载到本地,然后启动浏览器来查看。注意看浏览器中的地址栏,显示的不是 stackoverflow.com,而是一个以 file:// 开头的本地文件。
前面的用法都是批量执行一个脚本,我们也可以使用交互的方式来执行。该方式一般是用来测试提取数据的代码,也就是用来测试 XPath 或 CSS 表达式,查看它们的工作方式及从爬取的网页中提取的数据。
在编写 spider 时,该终端提供了交互性测试表达式代码的功能,免去了每次修改后运行完整 spider 的麻烦。一旦熟悉了 Scrapy 终端后,就会发现其在开发和调试爬虫时的巨大作用。如果安装了 IPython,Scrapy 终端将使用。如果没有安装 IPython,那么其启动标准的 CPython 终端。
该命令的格式如下:
scrapy shell [页面地址]
其会启动一个 shell,我们可以以交互的方式在 shell 内进行操作。下面的例子中,我们在 ex1 项目下打开页面 http://www.example.com/,其会自动使用当前设置去下载该页面的内容,并且将 request、response 等信息都以变量的形式提供给我们。
# 启动shell,并让其打开http://www.example.com/
$ scrapy shell http://www.example.com/
2019-03-20 08:52:42 [scrapy.utils.log] INFO: Scrapy 1.6.0 started (bot:
ex1)
… # 省略scrapy的常规输出
2019-03-20 08:52:43 [scrapy.core.engine] DEBUG: Crawled (200)
<GET http://www.example.com/> (referer: None) # 下载页面
[s] Available Scrapy objects:
[s] scrapy scrapy module (contains scrapy.Request, scrapy.Selector,
etc)
[s] crawler <scrapy.crawler.Crawler object at 0x108a67c90>
[s] item {}
[s] request <GET http://www.example.com/>
[s] response <200 http://www.example.com/>
[s] settings <scrapy.settings.Settings object at 0x108a67f10>
[s] spider <DefaultSpider 'default' at 0x108eb7450>
[s] Useful shortcuts:
[s] fetch(url[, redirect=True]) Fetch URL and update local objects
(by default, redirects are followed)
[s] fetch(req) Fetch a scrapy.Request and update local
objects
[s] shelp() Shell help (print this help)
[s] view(response) View response in a browser
这时就可以查看各种信息了,如 settings、request、response 等,方法如下:
>>> request # 查看请求信息
<GET http://www.example.com/>
>>> request.method # 查看请求的方法
'GET'
>>> request.url # 查看请求的地址
'http://www.example.com/'
>>> response # 查看回应消息
<200 http://www.example.com/>
>>> response.status # 查看状态码
200
也可以使用 xpath 来提取相关内容,方法如下:
>>> response.xpath("//h1/text()").extract() # 查看所有h1标签的内容
[u'Example Domain']
>>> response.xpath("//a/@href").extract() # 提取页面中包含的链接的地址
[u'http://www.iana.org/domains/example']
>>> response.xpath("//head/meta").extract() # 提取头部的meta标签的值
[u'<meta charset="utf-8">',
u'<meta http-equiv="Content-type" content="text/html; charset=utf-8">',
u'<meta name="viewport" content="width=device-width, initial-scale=1">']
在不创建项目时,可以使用这种方法来运行定义在指定文件中的爬虫。该命令的格式如下:
scrapy runspider 源文件
下面是一个简单的例子:
# 启动文件spider1.py中定义的爬虫
$ scrapy runspider spider1.py
# 显示一些系统版本信息
2019-03-28 02:51:54 [scrapy.utils.log] INFO: Scrapy 1.6.0 started (bot:
ex1)
2019-03-28 02:51:54 [scrapy.utils.log] INFO: Versions: lxml 4.3.2.0,
libxml2 2.9.9, cssselect 1.0.3, parsel 1.5.1, w3lib 1.20.0, Twisted
18.9.0,
Python 2.7.15 (default, Oct 2 2018, 11:47:18) –
[GCC 4.2.1 Compatible Apple LLVM 10.0.0 (clang-1000.11.45.2)],
pyOpenSSL 19.0.0 (OpenSSL 1.1.0j 20 Nov 2018), cryptography 2.4.2,
Platform Darwin-17.7.0-x86_64-i386-64bit
# 爬虫信息
2019-03-28 02:51:54 [scrapy.crawler] INFO:
Overridden settings: {'NEWSPIDER_MODULE': 'ex1.spiders', '
SPIDER_MODULES': ['ex1.spiders'], 'ROBOTSTXT_OBEY': True, 'BOT_NAME':
'ex1'}
# 扩展信息
2019-03-28 02:51:54 [scrapy.middleware] INFO: Enabled extensions:
['scrapy.extensions.memusage.MemoryUsage',
… # 省略扩展信息
# 爬虫爬取内容的信息
2019-03-28 02:51:56 [scrapy.downloadermiddlewares.retry]
DEBUG: Retrying <GET http://domain2.com/>
… # 省略爬取过程
# 统计信息
2019-03-28 02:51:56 [scrapy.statscollectors] INFO: Dumping Scrapy
stats:
… # 省略统计数据
# 关闭爬虫
2019-03-28 02:51:56 [scrapy.core.engine] INFO: Spider closed (finished)
Scrapy 提供了一个简单的性能测试工具,其创建了一个本地 HTTP 服务器,并以最大可能的速度进行爬取。该性能测试工具的目的是测试 Scrapy 在本地硬件上的效率,来获得一个基本的参考用于对比。其使用了一个简单的 spider,仅跟进链接,不做任何处理。
该命令格式如下:
scrapy bench
下面的例子演示了该命令的使用情况:
# 启动标定程序
$ scrapy bench
… # 一些系统信息
2019-03-21 08:11:16 [scrapy.statscollectors] INFO: Dumping Scrapy
stats:
{'downloader/request_bytes': 266851,
'downloader/request_count': 860,
'downloader/request_method_count/GET': 860,
'downloader/response_bytes': 1275062,
'downloader/response_count': 860,
'downloader/response_status_count/200': 860,
… # 其他统计信息
'start_time': datetime.datetime(2019, 3, 21, 0, 11, 6, 90223)}
2019-03-21 08:11:16 [scrapy.core.engine] INFO: Spider closed
(closespider_timeout)
在上面的例子中可以看到其性能大致是 860 个页面/分钟。
也可以用命令来查看 Scrapy 的配置信息,命令格式如下:
scrapy settings [参数]
下面的例子获得了某个配置的值。
# 在项目外面,获得爬虫的名称
$ scrapy settings –get=BOT_NAME
scrapybot # 这个是系统的默认信息
# 进入到某个项目的目录下
$ cd ex1
$ scrapy settings –get=BOT_NAME
ex1 # 这个就是从项目得到的配置信息
如果对当前使用的 Scrapy 版本不确定,也可以通过命令来获得相关的信息。其有两种用法,一种是仅获得 Scrapy 的版本信息,命令格式如下:
scrapy version
另外一种可以获得除了 Scrapy 版本信息之外的其他一些信息,如 Python 的版本信息、其使用的 lxml 库的版本信息等,该命令格式如下:
scrapy version -v
下面的例子演示了上面两种用法。
$ scrapy version # 仅显示Scrapy的版本信息
Scrapy 1.6.0
$ scrapy version -v # 显示更多的信息,如Python、lxml等的版本信息
Scrapy : 1.6.0
lxml : 4.3.2.0
libxml2 : 2.9.9
cssselect : 1.0.3
parsel : 1.5.1
w3lib : 1.20.0
Twisted : 18.9.0
Python : 2.7.15 (default, Oct 2 2018, 11:47:18) –
[GCC 4.2.1 Compatible Apple LLVM 10.0.0 (clang-1000.11.45.2)]
pyOpenSSL : 19.0.0 (OpenSSL 1.1.0j 20 Nov 2018)
cryptography : 2.4.2
Platform : Darwin-17.7.0-x86_64-i386-64bit
本文链接:http://so.lmcjl.com/news/786/