成都創新互聯專注于膠州企業網站建設,響應式網站開發,成都做商城網站。膠州網站建設公司,為膠州等地區提供建站服務。全流程按需定制開發,專業設計,全程項目跟蹤,成都創新互聯專業和態度為您提供的服務
1.爬取頁面效果圖
點擊"百度一下"按鈕前頁面

點擊"百度一下"按鈕后頁面

天涯社區登錄頁面

登錄進去之后個人主頁

二、具體實現代碼
HtmlUnit(底層也是采用httpclient)和jsoup API
package com.yuanhai.test;
import java.io.IOException;
import java.net.MalformedURLException;
import org.jsoup.Connection;
import org.jsoup.Jsoup;
import org.jsoup.nodes.Document;
import org.jsoup.nodes.Element;
import org.jsoup.safety.Whitelist;
import org.jsoup.select.Elements;
import org.junit.Assert;
import org.junit.Test;
import com.gargoylesoftware.htmlunit.BrowserVersion;
import com.gargoylesoftware.htmlunit.DefaultCredentialsProvider;
import com.gargoylesoftware.htmlunit.NicelyResynchronizingAjaxController;
import com.gargoylesoftware.htmlunit.WebClient;
import com.gargoylesoftware.htmlunit.html.HtmlAnchor;
import com.gargoylesoftware.htmlunit.html.HtmlButton;
import com.gargoylesoftware.htmlunit.html.HtmlDivision;
import com.gargoylesoftware.htmlunit.html.HtmlForm;
import com.gargoylesoftware.htmlunit.html.HtmlInput;
import com.gargoylesoftware.htmlunit.html.HtmlPage;
import com.gargoylesoftware.htmlunit.html.HtmlSubmitInput;
import com.gargoylesoftware.htmlunit.html.HtmlTextInput;
//參考博文
//1.http://blog.csdn.net/zstu_cc/article/details/39250903
//2.http://blog.csdn.net/cslie/article/details/48735261
public class HtmlUnitAndJsoup {
/*
* 首先說說HtmlUnit相對于HttpClient的最明顯的一個好處,
* 是HtmlUnit不僅保存了這個網頁對象,更難能可貴的是它還存有這個網頁的所有基本操作甚至事件。
* 現在很多網站使用大量ajax,普通爬蟲無法獲取js生成的內容。
*/
/*
* 依賴的jar包 commons-lang3-3.1.jar htmlunit-2.13.jar htmlunit-core-js-2.13.jar
* httpclient-4.3.1.jar httpcore-4.3.jar httpmime-4.3.1.jar sac-1.3.jar
* xml-apis-1.4.01.jar commons-collections-3.2.1.jar commons-io-2.4.jar
* xercesImpl-2.11.0.jar xalan-2.7.1.jar cssparser-0.9.11.jar
* nekohtml-1.9.19.jar
*/
// 百度新聞高級搜索
@Test
public void HtmlUnitBaiduAdvanceSearch() {
try {
// 得到瀏覽器對象,直接New一個就能得到,現在就好比說你得到了一個瀏覽器了
WebClient webclient = new WebClient();
// 這里是配置一下不加載css和javaScript,配置起來很簡單,是不是
webclient.getOptions().setCssEnabled(false);
webclient.getOptions().setJavaScriptEnabled(false);
// 做的第一件事,去拿到這個網頁,只需要調用getPage這個方法即可
HtmlPage htmlpage = webclient
.getPage("http://news.baidu.com/advanced_news.html");
// 根據名字得到一個表單,查看上面這個網頁的源代碼可以發現表單的名字叫“f”
final HtmlForm form = htmlpage.getFormByName("f");
System.out.println(form);
// 同樣道理,獲取”百度一下“這個按鈕
final HtmlSubmitInput button = form.getInputByValue("百度一下");
System.out.println(button);
// 得到搜索框
final HtmlTextInput textField = form.getInputByName("q1");
System.out.println(textField);
// 最近周星馳比較火呀,我這里設置一下在搜索框內填入”周星馳“
textField.setValueAttribute("周星馳");
// 輸入好了,我們點一下這個按鈕
final HtmlPage nextPage = button.click();
// 我把結果轉成String
System.out.println(nextPage);
String result = nextPage.asXml();
System.out.println(result);
} catch (Exception e) {
e.printStackTrace();
}
}
// 測試天涯論壇登陸界面 HtmlUnit 頁面JS的自動跳轉(響應碼是200,但是響應的頁面就是一個JS)
// httpClient就麻煩了
@Test
public void TianyaTestByHtmlUnit() {
try {
WebClient webClient = new WebClient();
// The ScriptException is raised because you have a syntactical
// error in your javascript.
// Most browsers manage to interpret the JS even with some kind of
// errors
// but HtmlUnit is a bit inflexible in that sense.
// 加載的頁面有js語法錯誤會拋出異常
webClient.getOptions().setJavaScriptEnabled(true); // 啟用JS解釋器,默認為true
webClient.getOptions().setCssEnabled(false); // 禁用css支持
// 設置Ajax異步處理控制器即啟用Ajax支持
webClient
.setAjaxController(new NicelyResynchronizingAjaxController());
// 當出現Http error時,程序不拋異常繼續執行
webClient.getOptions().setThrowExceptionOnFailingStatusCode(false);
// 防止js語法錯誤拋出異常
webClient.getOptions().setThrowExceptionOnScriptError(false); // js運行錯誤時,是否拋出異常
// 拿到這個網頁
HtmlPage page = webClient
.getPage("http://passport.tianya.cn/login.jsp");
// 填入用戶名和密碼
HtmlInput username = (HtmlInput) page.getElementById("userName");
username.type("yourAccount");
HtmlInput password = (HtmlInput) page.getElementById("password");
password.type("yourPassword");
// 提交
HtmlButton submit = (HtmlButton) page.getElementById("loginBtn");
HtmlPage nextPage = submit.click();
System.out.println(nextPage.asXml());
} catch (Exception e) {
e.printStackTrace();
}
}
// jsoup解析文檔
@Test
public void jsoupParse() {
try {
/** HtmlUnit請求web頁面 */
// 模擬chorme瀏覽器,其他瀏覽器請修改BrowserVersion.后面
WebClient wc = new WebClient(BrowserVersion.CHROME);
wc.getOptions().setJavaScriptEnabled(true); // 啟用JS解釋器,默認為true
wc.getOptions().setCssEnabled(false); // 禁用css支持
wc.getOptions().setThrowExceptionOnScriptError(false); // js運行錯誤時,是否拋出異常
wc.getOptions().setTimeout(10000); // 設置連接超時時間 ,這里是10S。如果為0,則無限期等待
HtmlPage page = wc.getPage("http://passport.tianya.cn/login.jsp");
String pageXml = page.asXml(); // 以xml的形式獲取響應文本
// text只會獲取里面的文本,網頁html標簽和script腳本會被去掉
String pageText = page.asText();
System.out.println(pageText);
// 方法一,通過get方法獲取
HtmlButton submit = (HtmlButton) page.getElementById("loginBtn");
// 方法二,通過XPath獲取,XPath通常用于無法通過Id搜索,或者需要更為復雜的搜索時
HtmlDivision div = (HtmlDivision) page.getByXPath("http://div").get(0);
// 網絡爬蟲中主要目的就是獲取頁面中所有的鏈接
java.util.List<HtmlAnchor> achList = page.getAnchors();
for (HtmlAnchor ach : achList) {
System.out.println(ach.getHrefAttribute());
}
System.out.println("-------jsoup部分------");
// 服務器端進行校驗并清除有害的HTML代碼,防止富文本提交有害代碼
Jsoup.clean(pageXml, Whitelist.basic());
/** jsoup解析文檔 */
// 把String轉化成document格式
Document doc = Jsoup.parse(pageXml);
Element loginBtn = doc.select("#loginBtn").get(0);
System.out.println(loginBtn.text());
Assert.assertTrue(loginBtn.text().contains("登錄"));
} catch (Exception e) {
e.printStackTrace();
}
}
// htmlunit設置代理上網
@Test
public void proxy() {
String proxyHost = "192.168.0.1";
int port = 80;
WebClient webClient = new WebClient(BrowserVersion.CHROME, proxyHost,
port);
webClient.setAjaxController(new NicelyResynchronizingAjaxController());
DefaultCredentialsProvider credentialsProvider = (DefaultCredentialsProvider) webClient
.getCredentialsProvider();
String username = "account";
String password = "password";
credentialsProvider.addCredentials(username, password);
}
// jsoup請求并解析
@Test
public void jsoupCrawl() throws IOException {
String url = "http://passport.tianya.cn/login.jsp";
Connection con = Jsoup.connect(url);// 獲取請求連接
// 瀏覽器可接受的MIME類型。
con.header("Accept",
"text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8");
con.header("Accept-Encoding", "gzip, deflate");
con.header("Accept-Language", "zh-cn,zh;q=0.8,en-us;q=0.5,en;q=0.3");
con.header("Connection", "keep-alive");
con.header("Host", url);
con.header("User-Agent",
"Mozilla/5.0 (Windows NT 6.1; WOW64; rv:26.0) Gecko/20100101 Firefox/26.0");
Document doc = con.get();
Elements loginBtn = doc.select("#loginBtn");
System.out.println(loginBtn.text());// 獲取節點中的文本,類似于js中的方法
}
}httpclient模擬post請求登錄
package com.yuanhai.test;
import java.io.IOException;
import java.security.cert.CertificateException;
import java.security.cert.X509Certificate;
import java.util.ArrayList;
import java.util.List;
import javax.net.ssl.SSLContext;
import org.apache.http.Consts;
import org.apache.http.Header;
import org.apache.http.HttpResponse;
import org.apache.http.NameValuePair;
import org.apache.http.client.HttpClient;
import org.apache.http.client.entity.UrlEncodedFormEntity;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.conn.ssl.SSLConnectionSocketFactory;
import org.apache.http.conn.ssl.SSLContextBuilder;
import org.apache.http.conn.ssl.TrustStrategy;
import org.apache.http.impl.client.HttpClients;
import org.apache.http.message.BasicNameValuePair;
import org.apache.http.util.EntityUtils;
import com.steadystate.css.parser.ParseException;
/**
* @author
* @date
* @version
*
*/
public class TianyaTestByHttpClient {
/**
* 無法實現js頁面的自動跳轉,HtmlUnit可以
*/
public static void main(String[] args) throws Exception {
// 這是一個測試,也是為了讓大家看的更清楚,請暫時拋開代碼規范性,不要糾結于我多建了一個局部變量等
// 得到認證https的瀏覽器對象
HttpClient client = getSSLInsecureClient();
// 得到我們需要的post流
HttpPost post = getPost();
// 使用我們的瀏覽器去執行這個流,得到我們的結果
HttpResponse hr = client.execute(post);
// 在控制臺輸出我們想要的一些信息
showResponseInfo(hr);
}
private static void showResponseInfo(HttpResponse hr) throws ParseException, IOException {
System.out.println("響應狀態行信息:" + hr.getStatusLine());
System.out.println("---------------------------------------------------------------");
System.out.println("響應頭信息:");
Header[] allHeaders = hr.getAllHeaders();
for (int i = 0; i < allHeaders.length; i++) {
System.out.println(allHeaders[i].getName() + ":" + allHeaders[i].getValue());
}
System.out.println("---------------------------------------------------------------");
System.out.println("響應正文:");
System.out.println(EntityUtils.toString(hr.getEntity()));
/* <body>
<script>
location.;
</script>
</body>*/
}
// 得到一個認證https鏈接的HttpClient對象(因為我們將要的天涯登錄是Https的)
// 具體是如何工作的我們后面會提到的
private static HttpClient getSSLInsecureClient() throws Exception {
// 建立一個認證上下文,認可所有安全鏈接,當然,這是因為我們僅僅是測試,實際中認可所有安全鏈接是危險的
SSLContext sslContext = new SSLContextBuilder().loadTrustMaterial(null, new TrustStrategy() {
public boolean isTrusted(X509Certificate[] chain, String authType) throws CertificateException {
return true;
}
}).build();
SSLConnectionSocketFactory sslsf = new SSLConnectionSocketFactory(sslContext);
return HttpClients.custom().//
setSSLSocketFactory(sslsf)//
// .setProxy(new HttpHost("127.0.0.1", 8888))
.build();
}
// 獲取我們需要的Post流,如果你是把我的代碼復制過去,請記得更改為你的用戶名和密碼
private static HttpPost getPost() {
HttpPost post = new HttpPost("https://passport.tianya.cn/login");
// 首先我們初始化請求頭
post.addHeader("Referer", "https://passport.tianya.cn/login.jsp");
post.addHeader("Host", "passport.tianya.cn");
post.addHeader("Origin", "http://passport.tianya.cn");
// 然后我們填入我們想要傳遞的表單參數(主要也就是傳遞我們的用戶名和密碼)
// 我們可以先建立一個List,之后通過post.setEntity方法傳入即可
// 寫在一起主要是為了大家看起來方便,大家在正式使用的當然是要分開處理,優化代碼結構的
List<NameValuePair> paramsList = new ArrayList<NameValuePair>();
/*
* 添加我們要的參數,這些可以通過查看瀏覽器中的網絡看到,如下面我的截圖中看到的一樣
* 不論你用的是firebug,httpWatch或者是谷歌自帶的查看器也好,都能查看到(后面會推薦輔助工具來查看)
* 要把表單需要的參數都填齊,順序不影響
*/
paramsList.add(new BasicNameValuePair("Submit", ""));
paramsList.add(new BasicNameValuePair("fowardURL", "http://www.tianya.cn"));
paramsList.add(new BasicNameValuePair("from", ""));
paramsList.add(new BasicNameValuePair("method", "name"));
paramsList.add(new BasicNameValuePair("returnURL", ""));
paramsList.add(new BasicNameValuePair("rmflag", "1"));
paramsList.add(new BasicNameValuePair("__sid", "1#1#1.0#a6c606d9-1efa-4e12-8ad5-3eefd12b8254"));
// 你可以申請一個天涯的賬號 并在下兩行代碼中替換為你的用戶名和密碼
paramsList.add(new BasicNameValuePair("vwriter", "yourAccount"));// 替換為你的用戶名
paramsList.add(new BasicNameValuePair("vpassword", "yourPassword"));// 你的密碼
// 將這個參數list設置到post中
post.setEntity(new UrlEncodedFormEntity(paramsList, Consts.UTF_8));
return post;
}
}參考文章:
http://blog.csdn.net/zstu_cc/article/details/39250903
http://blog.csdn.net/cslie/article/details/48735261
分享題目:HtmlUnit、httpclient、jsoup爬取網頁信息并解析
網頁鏈接:http://www.js-pz168.com/article34/jcijpe.html
成都網站建設公司_創新互聯,為您提供網站設計公司、企業網站制作、軟件開發、品牌網站建設、外貿網站建設、品牌網站設計
聲明:本網站發布的內容(圖片、視頻和文字)以用戶投稿、用戶轉載內容為主,如果涉及侵權請盡快告知,我們將會在第一時間刪除。文章觀點不代表本網站立場,如需處理請聯系客服。電話:028-86922220;郵箱:631063699@qq.com。內容未經允許不得轉載,或轉載時需注明來源: 創新互聯