一、介绍
WebMagic是基于Java的开源网络爬虫框架,可以快速、灵活、高效地爬行和提取网络数据。WebMagic支持多线程、分布式、自动重试等特点,使用方便。
二、优点1. 快速:使用NIO框架,可以有效地进行网络通信,提高爬虫效率。
2. 灵活性:支持自定义爬行规则,能够适应不同的网站结构和数据格式。
3. 高效:采用异步非阻塞方式,支持多线程和分布式部署,提高爬虫的效率和稳定性。
4. 易用:提供简单易懂的API,开发者可以快速上手。
三、四大组件1. Downloader(页面下载组件):负责下载网页,可选择不同的下载器。
2. PageProcessor(页面处理组件):处理下载的页面,包括分析页面、提取有用数据等。
3. Pipeline(结果输出组件):负责对 PageProcessor 处理后的结果可以存储在文件、数据库、搜索引擎等地方。
4. Scheduler(URL管理器):用于管理待抓取的事项 URL 为了保证数据的准确性和抓取效率,队列还支持使用Redis等分布式存储来实现分布式抓取。
四、使用场景1. 数据采集:可帮助企业或个人在数据挖掘、业务分析等领域快速、高效地获取网络上的数据。
2. 网站监控:可监控新闻、价格、商品等特定网站的变化,帮助企业及时了解市场动态。
3. 网络捕获:WebMagic可以模拟人类浏览器从网站捕获页面和内容,在网站的各个层次上收集信息和数据,从而构建完整的产品目录和分类。
五、注意事项1. 避免反爬虫机制:一些网站将设置反爬虫机制,需要通过模拟浏览器行为和使用代理来避免。
2. 控制爬行速度:爬行速度过快会给网站带来负担,也容易被网站禁止IP。
六、补充内容1. 多语言支持:WebMagic有Python、Scala等语言版本,可以适应不同开发者的需求。
2. 爬虫任务调度:WebMagic可与Quartz等任务调度框架相结合,实现定期爬取数据的功能。
3. WebMagic支持多线程:可利用多核CPU提高爬虫效率。
4. WebMagic支持多种功能:Cookie、代理等功能,可模拟登录,避免反爬等操作。
5. WebMagic支持MySQL等多种格式的数据存储、Redis、Elasticsearch等,便于后续数据处理。
6. 处理异常情况:WebMagic可以处理一些异常情况,如页面404、分析错误,提高爬虫的健壮性。
七、实际场景1. 案例一
(1) 场景
爬一个简单的页面。
(2) 代码
pom.xml
<!--web magic--><dependency> <groupId>us.codecraft</groupId> <artifactId>webmagic-core</artifactId> <version>0.8.0</version></dependency><dependency> <groupId>us.codecraft</groupId> <artifactId>webmagic-extension</artifactId> <version>0.8.0</version></dependency>
Webmagiccase1.java
/** * 简单的WebMagic爬行页面案例 * * @author wxy * @since 2023-05-30 */public class Webmagiccase1 { public static void main(String[] args) { String[] urls = new String[]{ "https://blog.csdn.net/qq_45871274/article/details/129162237" }; new MyTask().execute(urls); }}
MyTask.java
import us.codecraft.webmagic.Spider;/** * 爬取任务 * * @author wxy * @since 2023-05-30 */public class MyTask { public void execute(String... url) { Spider spider = Spider // 指定页面分析器 .create(new MyProcessor()) // 指定爬行结果的处理器 .addPipeline(new MyPipeline()) .addUrl(url) // 创建3个线程 .thread(3); ///异步爬行 spider.start(); }}
PageProcessor.java
import org.jsoup.Jsoup;import org.jsoup.nodes.Document;import org.jsoup.nodes.Element;import org.jsoup.select.Elements;import us.codecraft.webmagic.Page;import us.codecraft.webmagic.Site;import us.codecraft.webmagic.processor.PageProcessor;import java.util.ArrayList;import java.util.List;/** * 页面解析 * * @author wxy * @since 2023-05-30 */public class MyProcessor implements PageProcessor { @Override public void process(Page page) { String pageStrHtml = page.getHtml().get(); Document pageHtmlDocument = Jsoup.parse(pageStrHtml); List<String> contentList = new ArrayList<>(); // 获取文章标题 Elements title = pageHtmlDocument .select("h1[id=articleContentId]"); // 写入标题文本内容 page.putField("title", title.text()); // 获取文章内容 Elements contents = pageHtmlDocument .select("p[id=content_views]"); for (Element content : contents) { for (Element element : content.children()) { // 写入每个标签的文本内容 contentList.add(element.text()); } // 写入文章全部文本内容 page.putField("contents", contentList); } } @Override public Site getSite() { ////在爬取页面时设置http请求 比如编码,HTTP头,、超时、重试策略 等、代理等 return Site.me() // 重试次数 .setRetryTimes(3) // 间隔时间 .setSleepTime(100) // 设置超时间 .setTimeOut(10000); }}
MyPipeline.java
import us.codecraft.webmagic.ResultItems;import us.codecraft.webmagic.Task;import us.codecraft.webmagic.pipeline.Pipeline;import java.util.List;/** * 爬行结果的处理 * * @author wxy * @since 2023-05-30 */public class MyPipeline implements Pipeline { @Override public void process(ResultItems resultItems, Task task) { // 打印文章标题文本内容(在这里分析并保存到数据库) System.out.println(文章标题: "); System.out.println(resultItems.get("title").toString()); // 打印文章内容文本内容 List<String> contents = resultItems.get("contents"); System.out.println(文章内容: "); for (String content : contents) { System.out.println(content); } }}
最后,输出爬行文章的标题和内容:
