Python Scrapy-有时从子网站提取数据
我正在解析一个网站,我想提取一些关于作者的数据。因为一些作者写了很多文章,所以我将作者信息保存到数据库中。只有当我没有关于新作者的信息时,我才想抓取一个子站点来提取数据,然后将它们保存到数据库中。我已经阅读了很多关于如何从另一个网站提取数据的文档,但我无法让它工作。我对Python还相当陌生,不了解收益率和收益率之间的所有差异 以下是我的部分代码:Python Scrapy-有时从子网站提取数据,python,scrapy,Python,Scrapy,我正在解析一个网站,我想提取一些关于作者的数据。因为一些作者写了很多文章,所以我将作者信息保存到数据库中。只有当我没有关于新作者的信息时,我才想抓取一个子站点来提取数据,然后将它们保存到数据库中。我已经阅读了很多关于如何从另一个网站提取数据的文档,但我无法让它工作。我对Python还相当陌生,不了解收益率和收益率之间的所有差异 以下是我的部分代码: def start_requests(self): for url in self.getUrlsToCrawl(): yi
def start_requests(self):
for url in self.getUrlsToCrawl():
yield self.buildRequest(url[1], url[0])
def buildRequest(self, url, dbid):
return SplashRequest(url, self.parse,
endpoint='execute',
cache_args=['lua_source'],
args={'lua_source':script, 'image':0},
meta={'dbId': dbid, 'originalUrl': url},
errback=self.errback_httpbin, dont_filter=True)
def parse(self, response):
[...]
articleLoader.add_value('authors', self.getAuthors(response))
[...]
return articleLoader.load_item()
def getAuthors(self, response):
authorsArray = []
authorName = remove_tags(response.xpath(myxpath).extract_first())
authorUrl = response.xpath(myxpath).extract_first()
authorInfos = self.executeSQL('SELECT name, twitter, email FROM author WHERE LOWER(name) = LOWER(%s) and domain = %s', (authorName, self.domain, ))
authorItem = AuthorItem()
if len(authorInfos) != 0:
authorItem['name'] = authorInfos[0][0]
authorItem['twitter'] = authorInfos[0][1]
authorItem['email'] = authorInfos[0][2]
elif authorUrl:
self.fetchAuthorInfos(authorUrl, authorItem)
else:
authorItem['name'] = authorName
authorsArray.append(dict(authorItem))
return authorsArray
def fetchAuthorInfos(self, url, authorItem):
return SplashRequest(url, callback = self.parseAuthorInfos, meta={'item':authorItem})
def parseAuthorInfos(self, response):
authorItem = response.meta['item']
authorItem['name'] = 'toto'
authorItem['twitter'] = 'titi'
authorItem['email'] = 'maimai'
return authorItem
我(随机)尝试了收益率和收益率之间的不同组合。有时我会访问fetchAuthorInfos
,有时不会,但我从未访问过parseAuthorInfos
。如果作者的信息在我的数据库中,或者如果我没有个人作者url来获取所有信息,那么一切都可以正常工作
谢谢你的帮助
编辑多亏了Granitosaurus,我找到了一条出路,但我仍然不是100%满意,因为有时我可以为一篇文章找到几个作者,我希望能够为每个人提取信息
def parse(self, response):
[...]
return self.get_authors(response, articleLoader)
def get_authors(self, response, articleLoader):
[...]
elif authorUrl:
return Request(authorUrl, callback = self.parse_author_infos, meta={'item':articleLoader})
else:
authorLoader.add_value('name', authorName)
authorsArray.append(dict(authorLoader.load_item()))
articleLoader.add_value('authors', authorsArray)
return articleLoader.load_item()
def parse_author_infos(self, response):
[...]
return articleLoader.load_item()
这一行几乎没有任何作用:
self.fetchAuthorInfos(author_url, author_item)
函数返回SplashRequest,但未以任何方式分配、返回或使用它
你错过了这里的连锁逻辑。您要做的是将请求链继续到作者的页面,如:
def parse(self, response):
"""This parses article's page"""
article_loader = ArticleLoader(response)
# add some stuff to article loader
<...>
author_url = 'some_url'
if author_url:
# if there's url to author page scrape that url for authors info
return SplashRequest(url, callback=self.parse_author,
meta={'item': article_loader.load_item()})
# otherwise just scrape presented author info
author_item = dict()
author_item['name'] = 'foobar'
article_loader.add_value('author', author_item)
return article_loader.load_item()
def parse_author(self, response):
"""This parses author's page"""
article_loader = response.meta['item']
author_item['name'] = 'toto'
author_item['twitter'] = 'titi'
author_item['email'] = 'maimai'
aritcle_loader.add_value('author', author_item)
return article_loader
def解析(self,response):
“”“此解析文章的页面”“”
article\u loader=article loader(响应)
#添加一些东西到文章加载器
author\u url='some\u url'
如果作者地址:
#如果有指向作者页面的url,请从该url获取作者信息
返回SplashRequest(url,callback=self.parse_author,
meta={'item':项目\u加载程序。加载\u item()})
#否则,只需抓取提交的作者信息
作者\u项=dict()
作者项目['name']='foobar'
文章加载器。添加值(“作者”,作者项)
返回物品装载器。装载物品()
def parse_作者(自我,回复):
“”“这将分析作者的页面”“”
article\u loader=response.meta['item']
作者项目['name']='toto'
作者项目['twitter']='titi'
作者项目['email']='maimai'
算术加载器。添加值('author',author\u项)
退货物品加载器
您应该非常熟悉,例如使用snake_case而不是pascalCase。我一定会看一看,我更习惯Java谢谢您的回答。我改为elif authorUrl:return请求(authorUrl,callback=self.parseauthorInfo,meta={'item':authorItem})
但现在我的主项类似于{'authors':[]
其中URL是authorUrl中的URL。此外,我仍然看不到我在parseauthorInfo
@RogerFromSpace中打印的内容。您可以尝试将dont\u filter=True
参数添加到此请求中吗?即请求(dont\u filter=True)
。可能是您的请求被过滤掉了,因为您在爬网会话期间已经访问了该url。@RogerFromSpace您可以发布爬网日志吗?您可以通过键入以下内容生成一个:scrapy crawl myspider&>output.log
恐怕帮不了什么忙。我更改了所有的日志data@RogerFromSpace好吧,我想我得到了一份工作这里的逻辑要点。你应该做的是合并parse
和getAuthors
方法。你所需要的只是一个解析文章页面的方法,该方法要么返回一个项目(如果没有作者url),要么向作者页面返回另一个请求。请参阅我对代码的编辑:)