Nutch的Hadoop方式爬取效率優化

下面這些是潛在的影響爬取效率的內容(官方資料翻譯):
html

1)DNS設置
2)你的爬蟲數量,太多或太少
3)帶寬限制
4)每一主機的線程數
5)要抓取的urls的分配不均勻
6) robots.txt中的高爬取延時(一般和urls的分配不均勻同時出現)
7)有不少比較慢的網頁(一般和分配不均勻同時出現)
8)要下載太多的內容(PDF,大的html頁面,一般和分配不均勻同時出現)
9)其它java

那如今怎樣改善它們?
node

1)在每個本地的爬蟲機器上設置DNS,若是是多個爬取機器和一個單獨的DNS中心這種狀況,那麼它就會像有DOS攻擊在DNS服務器上那樣,使整個系統變慢。咱們常常設置兩層,首先命中本地DNS緩存,而後就是大的DNS緩存,就像OpenDNS或Verizon。
2)這將是map任務數乘以fetcher.threads.fetch屬性值的數量。因此10個map任務*20個線程=一次200個爬取列表。太多的話會超過你係統的負擔,太少的話就會使一些機器閒置。你須要認真考慮在你的環境下如何設置這些屬性。
3)帶寬限制,用ntop,ganglia和其它監控軟件來測定你使用了多少的帶寬。計算輸入和輸出的帶寬。能夠作一個簡單的測試,用抓取網絡中一臺不用做爬蟲的服務器中,若是它與其中一臺爬蟲機器鏈接時或當那臺機器抓取時從中下載信息時很是慢,這時你就能夠加大帶寬。若是你像我後來講的那樣設置http的超時時間而且增長了你的帶寬,你會開始看到不少http超時的錯誤。
4)urls分配的不均勻頗有多是限制性能的一個最大的因素。若是一個線程正在處理一個網站而且那個網站還有不少url等待抓取,那麼其它線程就會閒置直到那個線程完成抓取。一些解決方法是,使用fetcher.server.delay來縮短網頁抓取之間的時間間隔,和使用fetcher.threads.per.host來增長同一網站抓取的線程數(這仍然在同一個map任務中,所以也是在同一個JVM中的子任務中處理)。若是把這些屬性都設置爲大於0,你也能夠設置fetcher.server.min.delay屬性大於0來設置處理的最小和最大的界限。
5)在一個網站上抓取大量的網頁或在少許網站上抓取大量的網頁將顯著地下降抓取的速度。對於全網爬取,你但願用分佈式環境來使全部抓取線程活動。設置generate.max.per.host大於0將限制在同一網站/域名抓取網頁的數量
6)爬取延遲。大多數網站不使用這些設置只有少數使用(一些惡意的網站)。我見過爬取延遲每秒最長延遲2天的.fetcher.max.crawl.delay屬性將忽略爬取延遲大於x的頁面。我常常把它設置成10秒,默認是30秒。儘管設置爲10秒,若是你在某個網站上有大量的頁面要爬取,但你只能每10秒爬取一個頁面,這樣也是很慢的。另外一方面,把它的值設置太小將忽略該頁面而且不抓取這些網頁。
7)有時,網頁恰好很慢。設置http.timeout一個低點的值就有助於這種狀況。它的默認值爲10秒。若是你不在乎並想全部網頁都儘量的快,設置得小點。一些網站。例如digg,會在網站中限制你的帶寬而且只容許在某個時間段內存在x個到你機器的鏈接。因此即便你只在一個網站中爬取50個網頁(我仍然認爲太多了)。這樣將在每一頁面中等待10秒。ftp.timeout也能夠用來設置抓取ftp的內容時的時間間隔。
8)大量的內容意味着要下降抓取的速度。特別是下載PDF或其它非html的文件時。爲了不下載非html的內容,你可使用url過濾器。我更喜歡prefix和suffix過濾器。http.content.limit和ftp.content.limit屬性能夠限制一個文檔中下載數據的多少。
9)其它可能致使抓取變慢的因素:
一臺機器最大可打開的socket或文件的多少。你可能會開始看到IO錯誤或不能打開socket的錯誤。低效的路由。壞的或家裏的路由不能控制同一時間大量鏈接的創建。一個錯誤的路由設置也可能致使問題但這些問題一般很難發現。若是你認爲是這個問題,能夠用網絡跟蹤和映射工具來查找。反向的路由則多是你網絡供應商的問題。壞的網卡。我曾經見過一些網卡忽然達到了某個帶寬值。這個問題在使用新的網卡時更加廣泛。這一般不是我首先想到的可是一般是可能會出現的。可使用tcpdump和網絡監控apache

本次優化方向:緩存

A,1)3)爲硬件,設置好了之後改變不大。暫不考慮。
B,5)generate.max.per.host暫設置爲0。暫不考慮。
C,8)本次爬蟲設置只爬取網頁內容,不爬媒體文件。
D,2)4)6)7)9)爲優化目標服務器


Hadoop配置:網絡

三臺:主機內存8G,2臺slave內存20G,主從內存配置不合理有必定緣由,這裏就再也不贅述。之後也是一個優化方向socket

網絡帶寬:100M
tcp

優化前的準備工做:分佈式

沒有優化以前,種子數量在10條左右的時候,單機版和Hadoop版的爬取效率大約都在2條/秒(包括創建索引)。
優化了Nutch索引,stored和indexed,索引不須要存儲的儘可能不存儲,不須要索引的儘可能不索引。而且去掉沒必要要的索引項目。當種子數增長到40條左右的時候,Hadoop版的爬取效率大約在3.5條/秒。由此肯定了種子數量對爬取有影響的優化方向。

參照hadoop的優化方針,作了以下優化:

1,優化系統參數 readahead buffer
blockdev --report
blockdev --setra 1024 /dev/sda
2,優化hadoop參數
hdfs-default
 dfs.namenode.handler.count:20
 dfs.datanode.handler.count:5
 dfs.replication:3
mapred-default.xml
 mapreduce.tasktracker.http.threads:50
 io.sort.factor:20
 mapred.child.java.opts:-Xmx400m
 mapreduce.task.io.sort.mb:200
 mapreduce.map.sort.spill.percent:0.8
 mapreduce.map.output.compress:true
mapreduce.map.output.compress.codec:org.apache.hadoop.io.compress.DefaultCodec     com.hadoop.compression.lzo.LzoCodec爲最優
mapreduce.reduce.shuffle.parallelcopies:10

優化開始:

2014/7/9 上午

優化內容

增大種子數:選取的3000左右的有效的國外網站。

yarn-site
<property>
<name>yarn.scheduler.minimum-allocation-mb</name>
<value>2048</value>
</property>
<property>
<name>yarn.scheduler.maximum-allocation-mb</name>
<value>3072</value>
</property>
mapred-site
<property>
<name>mapreduce.map.memory.mb</name>
<value>1536</value>
</property>
<property>
<name>mapreduce.reduce.memory.mb</name>
<value>2560</value>
</property>
<property>
<name>mapreduce.map.java.opts</name>
<value>-Xms512m -Xmx1024m</value>
</property>
<property>
<name>mapreduce.reduce.java.opts</name>
<value>-Xms1024m -Xmx2048m</value>
</property>
slave
yarn-site
<property>
<name>yarn.scheduler.minimum-allocation-mb</name>
<value>3072</value>
</property>
<property>
<name>yarn.scheduler.maximum-allocation-mb</name>
<value>6144</value>
</property>
mapred-site
<property>
<name>mapreduce.map.memory.mb</name>
<value>4096</value>
</property>
<property>
<name>mapreduce.reduce.memory.mb</name>
<value>8192</value>
</property>
<property>
<name>mapreduce.map.java.opts</name>
<value>-Xms2048m -Xmx3072m</value>
</property>
<property>
<name>mapreduce.reduce.java.opts</name>
<value>-Xms5120m -Xmx6144m</value>
</property>

結果:

共爬取並創建了91986條solr索引,共耗時22235秒。最終效率:4.14條/秒。

4.136991



2923 2923 11:06:05 11:20:51 0:14
36538 33615 11:20:51 13:13:38 1:52
68255 31717 13:13:38 15:16:42 2:03
91986 23731 15:16:42 17:16:40 1:59

2014/7/9 下午

優化內容:

nutch-site

<name>fetcher.threads.per.host</name> 5
<name>fetcher.threads.fetch</name>20

結果:


    數
效率 5.38條/秒 全體 Nutch Index








