Mam problem tak:Korzystanie middleware, aby zapobiec scrapy z podwójnymi odwiedzenie stron internetowych
how to filter duplicate requests based on url in scrapy
Więc nie ma na stronie internetowej mają być przeszukiwane więcej niż jeden raz. Zaadaptowałem oprogramowanie pośrednie i napisałem polecenie drukowania, aby sprawdzić, czy poprawnie klasyfikuje on już widziane strony internetowe. To robi.
Mimo to parsowanie wydaje się być wykonywane wiele razy, ponieważ plik json, który otrzymuję, zawiera podwójne wpisy.
from scrapy.contrib.spiders import CrawlSpider, Rule
from scrapy.contrib.linkextractors.sgml import SgmlLinkExtractor
from scrapy.selector import HtmlXPathSelector
from scrapy.item import Item
from crawlspider.items import KickstarterItem
from HTMLParser import HTMLParser
### code for stripping off HTML tags:
class MLStripper(HTMLParser):
def __init__(self):
self.reset()
self.fed = []
def handle_data(self, d):
self.fed.append(d)
def get_data(self):
return str(''.join(self.fed))
def strip_tags(html):
s = MLStripper()
s.feed(html)
return s.get_data()
###
items = []
class MySpider(CrawlSpider):
name = 'kickstarter'
allowed_domains = ['kickstarter.com']
start_urls = ['http://www.kickstarter.com']
rules = (
# Extract links matching 'category.php' (but not matching 'subsection.php')
# and follow links from them (since no callback means follow=True by default).
Rule(SgmlLinkExtractor(allow=('discover/categories/comics',))),
# Extract links matching 'item.php' and parse them with the spider's method parse_item
Rule(SgmlLinkExtractor(allow=('projects/',)), callback='parse_item'),
)
def parse_item(self, response):
self.log('Hi, this is an item page! %s' % response.url)
hxs = HtmlXPathSelector(response)
item = KickstarterItem()
item['date'] = hxs.select('//*[@id="about"]/div[2]/ul/li[1]/text()').extract()
item['projname'] = hxs.select('//*[@id="title"]/a').extract()
item['projname'] = strip_tags(str(item['projname']))
item['projauthor'] = hxs.select('//*[@id="name"]')
item['projauthor'] = item['projauthor'].select('string()').extract()[0]
item['backers'] = hxs.select('//*[@id="backers_count"]/data').extract()
item['backers'] = strip_tags(str(item['backers']))
item['collmoney'] = hxs.select('//*[@id="pledged"]/data').extract()
item['collmoney'] = strip_tags(str(item['collmoney']))
item['goalmoney'] = hxs.select('//*[@id="stats"]/h5[2]/text()').extract()
items.append(item)
return items
My items.py wygląda tak:
# Define here the models for your scraped items
#
# See documentation in:
# http://doc.scrapy.org/topics/items.html
from scrapy.item import Item, Field
class KickstarterItem(Item):
# define the fields for your item here like:
date = Field()
projname = Field()
projauthor = Field()
backers = Field()
collmoney = Field()
goalmoney = Field()
pass
Moja middleware wygląda następująco:
import os
from scrapy.dupefilter import RFPDupeFilter
from scrapy.utils.request import request_fingerprint
class CustomFilter(RFPDupeFilter):
def __getid(self, url):
mm = url.split("/")[4] #extracts project-id (is a number) from project-URL
print "_____________", mm
return mm
def request_seen(self, request):
fp = self.__getid(request.url)
self.fingerprints.add(fp)
if fp in self.fingerprints and fp.isdigit(): # .isdigit() checks wether fp comes from a project ID
print "______fp is a number (therefore a project-id) and has been encountered before______"
return True
if self.file:
self.file.write(fp + os.linesep)
Dodałem tę linię do settings.py:
DUPEFILTER_CLASS = 'crawlspider.duplicate_filter.CustomFilter'
Wywołuję skrypt za pomocą "scrapy crawl kic kstarter -o items.json -t json ". Następnie widzę poprawne instrukcje drukowania z kodu oprogramowania pośredniego. Wszelkie uwagi na temat tego, dlaczego json zawiera wiele wpisów zawierających te same dane?
Czy mógłbyś opublikować swój kod pająka, proszę? Ułatwi to śledzenie duplikatów. :) – Talvalin
@Talvalin Dodałem kod do mojego pierwotnego wpisu. Dzięki za pomoc. – Damian
Każdy konkretny powód, dla którego nie używasz domyślnej metody scrapy, ponieważ istnieje już [dupefiltr] (https://scrapy.readthedocs.org/en/latest/topics/settings.html?highlight=settings#dupefilter- klasa) zaimplementowana i aktywna AFAIK. – DrColossos