Webcollector應用(一)

  webcollector是一個開源的Java網絡爬蟲框架。最近的爬蟲改用java寫了,對這一週的工做進行簡要總結。對於內部機制瞭解不深刻,主要側重在應用。html

1、環境搭建java

  須要安裝一個webcollector的jar包,從官網上下載bin文件,解壓,根據不一樣IDE的安裝方式進行安裝便可。node

  https://github.com/CrawlScript/WebCollectorgit

  關於使用,官網上提供了不少的例子,從GitHub上將整個Webcollector的工程下載下來,參照進行編碼。github

  

  我直接在官方提供的工程上面建了個文件夾,進行編碼。web

2、基本使用spring

  兩個class,一個Model,一個抓取sql

  一、Model類——封裝了要抓取的那些字段數據庫

 1 package cn.edu.hfut.dmic.webcollector.example.myCrawler.test;
 2 
 3 public class TongModel {
 4     String fullName;
 5     String shortName;
 6     String time;
 7     public String getFullName() {
 8         return fullName;
 9     }
10 
11     public void setFullName(String fullName) {
12         this.fullName = fullName;
13     }
14 
15     public String getShortName() {
16         return shortName;
17     }
18 
19     public void setShortName(String shortName) {
20         this.shortName = shortName;
21     }
22 
23     public String getTime() {
24         return time;
25     }
26 
27     public void setTime(String time) {
28         this.time = time;
29     }
30 }
View Code

  二、Crawl類——定義了抓取規則網絡

 1 package cn.edu.hfut.dmic.webcollector.example.myCrawler.test;
 2 import cn.edu.hfut.dmic.webcollector.crawler.DeepCrawler;
 3 //import cn.edu.hfut.dmic.webcollector.example.util.ProxyCollector;
 4 import cn.edu.hfut.dmic.webcollector.example.util.JDBCBase;
 5 import cn.edu.hfut.dmic.webcollector.model.Links;
 6 import cn.edu.hfut.dmic.webcollector.model.Page;
 7 import cn.edu.hfut.dmic.webcollector.net.HttpRequesterImpl;
 8 import cn.edu.hfut.dmic.webcollector.net.RandomProxyGenerator;
 9 import org.jsoup.nodes.Document;
10 import org.jsoup.nodes.Element;
11 import org.jsoup.select.Elements;
12 import org.springframework.jdbc.core.JdbcTemplate;
13 
14 import java.util.List;
15 public class CrawlTong  extends DeepCrawler{
16     JdbcTemplate jdbcTemplate = JDBCBase.getInstance().getTemplete2();
17     public CrawlTong(String crawlPath){
18         super(crawlPath);
19     }
20 
21     @Override
22     public Links visitAndGetNextLinks(Page page) {
23         Document doc = page.getDoc();
24         boolean iRedirect = page.getResponse().getRedirect();
25         if(iRedirect)
26             return null;
27         TongModel tongModel = new TongModel();
28         Elements elementsAll = doc.getAllElements();
29         tongModel.setFullName(elementsAll.select("a.v3-branding_logo").text());
30         tongModel.setShortName(elementsAll.select("a.v3-branding_logo").attr("href"));
31         tongModel.setTime("2010-01-21");
32         saveToDB(tongModel);
33         return null;
34     }
35     public int saveToDB(TongModel m)
36     {
37         System.out.println(m.getFullName());
38         System.out.println(m.getShortName());
39         System.out.println(m.getTime());
40         String sql = "insert into tong(fullName,shortName,timer) values(?,?,?)";
41         int updates=jdbcTemplate.update(sql,m.getFullName(),m.getShortName(),m.getTime());
42         return 0;
43     }
44     public static void main(String[] args) throws Exception{
45         CrawlTong crawler = new CrawlTong("/tong");
46         crawler.addSeed("https://www.tzg.cn/");
47         crawler.start(1);
48     }
49 
50 }
View Code

  繼承自抓取父類,我採用的是繼承DeepCrawler,相應的也能夠繼承自BreathCrawler。

  主要是三個方法,當寫完extends DeepCrawler,通常編輯器會提示你實現構造方法和重寫visitAndGetNextLinks方法,而後須要建立一個main函數

  (1)main函數,至關於爬蟲的入口

    ① 新建一個爬蟲

    ② 設定種子,即要爬取的URL

    ③ 能夠設定爬取的線程數,crawler.setThreads(1); 能夠並行爬行

    ④ 設定爬取的深度,crawler.start(10);

     關於深度,個人理解是,初始種子是第一層;若是在爬取的過程當中不斷的加入新的URL,經過第一層新加入的就算第二層;以此類推

     一般爬取的時候深度很差確認,最簡單的辦法就是設定個特別大的值

  (2)visitAndGetNextLinks方法,頁面解析

    採用Jsoup的方法,對頁面進行解析 http://www.open-open.com/jsoup/selector-syntax.htm

    定義一個Model的對象,經過set的方式把數據存入model  

    再將Model存放到數據庫中

  (3)構造方法

    關於構造方法,我目前的應用中基本沒有修改,後續遇到再補充

  (4)JdbcTemplate jdbcTemplate = JDBCBase.getInstance().getTemplete2();

    這行代碼,是數據庫相關的配置

    JDNCBase文件中的getTemplete2(),定義了鏈接哪一個數據庫

