Nutch 實戰

基本信息

Nutch是一個開放源代碼(open-source)的Java搜索引擎包,它提供了構建一個搜索引擎所需要的全部工具和功能。使用Nutch不 僅可以建立自己內部網的搜索引擎,同時也可以針對整個網絡建立搜索引擎。除了基本的功能之外,Nutch也還有不少自己的特色,如Map-Reduce、 Hadoop、Plugin等。

 




回頁首


Nutch的總體結構

Nutch從總體上看來,分爲三個主要的部分:爬行、索引和搜索,各部分之間的關係如圖1所示。Web db是Nutch初始運行的URL集合;Fetcher是用來抓取網頁的爬行器,也就是平時常說的Crawler;indexer是用來建立索引的部分, 它將會生成的索引文件並存放在系統之中;searcher是查詢器,用來完成對某一詞條的搜索並返回結果。


圖 1. Nutch 總體結構
Nutch 總體結構




回頁首


Nutch 的運行流程

在瞭解了 Nutch 的總體結構之後,再詳細的看看 Nutch 具體是如何運行的?Nutch 的運行流程如圖2所示。

1. 將起始 URL 集合注入到 Nutch 系統之中。

2. 生成片段文件,其中包含了將要抓取的 URL 地址。

3. 根據URL地址在互聯網上抓取相應的內容。

4. 解析所抓取到的網頁,並分析其中的文本和數據。

5. 根據新抓取的網頁中的URL集合來更新起始URL集合,並再次進行抓取。

6. 同時,對抓取到的網頁內容建立索引,生成索引文件存放在系統之中。


圖 2. Nutch 的運行流程
Nutch 的運行流程

從用戶端來看,Nutch 提供了一個基於 Tomcat 的應用程序,它允許用戶輸入詞條,然後 Nutch 會在已經建立好的索引文件中進行搜索,並將相應的結果返回給用戶。

 




回頁首


Nutch 的配置和運行

Nutch 既可以在 Linux 下運行,可以在 Windows 下運行,同時還可以在 Eclipse 環境中運行。在本部分中,主要介紹如何在 Eclipse 環境下運行 Nutch。

下載 Nuch 軟件包

首先,應該在 Nutch 的下載頁面 中下載相應的Nutch軟件包,現在最新的版本號是0.9, 通常使用的版本號是 0.8.1。

解壓縮

下載後得到的是一個名爲 nutch-0.9.tar.gz 的壓縮包,使用7-Zip可以將其解壓縮,解壓後得到的文件結構如圖3所示。


圖 3. Nutch 的目錄結構
Nutch 的目錄結構

在bin文件夾下存放的是用於命令行運行的文件;Nutch的配置文件都放在了conf下,lib是一些運行所需要的jar文件;plugins下 存放的相應的插件;在src文件夾中的是Nutch的所有源文件;webapps文件夾中存放的是web運行相關文件;nutch-0.9.war是 Nutch所提供的基於Tomcat的應用程序包。

導入源代碼

在獲得Nutch的源代碼之中,就可以將其導入到Eclipse環境中,並生成一個新的java工程。導入後的代碼結構如圖4所示。在導入過程中應該注意的是,需要把lib下的所有jar文件以及conf文件夾都添加到工程的build path之中。

另外,Nutch還需要另外兩個jar文件,jid3lib-0.5.1.jar和rtf-parser.jar,請分到到下面兩個鏈接下載。

http://nutch.cvs.sourceforge.net/nutch/nutch/src/plugin/parse-mp3/lib/

http://nutch.cvs.sourceforge.net/nutch/nutch/src/plugin/parse-rtf/lib/


圖 4. Nutch 的包結構
Nutch 的包結構

配置

在正式開始運行Nutch之前,還需要做一些必要的配置,不然在運行時會出錯,無法按照要求抓取到相應的頁面。

第一個需要修改的文件是 nutch-default.xml, 需要將 HTTP properties 部分的 http.agent.name 賦予一個有意思的字符串;還需要將 plugin properties 部分的 plugin.folders 按照具體的情況做必要修改。清單 1 和清單 2 分別是本文中的 Demo 運行時的具體配置情況,供大家參考。


清單1.

<!-- HTTP properties -->
<name>http.agent.name</name>
<value>testNutch</value>
<description>Just for Testing
</description>
</property>



清單2.

<!-- plugin properties -->
<property>
<name>plugin.folders</name>
<value>plugin</value>
<description>Directories where nutch plugins are located. Each
element may be a relative or absolute path. If absolute, it is used
as is. If relative, it is searched for on the classpath.</description>
</property>

 

其次,需要修改的文件是crawl-urlfilter.txt, 將其中的MY.DOMAIN.NAME部分按照實際的域名進行修改。清單3中的配置是對*.ibm.com/域進行抓取。


清單3.

# accept hosts in MY.DOMAIN.NAME
+^http://([a-z0-9]*/.)*ibm.com/

 

另外,還需要的一個操作是在conf文件夾下,建立一個名爲prefix-urlfilter.txt的文本文件,其中的內容很簡單,如清單4所示。


清單4.