總條數 每回條數 開始 終了 耗時 速度 開始 終了 耗時 速度 開始 終了 耗時 速度
1 2923 2923 18:22:04 18:48:55 1611 1.81 18:22:04 18:35:13 789 3.70 18:37:05 18:48:55 710 4.12
2 36538 33615 18:49:41 20:59:04 7763 4.33 18:49:41 20:20:31 5450 6.17 20:22:18 20:59:04 2206 15.24
3 68255 31717 21:00:11 22:57:35 7044 4.50 21:00:11 22:26:21 5170 6.13 22:28:08 22:57:35 1767 17.95
4 91986 23731 22:59:19 0:58:52 7173 3.31 22:59:19 0:28:49 5370 4.42 0:31:03 0:58:52 1669 14.22
5 115646 23660 1:00:49 2:49:14 6505 3.64 1:00:49 2:19:21 4712 5.02 2:21:19 2:49:14 1675 14.13

結論:

速度從4.14-〉5.38,提高了29.95%。從這一點來看Nutch的fetch線程數目對爬取效率有必定影響。


2014/7/10

優化內容:

根據7/9日的方向,增長fetch線程數。

nutch-site
<property>
  <name>fetcher.threads.fetch</name>
  <value>100</value>
</property>
<property>
 <name>plugin.includes</name>
    <value>protocol-http|urlfilter-regex|parse-html|index-(basic|customized)|indexer-solr|scoring-opic|urlnormalizer-(pass|regex|basic)</value>
</property>
<property>
  <name>indexer.skip.notmodified</name>
  <value>true</value>
  <description>Whether the indexer will skip records with a db_notmodified status.
  </description>
</property>

結果:


    數
效率 6.22條/秒 全體 Nutch Index








總條數 每回條數 開始 終了 耗時 速度 開始 終了 耗時 速度 開始 終了 耗時 速度
1 3014 3014 15:01:01 15:26:07 1506 2.00 15:01:01 15:13:30 749 4.02 15:15:13 15:26:07 654 4.61
2 39069 36055 15:26:54 17:34:55 7681 4.69 15:26:54 17:01:35 5681 6.35 17:03:25 17:34:55 1890 19.08
3 73156 34087 17:35:57 19:33:36 7059 4.83 17:35:57 18:59:06 4989 6.83 19:01:08 19:33:36 1948 17.50
4 103994 30838 19:34:55 21:46:40 7905 3.90 19:34:55 21:03:07 5292 5.83 21:05:31 21:46:40 2469 12.49

結論:

速度從5.38-〉6.22,提高了15.61%。fetch線程數目增長,優化效果在減少。


2014/7/11上午

改變優化方向:

考慮到網速的問題,放棄了用以前有3000左右的有效網站地址的國外新聞網站。改用下列網址http://bj.elanw.com/,因爲初始只有一個地址。防止爬取深度過深,先爬去兩層而後做爲基礎,再做爬取。再次爬取的層數爲3層。

結果:


    數
效率 11.61條/秒 全體 Nutch Index








總條數 每回條數 開始 終了 耗時 速度 開始 終了 耗時 速度 開始 終了 耗時 速度
1 2830 2830 11:13:05 11:35:52 1367 2.07 11:13:05 11:26:40 815 3.47 11:28:20 11:35:52 452 6.26
2 43885 41055 11:36:51 13:07:01 5410 7.59 11:36:51 12:29:47 3176 12.93 12:31:55 13:07:01 2106 19.49
3 83074 39189 13:08:11 14:27:47 4776 8.21 13:08:11 14:00:53 3162 12.39 14:02:53 14:27:47 1494 26.23

結論:

速度從6.22-〉11.61,提高了86.66%。可見訪問網站的速度對爬蟲有很大影響。


2014/7/11下午

優化方向:

統計了一下上午爬蟲每一個階段的詳細數據,結果以下:

Inject Generate Fetch Parse CrawlDB Link inversion Dedup Index Cleanup index
11:13:05 11:14:54 11:16:22 11:21:51 11:23:25 11:24:34 11:26:40 11:28:20 11:35:52
0:01:49 0:01:28 0:05:29 0:01:34 0:01:09 0:02:06 0:01:40 0:07:32 0:00:59
11:36:51 11:36:51 11:38:38 12:11:34 12:21:58 12:23:39 12:29:47 12:31:55 13:07:01

