如何使用Scrapy从数据库中删除过期的项目

时间:2010-01-12 19:44:48

标签: python screen-scraping scrapy

我正在使用视频网站来频繁访问内容。我正在考虑使用scrapy来执行我的蜘蛛侠,但我不确定如何删除过期的项目。

检测项目是否过期的策略是:

  1. 蜘蛛网站的“delete.rss”。
  2. 每隔几天,尝试重新加载内容页面并确保它仍然有效。
  3. 蜘蛛网站内容索引的每一页,如果找不到,则删除该视频。
  4. 请告诉我如何在scrapy中删除过期的物品。我将通过django将我的scrapy项目存储在mysql DB中。

    2010-01-18更新

    我找到了一个有效的解决方案,但仍然可能不是最佳解决方案。我在每个同步的视频上都保留了“found_in_last_scan”标志。当蜘蛛启动时,它将所有标志设置为False。完成后,它会删除仍将标志设置为False的视频。我通过附加到signals.spider_openedsignals.spider_closed来做到这一点。请确认这是一个有效的策略,并且没有任何问题。

2 个答案:

答案 0 :(得分:4)

我没有测试过这个!
我必须承认我没有尝试过在Scrapy中使用Django模型,但是这里有:

我想象的最简单的方法是通过扩展XMLFeedSpider(从scrapy文档复制,然后修改)为deleted.rss文件创建一个新的蜘蛛。我建议你创建一个新的蜘蛛,因为以下逻辑很少与用于抓取网站的逻辑有关:

from scrapy import log
from scrapy.contrib.spiders import XMLFeedSpider
from myproject.items import DeletedUrlItem

class MySpider(XMLFeedSpider):
    domain_name = 'example.com'
    start_urls = ['http://www.example.com/deleted.rss']
    iterator = 'iternodes' # This is actually unnecesary, since it's the default value
    itertag = 'item'

    def parse_node(self, response, url):
        url['url'] = node.select('#path/to/url').extract()

        return url # return an Item 

SPIDER = MySpider()

这是你正在使用的工作蜘蛛,但是IIRC的RSS文件是纯XML。我不确定deleted.rss是怎样的,但我相信你可以弄清楚如何从XML中提取URL。现在,这个示例导入myproject.items.DeletedUrlItem,这只是本例中的一个字符串,但您需要使用类似下面的代码创建DeletedUrlItem:

您需要创建DeletedUrlItem:

class DeletedUrlItem(Item):
    url = Field()

而不是保存delete the items using Django's Model API中的Scrapy's ItemPipeline - 我假设您使用的是DjangoItem

# we raise a DropItem exception so Scrapy
# doesn't try to process the item any further
from scrapy.core.exceptions import DropItem

# import your model
import django.Model.yourModel

class DeleteUrlPipeline(item):

    def process_item(self, spider, item):
        if item['url']:
            delete_item = yourModel.objects.get(url=item['url'])
            delete_item.delete() # actually delete the item!
            raise DropItem("Deleted: %s" % item)

注意delete_item.delete()


我知道这个答案可能包含错误,它是由内存写的:-)但是如果你有评论或者无法解决这个问题我肯定会更新。

答案 1 :(得分:0)

如果您有一个HTTP URL,您怀疑它可能根本不再有效(因为您在“已删除”的Feed中找到它,或者仅因为您暂时没有检查它),最简单,最快检查的方法是发送该URL的HTTP HEAD请求。在Python中,最好使用标准库的httplib模块:使用HTTPConnection向感兴趣的主机创建连接对象c(如果是HTTP 1.1,则可以重复使用它多个URL具有更好的性能和更低的systrem负载),然后执行一个(或更多,如果可行,即如果正在使用HTTP 1.1)调用c的{​​{3}}方法,第一个参数'HEAD' ,第二个参数是您正在检查的URL(当然没有主机部分; - )。

在每次request之后,您致电c.getresponse()以获取request对象,其status属性会告诉您该网址是否仍然有效。

是的,它有点低级别,但正是由于这个原因,它可以让你更好地优化你的任务,只需要一点点HTTP知识; - )。