補充1:DAO

  WebCollector自己融合了Spring框架(不知道這樣說合不合理,自己對Java的框架理解不深),能夠經過DAO的形式對數據進行存儲。

 1 package cn.edu.hfut.dmic.webcollector.example.myCrawler.test;
 2 
 3 import cn.edu.hfut.dmic.webcollector.example.util.GenericDaoImpl;
 4 
 5 import java.util.List;
 6 
 7 public class DataVaryDao extends GenericDaoImpl<DataVaryModel,Long> {
 8 
 9     public DataVaryDao(){super(DataVaryModel.class);}
10 
11     public Long add(DataVaryModel model)
12     {
13         return insert(model);
14     }
15 
16     public int updata(DataVaryModel model)
17     {
18         return this.update(model);
19     }
20 
21     public List<DataVaryModel> getDataBySql(String sql, List<Object> values)
22     {
23         return this.selectBySqlList(sql, values);
24 
25     }
26 
27     @Override
28     public long getCountBySqlList(String sql, List<Object> values) {
29         return 0;
30     }
31 }
View Code
 1 dataList = dataDao.getDataBySql("select * from table where xmbm = ? and platform_id = ?", valueList);
 2             dataModelDB = dataList.get(0);
 3             
 4             dataVaryModel=new DataVaryModel();
 5             dataVaryModel.setData_id(dataModelDB.getId());
 6             dataVaryModel.setKtje(ktje);
 7             dataVaryModel.setXmzt(xmzt);
 8             dataVaryModel.setTzrc(tzrc);
 9             dataVaryModel.setCreate_date(new Timestamp(new Date().getTime()));
10             dataVaryDao.add(dataVaryModel);
View Code

  上面就是定義了一個簡單的DAO類,這個類也繼承自一個基類;而後經過調用DAO中的方法進行數據存儲

  固然DAO對數據的增刪改查等須要本身後臺實現

補充2:動態增長種子

  爬取的一個常見狀況,一邊爬網頁,一邊將網頁中的URL加入到爬取隊列中。  

1 Links links=new Links();
2 for(int i=0;i<length;i++){
3                 String temp=pre+elements1.get(i).attr("href");
4                 System.out.println(temp);
5                 System.out.println(elements1.get(i).text().trim());
6                 links.add(temp);
7             }
8 
9 return links;
View Code

  在visitAndGetNextLinks方法中,定義一個Links類型的變量,將URL加入變量中,返回便可

  如上述說起的爬取深度,爬出初始URL頁面獲取的links就是第二層,一顆樹形的結構,隨着抓取的增長,深度不斷加深

補充3:不動態增長種子,可是爬取新頁面

  還有一種狀況,在爬取的過程當中獲得了新的URL,可是不想放入對爬取隊列,想當下就拿到上面的數據。

 1  String newUrl="http://www.xueshandai.com/invest/invest-record/"+xmbm;
 2             try {
 3                 System.out.println(newUrl);
 4                 String html = requester.getResponse(newUrl).getHtml("UTF-8");
 5                 Pattern p = Pattern.compile("<div class=\"jtit3\">(.*?)</div>");
 6                 Matcher m = p.matcher(html);
 7                 System.out.println(m);
 8                 if(m.find()){
 9                     System.out.println("------find---------");
10                     String s=m.group().split(":")[3].split("<")[0];
11                     System.out.println(s.substring(0,s.length()-1));
12                     tzrc = Integer.parseInt(s.substring(0,s.length()-1));
13                 }
14             } catch (Exception e) {
15                 e.printStackTrace();
16             }
View Code

  requester.getResponse(newUrl).getHtml("UTF-8");

  經過這樣一條語句,能夠直接獲得url的HTML,不過存儲的是String類型,能夠經過正則進行解析,獲取須要的數據。

補充4:對不一樣種類的URL進行分門處理

  可能抓取隊列中存放着不一樣類型的URL,對每一種爬取方案是不一樣的。

  高大上的方法:定義抽取器

  簡單方法:字符串匹配

   if(pageURL.contains("list")){}

  else if (pageURL.contains("detail")){}

 

以上,就是目前遇到的一些狀況,比較簡單,還會再用兩週。

後續內容:

  (1)加代理(已經遇到封IP的狀況了)、加頭部文件

  (2)抽取器

  (3)解析Json文件、XML文件

  (4)內部機制的學習調用

相關文章
相關標籤/搜索