0:01:47 0:32:56 0:10:24 0:01:41 0:06:08 0:02:08 0:35:06 0:01:10
13:08:11 13:08:11 13:09:56 13:41:31 13:50:56 13:52:27 14:00:53 14:02:53 14:27:47

0:01:45 0:31:35 0:09:25 0:01:31 0:08:26 0:02:00 0:24:54

從結果上看:fetch和index所耗時間佔每次爬取時間的80%左右,因此重點考慮fetch的參數優化。

另外,察看資料發現以前Nutch的配置有個優化項目設置不對,Nutch1.8中不是fetcher.threads.per.host而是fetcher.threads.per.queue。

優化內容:

<property>
  <name>fetcher.threads.per.queue</name>
  <value>5</value>
</property>
<property>
  <name>fetcher.queue.depth.multiplier</name>
  <value>100</value>
</property>
<property>
  <name>fetcher.server.delay</name>
  <value>2.0</value>
</property>
<property>
  <name>fetcher.server.min.delay</name>
  <value>1.0</value>
</property>

結果:


    數
效率 13.87條/秒 全體 Nutch Index








總條數 每回條數 開始 終了 耗時 速度 開始 終了 耗時 速度 開始 終了 耗時 速度
1 2238 2238 14:38:05 14:56:37 1112 2.01 14:38:05 14:48:07 602 3.72 14:49:43 14:56:37 414 5.41
2 43704 41466 14:57:25 16:21:00 5015 8.27 14:57:25 15:43:12 2747 15.10 15:44:52 16:21:00 2168 19.13
3 82269 38565 16:21:25 17:34:21 4376 8.81 16:21:25 17:04:29 2584 14.92 17:06:24 17:34:21 1677 23.00

結論:

速度從11.61-〉13.87,提高了19.47%。可見fetch的參數優化對總體爬蟲效率有不小的影響。


2014/7/11晚上

優化內容:fetch參數

<property>
  <name>fetcher.threads.per.queue</name>
  <value>10</value>
</property>
<property>
  <name>fetcher.queue.depth.multiplier</name>
  <value>200</value>
</property>
<property>
  <name>fetcher.threads.fetch</name>
  <value>200</value>
</property>

結果:


    數
效率 14.52條/秒 全體 Nutch Index








總條數 每回條數 開始 終了 耗時 速度 開始 終了 耗時 速度 開始 終了 耗時 速度
1 2224 2224 18:07:04 18:23:59 1015 2.19 18:07:04 18:16:33 569 3.91 18:18:07 18:23:59 352 6.32
2 42079 39855 18:24:46 19:35:45 4259 9.36 18:24:46 19:07:15 2549 15.64 19:09:02 19:35:45 1603 24.86
3 83466 41387 19:36:47 20:46:35 4188 9.88 19:36:47 20:20:37 2630 15.74 20:22:24 20:46:35 1451 28.52

結論:

速度從13.87-〉14.52,提高了4.69%。可見fetch的參數優化對總體爬蟲效率有影響,但效果已經減少


總結:

經過這幾天的優化,使得爬蟲效率從4.14條/秒提高到了14.52條/秒,速度提高250.72%

1,Nutch爬蟲總體過程當中,fetch和index建立佔據着總體爬取時間的80%左右,fetch:55%,index:35%

   fetch方面主要考慮參數優化,nutch1.8種有10多個參數,上述已經作了部分優化。
    index建立的優化主要考慮作solr集羣,如今仍是單機版。是從此的優化方向

2,Hadoop的相關優化,要事先作完,特別是虛擬內存和物理內存的優化,不然在優化1時會出現內存溢出,IO異常等錯誤

3,爬取網站的訪問速度對爬蟲效率有很大影響,這個很容易理解

4,從每次爬蟲的速度來看,種子數量對爬蟲速度有很大的影響爬蟲官方目標是每月幾十億,暫算30億的話,天天1億網頁爬取量來算,每秒要爬取1100多網頁。若是其餘因素都很理想得狀態下,種子數量的多少對爬蟲速度有很是大的影響實際實踐效率數據:天天200萬網頁,每秒20多條網頁。

相關文章
相關標籤/搜索