linux 环境下 Java 运行 selenium 无界面 chrome 环境设置

前言

《Java 中使用 selenium 和 chrome 浏览器下载动态网页》 一文中,演示了如何在 window 环境下通过 selenium 和 chrome 来下载动态网页。但是我们的爬虫一般是运行在 linux 服务器上的。服务器上一般是没有 GUI 环境的。无法打开 chrome 窗口界面。以前的时候,爬虫系统是用一种无界面的浏览器 PhantomJS 来实现。但是现在因为 FireFox 、chrome 这些浏览器开始支持无头模式后, PhantomJS 已经停止更新了,所以现在推荐使用 FireFox 和 chrome 的无头模式来替代 PhantomJS 了。所谓的无头模式就是无界面运行模式,正好适合在 linux 服务器这种没有 GUI 环境的情况下使用。

在 linux 环境下使用 selenium 驱动 chrome 需要安装 chrome 浏览器和 chrome webdriver。下面在 centos 7 环境下展示应该如何做。

安装 google chrome

首先从地址 https://dl.google.com/linux/direct/google-chrome-stable_current_x86_64.rpm 下载离线安装包。然后执行下面的命令安装 chrome 需要的依赖包

yum install libX11 libXcursor libXdamage libXext libXcomposite libXi libXrandr gtk3 libappindicator-gtk3 xdg-utils libXScrnSaver liberation-fonts

然后执行命令安装 chrome

rpm -ivh google-chrome-stable_current_x86_64.rpm

完成后执行下面的命令查看版本

[root@localhost ~]# google-chrome --version
Google Chrome 70.0.3538.110 

可以看出当前版本为 70 版本

安装 chrome webdriver

和文章 《Java 中使用 selenium 和 chrome 浏览器下载动态网页》 中一样,找到支持 70 版本 chrome 的下载地址,下载 linux 平台版本的文件 chromedriver_linux64.zip 即可

 
web driver 不同平台

无头模式 selenium chrome 调用程序样例

