蜘蛛larbin

来源:互联网 发布:python 单例模式 编辑:程序博客网 时间:2024/04/28 23:13

                                                                             larbin

    

互联网是一个庞大的非结构化的数据库,将数据有效的检索并组织呈现出来有着巨大的应用前景,尤其是类似RSS的以XML为基础的结构化的数据越来越多,内容的组织方式越来越灵活,检索组织并呈现会有着越来越广泛的应用范围,同时在时效性和可读性上也会有越来越高的要求。这一切的基础是爬虫,信息的来源入口。一个高效,灵活可扩展的爬虫对以上应用都有着无可替代的重要意义。

要设计一个爬虫,首先需要考虑的效率。对于网络而言,基于TCP/IP的通信编程有几种方法。

第一种是单线程阻塞,这是最简单也最容易实现的一种,一个例子:在Shell中通过curl,pcregrep等一系统命令可以直接实现一个简单的爬虫,但同时它的效率问题也显而易见:由于是阻塞方式读取,dns解析,建立连接,写入请求,读取结果这些步骤上都会产生时间的延迟,从而无法有效的利用服务器的全部资源。

第二种是多线程阻塞。建立多个阻塞的线程,分别请求不同的url。相对于第一种方法,它可以更有效的利用机器的资源,特别是网络资源,因为无数线程在同时工作,所以网络会比较充分的利用,但同时对机器CPU资源的消耗也是比较大,在用户级多线程间的频繁切换对于性能的影响已经值得我们考虑。

第三种是单线程非阻塞。这是目前使用的比较多的一种做法,无论在client还是server都有着广泛的应用。在一个线程内打开多个非阻塞的连接,通过poll/epoll/select对连接状态进行判断,在第一时间响应请求,不但充分利用了网络资源,同时也将本机CPU资源的消耗降至最低。这种方法需要对dns请求,连接,读写操作都采用异步非阻塞操作,其中第一种比较复杂,可以采用adns作为解决方案,后面三个操作相对简单可以直接在程序内实现。

效率问题解决后就需要考虑具体的设计问题了。

url肯定需要一个单独的类进行处理,包括显示,分析url,得到主机,端口,文件数据。

然后需要对url进行排重,需要一个比较大的url Hash表。

如果还要对网页内容进行排重,则还需要一个Document Hash表。

爬过的url需要记录下来,由于量比较大,我们将它写到磁盘上,所以还需要一个FIFO的类(记作urlsDisk)。

现在需要爬的url同样需要一个FIFO类来处理,重新开始时,url会从定时从爬过的urlFIFO里取出来,写到这个FIFO里。正在运行的爬虫需要从这个FIFO里读数据出来,加入到主机类的url列表里。当然,也会从前一个FIFO里直接读url出来,不过优先级应该比这个里面出来的url低,毕竟是已经爬过的。

爬虫一般是对多个网站进行爬取,但在同时站点内dns的请求可以只做一次,这就需要将主机名独立于url,单独有一个类进行处理。

主机名解析完成后需要有一个解析完成的IP类与之应用,用于connect的时候使用。

HTML文档的解析类也要有一个,用来分析网页,取出里面的url,加入到urlsDisk。

再加上一些字符串,调度类,一个简单的爬虫基本上就完成了。

以上基本上是Larbin的设计思路,Larbin在具体实现上还有一些特殊的处理,例如带了一个webserver,以及对特殊文件的处理。Larbin有一点设计不不太好,就是慢的访问会越来越多,占用大量的连接,需要改进,另外如果对于大规模的爬虫,这仅仅实现了抓取的部分,要分布式的扩展还需要增加url的集中管理与调度以及前台spider的分布式算法。



Larbin网站爬虫简明使用说明




larbin是一种爬虫工具,我也是前段时间网上看到 Larbin 一种高效的搜索引擎爬虫工具 一文时才知道有这么个东西,初步认定,我比较喜欢这个工具(比起nutch的crawl来说),因为它是C++写的,类似C嘛,我熟,可以自己改改,顺便学习一下C++(几年来的经验告诉我说:改别人的东西来学一种技术比从头写helloworld快很多)。于是开始了我艰辛的larbin试用之旅。 

  回头看看自己遇到的问题都是由于没认真看文档引起的,唉,老毛病了。下次即使是E文的也得好好看,不能盲目的试,浪费时间。 

  larbin官方地址:http://larbin.sourceforge.net/index-eng.html


  一,编译 

  这也好说,whahahaha,那是!因为从官方网站下下来的代码不能编译通过(linux gcc下)


  ./configure 

  make


  gcc -O3 -Wall -D_REENTRANT -c -o parse.o parse.c 

  parse.c:115: error: conflicting types for ’adns__parse_domain’ 


  internal.h:571: error: previous declaration of ’adns__parse_domain’ was here


  parse.c:115: error: conflicting types for ’adns__parse_domain’

  internal.h:571: error: previous declaration of ’adns__parse_domain’ was here 


  gmake[1]: *** [parse.o] 错误 1 

  gmake[1]: Leaving directory `/home/leo/leo/larbin-2.6.3/adns’

  make: *** [all] 错误 2 

  函数原型和定义不一致这个好改:


  打开./adns/internal.h文件,把568-571行直接注释掉就行了。  

二,运行 

  运行后可以http://host:8081 看运行状态,不错的想法。 larbin.conf中有个:inputPort 1976配置,就是可以运行时增加要抓取的URL,直接telnet host 1976进行增加就可以

  三,结果

  文档 How to customize Larbin 说明: 

  The first thing you can define is the module you want to use forouput. This defines what you want to do with the pages larbin gets.Here are the different options :


  DEFAULT_OUTPUT : This module mainly does nothing, except statistics. 

  SIMPLE_SAVE : This module saves pages on disk. It stores 2000 files per directory (with an index).


  MIRROR_SAVE : This module saves pages on disk with the hierarchy of the site they come from. It uses one directory per site. 

  STATS_OUTPUT : This modules makes some stats on the pages. Inorder to see the results, see http://localhost:8081/output.html. 

  默认什么都没输出,修改了options.h再编译


  改:


  SIMPLE_SAVE 简单输出一个目录两千个文件,包含索引。 

  CGILEVEL=0 处理服务器端程序,也就是但url中包含? & = 之类的querString时也处理。 

  NO_DUP


  其余可根据各自需要修改,详见: How to customize Larbin 一文。


  四,问题


  在使用过程中发现,在抓网页的时候,如果URL中包含未编码(encodurl)中文时,无法抓取,简单的看了一下在:src/utils/url.cc中的fileNormalize 有涉及。于是写了个encodurl函数加在url类的构造函数里,问题就解决了。


  SimpleRobot



原创粉丝点击