翁紹菲 廖翔宇 祝光儀 范雅靜 甘宇健

摘要:近年來(lái),隨著互聯(lián)網(wǎng)的迅速發(fā)展,人們對(duì)于數(shù)據(jù)的挖掘與應(yīng)用越來(lái)越重視。為了讓程序自動(dòng)瀏覽互聯(lián)網(wǎng)中的海量網(wǎng)頁(yè),把用戶需要的信息進(jìn)行收集整理,轉(zhuǎn)化成便于閱讀的形式并存儲(chǔ)起來(lái),方便用戶的理解和使用。研究了分布式爬蟲和Scrapy框架,將Scrapy和Redis相結(jié)合,設(shè)計(jì)并實(shí)現(xiàn)了一個(gè)基于Scrapy框架的分布式網(wǎng)站采集系統(tǒng)。結(jié)果表明該系統(tǒng)操作簡(jiǎn)單,可以降低編寫爬蟲的難度,同時(shí)分布式的采用也提高了爬蟲采集的效率。
關(guān)鍵詞:爬蟲軟件;C#;Scrapy框架;分布式;Redis
中圖分類號(hào):TP311? ? ? 文獻(xiàn)標(biāo)識(shí)碼:A
文章編號(hào):1009-3044(2019)20-0073-03
開放科學(xué)(資源服務(wù))標(biāo)識(shí)碼(OSID):
Abstract: In recent years, with the rapid development of the Internet, people are paying more and more attention to the mining and application of data. To make the program automatically browse the massive web pages on the Internet, and collect the information needed by users and then convert it into a form that is easy to read and store, so than it can convenient for people to understand and use. distributed crawler and Scrapy framework is studied, A distributed website collection system by combine the Scrapy and Redis is designed and implemented . The result shows that the system is simple to operate, which can reduce the difficulty of writing crawler script, and that the distributed structure improves the efficiency.
Key words: crawler; C#; Scrapy; distributed system; Redis
1 背景
在如今這個(gè)大數(shù)據(jù)的時(shí)代,人們手動(dòng)利用搜索引擎來(lái)尋找大量特定數(shù)據(jù)效率極低,而且針對(duì)性差,無(wú)法進(jìn)行系統(tǒng)的處理和展示。如果能夠?qū)⒒ヂ?lián)網(wǎng)中的龐大的信息數(shù)據(jù)收集起來(lái),經(jīng)過(guò)數(shù)據(jù)挖掘、數(shù)據(jù)清洗和數(shù)據(jù)分析后,它們可以變成具有參考和借鑒價(jià)值的信息,為人們提供靈感來(lái)源或決策參考的數(shù)據(jù)支持。因此,如何高效準(zhǔn)確地獲取所需的信息數(shù)據(jù)資源成為一個(gè)極其關(guān)鍵的問(wèn)題。
本文研究的主要內(nèi)容是設(shè)計(jì)并實(shí)現(xiàn)一個(gè)分布式爬蟲采集軟件,該軟件能夠適用于絕大多數(shù)的網(wǎng)站。即使非技術(shù)人員也可以通過(guò)簡(jiǎn)單的學(xué)習(xí)和分析輕松運(yùn)用本軟件爬取簡(jiǎn)單的目的信息數(shù)據(jù);對(duì)于專業(yè)人士而言,本系統(tǒng)可以減輕他們的工作量。
2 研究現(xiàn)狀
隨著20世紀(jì)90年代搜索引擎的出現(xiàn),網(wǎng)絡(luò)爬蟲也隨之出現(xiàn)。網(wǎng)絡(luò)爬蟲,又被稱為網(wǎng)頁(yè)蜘蛛,是一種根據(jù)設(shè)定的規(guī)則,自動(dòng)地抓取網(wǎng)頁(yè)信息的程序或者腳本[1]。隨著分布式網(wǎng)絡(luò)爬蟲的出現(xiàn),爬取效率得到了很大的提高。分布式網(wǎng)絡(luò)爬蟲可以看成是由多個(gè)集中式網(wǎng)絡(luò)爬蟲構(gòu)成, 分布式系統(tǒng)中的每個(gè)節(jié)點(diǎn)都可以看作一個(gè)集中式網(wǎng)絡(luò)爬蟲[2],Web Gather和Google搜索引擎所使用的網(wǎng)絡(luò)爬蟲系統(tǒng)就是分布式的爬蟲。現(xiàn)在網(wǎng)絡(luò)爬蟲已經(jīng)深入到了生活中的各個(gè)領(lǐng)域,如在金融方面徐翔等博士編寫設(shè)計(jì)的網(wǎng)絡(luò)爬蟲可用來(lái)分析網(wǎng)絡(luò)輿情與上證指數(shù)漲跌幅的關(guān)聯(lián)性[3];農(nóng)業(yè)方面劉曉剛教授開發(fā)了網(wǎng)絡(luò)爬蟲進(jìn)行網(wǎng)上農(nóng)產(chǎn)品的大數(shù)據(jù)抓取[4]。
3 工具簡(jiǎn)介
3.1 Scrapy
Scrapy是Python開發(fā)的一個(gè)快速、高層次的屏幕抓取和WEB抓取框架,用于抓取WEB站點(diǎn)并從頁(yè)面中提取結(jié)構(gòu)化的數(shù)據(jù)。Scrapy用途廣泛,可以用于數(shù)據(jù)挖掘、監(jiān)測(cè)和自動(dòng)化測(cè)試[5]。
3.2 Scrapy-redis
Scrapy-Redis是使用Scrapy框架和Redis數(shù)據(jù)庫(kù)工具組合實(shí)現(xiàn)的一個(gè)網(wǎng)絡(luò)分布式抓取開源項(xiàng)目[6]。雖然Scrapy框架本身并不支持分布式爬蟲,但是搭載了Redis數(shù)據(jù)庫(kù)后形成的Scrapy-Redis模式可以很好的解決這個(gè)問(wèn)題,它的原理是將Scrapy自身待抓取的網(wǎng)頁(yè)URL隊(duì)列替換成Redis的數(shù)據(jù)庫(kù)內(nèi)的隊(duì)列,使得要爬取的請(qǐng)求存放在同一個(gè)Redis服務(wù)器。開始分布式任務(wù)后,多個(gè)爬蟲程序便可以去同一個(gè)Redis的數(shù)據(jù)庫(kù)里獲取請(qǐng)求隊(duì)列的URL,分別采集任務(wù),再把數(shù)據(jù)存入同一個(gè)Redis數(shù)據(jù)庫(kù)里。
4 系統(tǒng)總體設(shè)計(jì)
本軟件是一個(gè)簡(jiǎn)單易操作的爬蟲采集軟件,使用了熱門的框架和技術(shù),親和性適用性強(qiáng),運(yùn)行和維護(hù)不需要太多的成本;建立任務(wù)過(guò)程簡(jiǎn)單易學(xué),無(wú)需太多人力投入。
軟件分成三個(gè)模塊,系統(tǒng)框架圖如圖1所示。C#窗體程序負(fù)責(zé)和用戶的交互,Scrapy-Redis框架負(fù)責(zé)爬取數(shù)據(jù),Redis數(shù)據(jù)庫(kù)和用戶指定數(shù)據(jù)庫(kù)負(fù)責(zé)存儲(chǔ)數(shù)據(jù)。系統(tǒng)的任務(wù)由一個(gè)至多個(gè)層構(gòu)成,每一層是一個(gè)獨(dú)立的方法,代表一個(gè)邏輯層的網(wǎng)頁(yè)。在每一層里,可以通過(guò)添加不同屬性的Xpath等信息爬取該層網(wǎng)頁(yè)中的不同內(nèi)容。通過(guò)添加網(wǎng)站的起始URL、層X(jué)path和每層的屬性信息,系統(tǒng)將自動(dòng)生成爬蟲來(lái)采集網(wǎng)頁(yè)并將采集到的內(nèi)容存入數(shù)據(jù)庫(kù)。
4.1 交互層——窗體模塊設(shè)計(jì)
交互層主要負(fù)責(zé)軟件操作頁(yè)面展示和進(jìn)行人機(jī)交互。系統(tǒng)的設(shè)計(jì)可以分為四個(gè)模塊:主頁(yè)面模塊、創(chuàng)建與編輯任務(wù)視圖模塊、服務(wù)端視圖模塊和客戶端視圖模塊。
1)主頁(yè)面模塊,使用者可以查看所有任務(wù)的信息列表,具體包括每個(gè)任務(wù)的任務(wù)名、采集網(wǎng)址、模式(單任務(wù)、分布式)、類型(服務(wù)器/客戶端/單機(jī))、狀態(tài)、開啟時(shí)間等信息。針對(duì)每個(gè)任務(wù),使用者可以選擇對(duì)其進(jìn)行開始、暫停、停止、編輯、前往根目錄等操作。
2)創(chuàng)建與編輯任務(wù)視圖模塊,使用者可對(duì)任務(wù)進(jìn)行模式選擇,填寫任務(wù)基礎(chǔ)信息和編輯任務(wù)的操作。編輯任務(wù)的界面分為可視化界面和代碼界面。在可視化界面,用戶可以通過(guò)一些可視化的操作增刪改查爬蟲的層和每層的屬性信息,選擇該層爬蟲是否需要分頁(yè)處理;在代碼界面,用戶可以預(yù)覽生成的代碼。經(jīng)過(guò)一些可視化的流程和少量修改,使用者可完成針對(duì)性的爬取任務(wù)。
3)服務(wù)端視圖模塊,使用者可以監(jiān)聽客戶端接入請(qǐng)求、查看各個(gè)已接入客戶端的信息、開啟Redis數(shù)據(jù)庫(kù)監(jiān)聽、將任務(wù)發(fā)送至客戶端、開啟和停止采集任務(wù)。
4) 客戶端視圖模塊,使用者可以通過(guò)客戶端視圖模塊查看是否成功連接服務(wù)端,接收服務(wù)器任務(wù)和開始客戶端采集任務(wù)。
4.2 邏輯業(yè)務(wù)層——爬蟲模塊設(shè)計(jì)
邏輯業(yè)務(wù)層是本系統(tǒng)的核心,它主要用于實(shí)現(xiàn)對(duì)具體業(yè)務(wù)的操作,在本例中主要用于實(shí)現(xiàn)根據(jù)交互層提交的任務(wù)數(shù)據(jù)進(jìn)行爬蟲生成,網(wǎng)站爬取然后將采集結(jié)果存入數(shù)據(jù)庫(kù)。
爬蟲提取網(wǎng)頁(yè)內(nèi)容的核心方法主要有Beautifulsoup、正則表達(dá)式和Xpath三種。Beautifulsoup是Python自帶的一個(gè)Html的解析庫(kù),它的優(yōu)點(diǎn)是更符合人們直觀理解的語(yǔ)義。系統(tǒng)將需要分頁(yè)的頁(yè)面使用BeautifulSoup解析 “下一頁(yè)”字段所對(duì)應(yīng)的URL地址,如果沒(méi)有對(duì)應(yīng)的完整網(wǎng)址,則將任務(wù)的采集網(wǎng)址和找到的URL地址的組合作為下一重的URL地址。正則表達(dá)式是對(duì)字符串進(jìn)行過(guò)濾處理的一種邏輯公式,雖然正則表達(dá)式能使爬蟲處理速度更快,并且比起Xpath功能更為強(qiáng)大,但它復(fù)雜且容易出錯(cuò),增加普通人的學(xué)習(xí)難度和使用難度。Xpath 是一門在 XML 文檔中查找信息的語(yǔ)言, 靈活易學(xué),便于非編程人員的學(xué)習(xí)及使用。綜上考慮本系統(tǒng)將采用Xpath作為系統(tǒng)的爬取核心[7]。
4.3 數(shù)據(jù)庫(kù)層設(shè)計(jì)
數(shù)據(jù)庫(kù)層用于實(shí)現(xiàn)系統(tǒng)對(duì)數(shù)據(jù)庫(kù)的操作,本例中主要體現(xiàn)在系統(tǒng)自動(dòng)創(chuàng)建數(shù)據(jù)庫(kù)、刪除數(shù)據(jù)庫(kù)和將數(shù)據(jù)插入數(shù)據(jù)庫(kù)的操作。為了方便用戶信息存儲(chǔ),系統(tǒng)需要在爬蟲存儲(chǔ)模塊創(chuàng)建一個(gè)原始數(shù)據(jù)庫(kù),使得用戶只需將數(shù)據(jù)庫(kù)類型、數(shù)據(jù)庫(kù)名、帳號(hào)、密碼填入配置文件,運(yùn)行代碼后系統(tǒng)會(huì)自動(dòng)在目標(biāo)數(shù)據(jù)庫(kù)自動(dòng)創(chuàng)建表和存入信息。系統(tǒng)為每個(gè)任務(wù)的每層創(chuàng)建一個(gè)單獨(dú)的表,創(chuàng)建表的表名為任務(wù)名_層數(shù),表中每一列的字段名為任務(wù)的屬性名稱。這種結(jié)構(gòu)有利于直觀的區(qū)分每一層和顯示每一層的表單數(shù)據(jù)。
5 系統(tǒng)主要實(shí)現(xiàn)
5.1 爬蟲腳本
系統(tǒng)使用Python作為開發(fā)爬蟲的語(yǔ)言。爬蟲主要使用Scrapy-Redis框架,除了解決了分布式處理的難題,這種框架最大的優(yōu)點(diǎn)還有方便的去重處理和程序中斷處理。由于URL存放在同一個(gè)服務(wù)端,服務(wù)端可以經(jīng)過(guò)統(tǒng)一去重后再分配給各個(gè)客戶端進(jìn)行抓取,并且,當(dāng)程序出現(xiàn)中斷后,數(shù)據(jù)庫(kù)中仍存在請(qǐng)求隊(duì)列, 當(dāng)系統(tǒng)再次啟動(dòng)時(shí)任務(wù)將會(huì)繼續(xù)爬取[8]。
對(duì)于爬取動(dòng)態(tài)JS處理的網(wǎng)頁(yè),系統(tǒng)采用無(wú)頭瀏覽器抓取單個(gè)網(wǎng)頁(yè)并進(jìn)行渲染,解決了傳統(tǒng)HTTP爬蟲抓取單頁(yè)應(yīng)用難以處理異步請(qǐng)求的問(wèn)題[9]。為了提升爬取頁(yè)面爬蟲的運(yùn)行速度,代碼默認(rèn)是禁用Css圖片的,如需加載,手動(dòng)將相應(yīng)代碼刪掉即可。
5.2 窗體程序搭建
軟件使用C/S架構(gòu)。服務(wù)器和客戶端之間通過(guò)Socket進(jìn)行數(shù)據(jù)傳輸。Socket是一個(gè)網(wǎng)絡(luò)通信接口,它采用的TCP/IP協(xié)議可以唯一的標(biāo)識(shí)網(wǎng)絡(luò)中的一個(gè)進(jìn)程,使得服務(wù)器可以安全準(zhǔn)確地傳輸數(shù)據(jù)至客戶端[10]。
交互界面使用C#窗體程序進(jìn)行開發(fā)。系統(tǒng)開始任務(wù)后將解析編輯文件過(guò)程生成的Xml格式任務(wù)數(shù)據(jù)和原始的爬蟲代碼相結(jié)合,利用字符串處理技術(shù)自動(dòng)生成目標(biāo)爬蟲代碼,調(diào)用Cmd執(zhí)行命令執(zhí)行爬蟲程序。執(zhí)行完任務(wù)后,任務(wù)狀態(tài)將更新為已完成,同時(shí)數(shù)據(jù)庫(kù)獲得爬蟲程序存入的對(duì)應(yīng)任務(wù)采集數(shù)據(jù)。
5.3 數(shù)據(jù)庫(kù)層的實(shí)現(xiàn)
為了提高數(shù)據(jù)的安全性,防止誤刪,也為了便于分布式系統(tǒng)的存儲(chǔ),系統(tǒng)采用Redis數(shù)據(jù)庫(kù)和用戶設(shè)計(jì)數(shù)據(jù)庫(kù)并行儲(chǔ)存系統(tǒng)爬取下來(lái)的數(shù)據(jù)。配置完數(shù)據(jù)庫(kù)的文件后,爬蟲存儲(chǔ)模塊通過(guò)調(diào)用已編寫封裝好的DLL(動(dòng)態(tài)鏈接庫(kù)文件)來(lái)幫助創(chuàng)建和存入數(shù)據(jù)庫(kù)。基于數(shù)據(jù)庫(kù)兼容性的考慮,系統(tǒng)支持TXT文本和Mysql、SqlServer等數(shù)據(jù)庫(kù)。
6 結(jié)束語(yǔ)
這套系統(tǒng),可在通過(guò)一些可視化的操作后,完成爬蟲的爬取。使用它用戶可以更加簡(jiǎn)單快捷地爬取網(wǎng)站。同時(shí),爬蟲的設(shè)計(jì)基本上解決了一般爬蟲的去重、分頁(yè)處理、動(dòng)態(tài)JS加載、存入數(shù)據(jù)庫(kù)等問(wèn)題,滿足了爬蟲人員的一般需要。分布式爬蟲的功能解決了單臺(tái)機(jī)器爬取大型網(wǎng)站速度慢的問(wèn)題。未來(lái)還將繼續(xù)完善本系統(tǒng)的研究,解決初始數(shù)據(jù)庫(kù)設(shè)計(jì)缺陷、反爬蟲處理等問(wèn)題。
參考文獻(xiàn):
[1] 百度百科. 網(wǎng)絡(luò)爬蟲[EB/OL]. [2019-04-17]. https://baike.baidu.com/item/網(wǎng)絡(luò)爬蟲/5162711?fr=aladdin.
[2] 劉洋, 崔翠, 李立新. 一種基于python語(yǔ)言的網(wǎng)絡(luò)爬蟲研究[EB/OL].https://www.xzbu.com/8/view-7493419.htm.
[3] 徐翔, 靳菁, 呂偉欣. 網(wǎng)絡(luò)輿情作為社會(huì)傳感器對(duì)股票指數(shù)的影響——基于LDA主題模型的挖掘分析[J]. 財(cái)務(wù)與金融, 2018(6): 1-9.
[4] 劉曉剛. 農(nóng)產(chǎn)品大數(shù)據(jù)的抓取和分析方法探索[J]. 農(nóng)村經(jīng)濟(jì)與科技, 2018, 29(19): 304-305.
[5] 百度百科. Scrapy[EB/OL]. [2018-12-05].https://baike.baidu.com/item/scrapy/7914913?fr=aladdin.
[6] 鄧萬(wàn)宇, 劉光達(dá), 董瑩瑩. 一種基于Scrapy-Redis的分布式微博數(shù)據(jù)采集方案[J]. 信息技術(shù), 2018(11): 59-62.
[7] lingojames. python爬蟲里信息提取的核心方法: Beautifulsoup、Xpath和正則表達(dá)式[EB/OL]. [2017-06-01] https://blog.csdn.net/lingojames/article/details/72835972.
[8] 黎玉香, 于偉. 分布式網(wǎng)絡(luò)爬蟲系統(tǒng)的基本原理與實(shí)現(xiàn)[J]. 花炮科技與市場(chǎng), 2018(4): 45.
[9] 褲褲他爸. 2018-08-16面試題-無(wú)頭瀏覽器[EB/OL]. [2018-08-16] https://www.jianshu.com/p/35a9e566e6d6.
[10] Xiao__Tian_. 基于TCP協(xié)議的網(wǎng)絡(luò)通信(socket編程)[EB/OL]. [2016-07-28] https://blog.csdn.net/xiao__tian__/article/details/52050863.
【通聯(lián)編輯:謝媛媛】