# prefix-urlfilter.txt file starts here
http
# prefix-urlfilter.txt file ends here

 

抓取

在配置完成之後,就可以開始運行Nutch的Crawler了,不過,正如本文前面所述,開始運行前還需要設定初始URL集合。具體的方法是建立一 個文件夾(本文建立的文件夾名爲url),並在其中建立一個純文本文件(本文建立的文件名爲urls.txt),文件文件中存放了需要抓取的其實URL地 址,如“http://www.ibm.com/”。

然後在org.apache.nutch.crawl包下的Crawl.java文件上點擊右鍵,選擇“Run as”,再選擇“open run dialog”,在如圖5所示的對話框中輸入運行參數,然後點擊“Run”。這樣系統就可以運行了。


圖 5. 運行 Crawler
運行 Crawler

在運行過程中,會出現很多的log信息,圖6和圖7是系統運行過程中的一些截圖,從中可以看出正在抓取的網頁URL地址和抓取速度等一些信息。等抓取任務成後,系統會自動生成相應的索引文件,以後查詢器使用。在以後的文章中,會深入探討相應的話題。


圖 6. Nutch 運行信息 1
Nutch 運行信息 1

圖 7. Nutch 運行信息 2
Nutch 運行信息 2




回頁首


深入分析 Crawl 源代碼

在瞭解了 Nutch 的運行過程之後,再來分析 Nutch 內部的運行流程是什麼樣子的,以及各個類之間是如何協同配置的?

Crawl的入口

正如在前文中所提到的,在運行 Crawl 時需要輸入一些必要的參數,並且格式也是一定的。具體的用法是 Crawl <urlDir> [-dir d] [-threads n] [-depth i] [-topN N]。其中,<urlDir> 是必須有的參數;Crawl 是運行的主文件;-dir 表示存放的目標文件夾;-threads 表示抓取過程中其中的線程數;-depth 表示要抓取的深度層次。

如果在運行時不指定這些參數,那麼Nutch會默認設定這個參數值。詳見清單。


清單 5.

   Path dir = new Path("crawl-" + getDate());
int threads = job.getInt("fetcher.threads.fetch", 10);
int depth = 5;
int topN = Integer.MAX_VALUE;

 

如果指定了運行參數,Nutch會按照以下的方式來處理。


清單 6.

for (int i = 0; i < args.length; i++) {
if ("-dir".equals(args[i])) {
dir = new Path(args[i+1]);
i++;
} else if ("-threads".equals(args[i])) {
threads = Integer.parseInt(args[i+1]);
i++;
} else if ("-depth".equals(args[i])) {
depth = Integer.parseInt(args[i+1]);
i++;
} else if ("-topN".equals(args[i])) {
topN = Integer.parseInt(args[i+1]);
i++;
} else if (args[i] != null) {
rootUrlDir = new Path(args[i]);
}
}

 

生成目標文件夾

在設定運行參數後,經過一個必要的處理,Nutch會生成若干個目標文件夾用來存儲不同的文件內容,具體包括:crawlDb,linkDb,segments,indexes和index。


清單 7.

    Path crawlDb = new Path(dir + "/crawldb");
Path linkDb = new Path(dir + "/linkdb");
Path segments = new Path(dir + "/segments");
Path indexes = new Path(dir + "/indexes");
Path index = new Path(dir + "/index");

 

注入、抓取和更新

當生成了所需要的目標文件夾之後,Nutch就可以開始抓取工作了。當然,在抓取網頁過程中會使用功能類來完成相應的單元工作。具體來講,在注入、 抓取和更新過程中,會用來的功能類有Injector、Generator、Fetcher、ParseSegment和CrawlDb。

整個過程分爲以下幾個步驟:


注入

injector.inject(crawlDb, rootUrlDir);



抓取

Path segment = generator.generate(crawlDb, segments, -1, topN, System
.currentTimeMillis(), false, false);
if (segment == null) {
LOG.info("Stopping at depth=" + i + " - no more URLs to fetch.");
break;
}
fetcher.fetch(segment, threads);



更新

if (!Fetcher.isParsing(job)) {
parseSegment.parse(segment);
}
crawlDbTool.update(crawlDb, new Path[]{segment}, true, true);

 

4. 反轉、索引、去重及合併

最後的工作就是生成索引,去重併合並索引。不過,現在一般都是會生成倒排索引文件,所以在建立索引之前還會有一個反轉的操作,如清單所示。


清單 8.

linkDbTool.invert(linkDb, segments, true, true, false); // invert links

// 索引
indexer.index(indexes, crawlDb, linkDb, fs.listPaths(segments));
//去重
dedup.dedup(new Path[] { indexes });
//合併
merger.merge(fs.listPaths(indexes), index, tmpDir);





回頁首


總結

本文主要介紹了使用Nutch進行網頁抓取和建立索引方面的內容,首先分析了網頁抓取的過程,然後結合源代碼分析了整個抓取過程的組織和實現。當然了,Nutch是一款功能非常豐富的開源搜索引擎,關於其他方面的內容,將在後面的文章中一一介紹。


參考資料

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章