htmlunit爬取数据

来源:互联网 发布:物理软件高中 编辑:程序博客网 时间:2024/05/16 02:55

      HtmlUnit是一个“java程序的浏览器”。它为html文档建模,提供了一个API,允许您调用页面、填写表单、点击链接等,就像你在“正常”浏览器里做的一样。他有相当好的JavaScirpt支持(不断改进),甚至可以使用相当复杂的AJAX库,模拟Chrome、Firefox或Internet Explorer,这取决于所使用的配置。他通常用于测试的目的或从web站点检索信息。

      下面贴出我在阳光高考中抓取专业的例子,这个例子最主要的特点是模仿浏览器的点击时间,动态的获取数据,其中包括ajax请求的数据:



public static void main(String[] args) throws IOException {  /*  String url="http://gaokao.chsi.com.cn/zyk/zybk/";    Document doc = Jsoup.connect(url).get();    System.out.println(doc);*/    WebClient webClient = new WebClient();    // 部分js无法加载,导致控制台报错,下面几行代码都是为了让控制台不报错,但是不能从根本上解决问题哟!    LogFactory.getFactory().setAttribute("org.apache.commons.logging.Log",    "org.apache.commons.logging.impl.NoOpLog");    java.util.logging.Logger.getLogger("com.gargoylesoftware.htmlunit").setLevel(Level.OFF);    java.util.logging.Logger.getLogger("org.apache.commons.httpclient").setLevel(Level.OFF);    webClient.getOptions().setThrowExceptionOnFailingStatusCode(false);    webClient.getOptions().setThrowExceptionOnScriptError(false);    //开启javascript    webClient.getOptions().setJavaScriptEnabled(true);    //htmlunit对css不是很友好呢!    webClient.getOptions().setCssEnabled(false);    //使重定向可用    webClient.getOptions().setRedirectEnabled(true);    //设置超时时间    webClient.getOptions().setTimeout(50000);    //获取网页    HtmlPage htmlpage = webClient.getPage("http://gaokao.chsi.com.cn/zyk/zybk/");    //加载javascript,有时候数据会加载不到,这个时候就需要加一个延迟时间。    webClient.waitForBackgroundJavaScript(20000);    //得到本科数据本科数据    HtmlElement bk = htmlpage.getHtmlElementById("1050");    //通过xpath解析网页内容,关于xpath获取节点,可以在W3School教程中看到(解析很方便而且很简单哦)    List<HtmlListItem> byXPath = (List<HtmlListItem>) htmlpage.getByXPath("//ul[@id='mlUl']/li");    ArrayList<HashMap<String, ArrayList<String>>> hashMaps = new ArrayList<>();    for (HtmlListItem htmlListItem : byXPath) {        HashMap<String, ArrayList<String>> hashMap = new HashMap<>();        //得到节点文本        String textContent = htmlListItem.getTextContent();        System.out.println(textContent);        //执行click()事件,这是使用htmlunit最便捷的地方了,可以模仿浏览器的行为        HtmlPage middle = (HtmlPage)htmlListItem.click();        webClient.waitForBackgroundJavaScript(20000);        List<HtmlListItem> byXPath1 = (List<HtmlListItem>) middle.getByXPath("//ul[@id='xkUl']/li");        for (HtmlListItem listItem : byXPath1) {            String textContent1 = listItem.getTextContent();          //  System.out.println(textContent1);            HtmlPage professionPage = (HtmlPage)listItem.click();            webClient.waitForBackgroundJavaScript(20000);           // System.out.println(professionPage.asXml());            //通过xpath解析获取自己想要的数据            List<HtmlAnchor> professionList = (List<HtmlAnchor>) professionPage.getByXPath("//div[@id='listResult']/table/tbody/tr/td[1]/a[@target='_blank']");            for (HtmlAnchor item : professionList) {                String profession= item.getTextContent();            }        }    }}

怎么样,是不是很简单?上面的例子只是模仿了点击事件,然而htmlunit还有更加高级的功能,从原理上来说,他是直接访问网站的服务器,发的请求,所以没有被封号的危险,简单又容易上手。下面给出一个模仿表单提交事件的例子:

public static void test() throws IOException {        WebClient webclient = new WebClient();        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);        // 最近周星驰比较火呀,我这里设置一下在搜索框内填入”java“        textField.setValueAttribute("java");        // 输入好了,我们点一下这个按钮        final HtmlPage nextPage = button.click();              String result = nextPage.asXml();        System.out.println(result);    }}


阅读全文
0 0