还是以 《Java 中使用 selenium 和 chrome 浏览器下载动态网页》 中的程序为基础,将他改造为无头模式

        WebDriver webDriver = null;
        try {
            String url = "https://www.jianshu.com/p/675ea919230e";
            ChromeOptions chromeOptions=new ChromeOptions(); //设置 chrome 的无头模式 chromeOptions.setHeadless(Boolean.TRUE); //启动一个 chrome 实例 webDriver = new ChromeDriver(chromeOptions); //访问网址 webDriver.get(url); Document document = Jsoup.parse(webDriver.getPageSource()); Element titleElement = document.selectFirst("div.article h1.title"); Element authorElement = document.selectFirst("div.article div.author span.name"); Element timeElement = document.selectFirst("div.article span.publish-time"); Element wordCountElement = document.selectFirst("div.article span.wordage"); Element viewCountElement = document.selectFirst("div.article span.views-count"); Element commentCountElement = document.selectFirst("div.article span.comments-count"); Element likeCountElement = document.selectFirst("div.article span.likes-count"); Element contentElement = document.selectFirst("div.article div.show-content"); if (titleElement != null) { System.out.println("标题:" + titleElement.text()); } if (authorElement != null) { System.out.println("作者:" + authorElement.text()); } if (timeElement != null) { System.out.println("发布时间:" + timeElement.text()); } if (wordCountElement != null) { System.out.println(wordCountElement.text()); } if (viewCountElement != null) { System.out.println(viewCountElement.text()); } if (commentCountElement != null) { System.out.println(commentCountElement.text()); } if (likeCountElement != null) { System.out.println(likeCountElement.text()); } if (contentElement != null && contentElement.text() != null) { System.out.println("正文长度:" + contentElement.text().length()); } } catch (Exception e) { e.printStackTrace(); } finally { if (webDriver != null) { //退出 chrome webDriver.quit(); } } 

和前文中的代码相比,就是下面的地方不一样

            ChromeOptions chromeOptions=new ChromeOptions();
            //设置 chrome 的无头模式
            chromeOptions.setHeadless(Boolean.TRUE);
            //启动一个 chrome 实例
            webDriver = new ChromeDriver(chromeOptions); 

这个参数决定了是否用无头模式来启动
将程序打包并且上传到 linux 服务器上,执行命令

java -jar -Dwebdriver.chrome.driver=/data/deploy/chromedriver spider_demo-0.0.1-SNAPSHOT.jar 

控制台会打印出下面的内容

标题:是什么支撑了淘宝双十一,没错就是它java编程语言。
作者:Java帮帮
发布时间:2018.08.29 14:49 字数 561 阅读 632 评论 0 喜欢 4 正文长度:655 

说明在 linux 用 java 通过 selenium 调用 chrome 访问这个网页成功了。如果没有设置上面的无头模式参数,那么执行的时候将会出现下面的提示

org.openqa.selenium.WebDriverException: unknown error: Chrome failed to start: exited abnormally
  (unknown error: DevToolsActivePort file doesn't exist)
  (The process started from chrome location /usr/bin/google-chrome is no longer running, so ChromeDriver is assuming that Chrome has crashed.)
  (Driver info: chromedriver=2.44.609551 (5d576e9a44fe4c5b6a07e568f1ebc753f1214634),platform=Linux 3.10.0-514.26.2.el7.x86_64 x86_64) (WARNING: The server did not provide any stacktrace information)
Command duration or timeout: 399 milliseconds
Build info: version: 'unknown', revision: 'unknown', time: 'unknown'
System info: host: 'iz2ze9kvzy03hms75m3jzlz', ip: '172.17.251.3', os.name: 'Linux', os.arch: 'amd64', os.version: '3.10.0-514.26.2.el7.x86_64', java.version: '1.8.0_171' Driver info: driver.version: ChromeDriver at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method) at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:62) at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45) at java.lang.reflect.Constructor.newInstance(Constructor.java:423) at org.openqa.selenium.remote.ErrorHandler.createThrowable(ErrorHandler.java:214) at org.openqa.selenium.remote.ErrorHandler.throwIfResponseFailed(ErrorHandler.java:166) at org.openqa.selenium.remote.JsonWireProtocolResponse.lambda$new$0(JsonWireProtocolResponse.java:53) at org.openqa.selenium.remote.JsonWireProtocolResponse.lambda$getResponseFunction$2(JsonWireProtocolResponse.java:91) at org.openqa.selenium.remote.ProtocolHandshake.lambda$createSession$0(ProtocolHandshake.java:122) at java.util.stream.ReferencePipeline$3$1.accept(ReferencePipeline.java:193) at java.util.Spliterators$ArraySpliterator.tryAdvance(Spliterators.java:958) at java.util.stream.ReferencePipeline.forEachWithCancel(ReferencePipeline.java:126) at java.util.stream.AbstractPipeline.copyIntoWithCancel(AbstractPipeline.java:498) at java.util.stream.AbstractPipeline.copyInto(AbstractPipeline.java:485) at java.util.stream.AbstractPipeline.wrapAndCopyInto(AbstractPipeline.java:471) at java.util.stream.FindOps$FindOp.evaluateSequential(FindOps.java:152) at java.util.stream.AbstractPipeline.evaluate(AbstractPipeline.java:234) at java.util.stream.ReferencePipeline.findFirst(ReferencePipeline.java:464) at org.openqa.selenium.remote.ProtocolHandshake.createSession(ProtocolHandshake.java:125) at org.openqa.selenium.remote.ProtocolHandshake.createSession(ProtocolHandshake.java:73) at org.openqa.selenium.remote.HttpCommandExecutor.execute(HttpCommandExecutor.java:136) at org.openqa.selenium.remote.service.DriverCommandExecutor.execute(DriverCommandExecutor.java:83) at org.openqa.selenium.remote.RemoteWebDriver.execute(RemoteWebDriver.java:548) at org.openqa.selenium.remote.RemoteWebDriver.startSession(RemoteWebDriver.java:212) at org.openqa.selenium.remote.RemoteWebDriver.<init>(RemoteWebDriver.java:130) at org.openqa.selenium.chrome.ChromeDriver.<init>(ChromeDriver.java:181) at org.openqa.selenium.chrome.ChromeDriver.<init>(ChromeDriver.java:168) at org.openqa.selenium.chrome.ChromeDriver.<init>(ChromeDriver.java:123) at com.yanggaochao.spider.SpiderDemoApplication.run(SpiderDemoApplication.java:34) at org.springframework.boot.SpringApplication.callRunner(SpringApplication.java:813) at org.springframework.boot.SpringApplication.callRunners(SpringApplication.java:797) at org.springframework.boot.SpringApplication.run(SpringApplication.java:324) at org.springframework.boot.SpringApplication.run(SpringApplication.java:1260) at org.springframework.boot.SpringApplication.run(SpringApplication.java:1248) at com.yanggaochao.spider.SpiderDemoApplication.main(SpiderDemoApplication.java:21) at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62) at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) at java.lang.reflect.Method.invoke(Method.java:498) at org.springframework.boot.loader.MainMethodRunner.run(MainMethodRunner.java:48) at org.springframework.boot.loader.Launcher.launch(Launcher.java:87) at org.springframework.boot.loader.Launcher.launch(Launcher.java:50) at org.springframework.boot.loader.JarLauncher.main(JarLauncher.java:51) 

这样,我们就可以在我们的爬虫系统里面采用浏览器的方式下载网页,实现所见即所得的下载效果。再也不用担心动态渲染的网页内容无法下载了。



作者:阿土伯已经不是我
链接:https://www.jianshu.com/p/b2609ed57f07
来源:简书
简书著作权归作者所有,任何形式的转载都请联系作者获得授权并注明出处。

猜你喜欢

转载自www.cnblogs.com/ppp1314520818/p/11300348.html