# jWebSpider **Repository Path**: devaper/j-web-spider ## Basic Information - **Project Name**: jWebSpider - **Description**: 基于实体映射的JavaWeb爬虫 - **Primary Language**: Java - **License**: Apache-2.0 - **Default Branch**: master - **Homepage**: None - **GVP Project**: No ## Statistics - **Stars**: 0 - **Forks**: 0 - **Created**: 2022-11-21 - **Last Updated**: 2023-07-24 ## Categories & Tags **Categories**: Uncategorized **Tags**: Java ## README # jWebSpider > jWebSpider是一款基于实体映射的JavaWeb爬虫工具,HTML解析库使用Jsoup ## 使用方法 1. ```git git clone https://gitee.com/horizon007/j-web-spider.git ``` 2. 创建测试类、测试方法 3. 按照示例修改并运行程序 ## 使用介绍 在jWebSpider中,每个属性都有一个Context ### WebSpider 该类型为主要的功能类 ```java // 创建实例 WebSpider webSpider = new WebSpider(); // 设置线程池,内部是以多线程方式执行的,每次使用DEEP转换器都会在新线程执行 // 如果没有设置,内部会自动初始化一个固定尺寸为10的线程池 webSpider.setExecutorService(Executors.newFixedThreadPool(10)); // 通过一个数据提供者初始化,WebProvider通过加载对应URL的HTML内容转化为Document webSpider.init(new WebProvider("url")); // 将第一个参数查询到的所有元素作为Item[]的上下文,每一个元素创建一个Item进行解析 List items = webSpider.parse("ul > li", Item.class); ``` ### @Context 注解 | 属性 | 类型 | 默认值 | 介绍 | | ----------- | ----------- | ---------------- | -------------------------------------------------- | | selector | String | "" | CSS选择器,基于当前对象所处于的上下文进行查找元素作为当前属性上下文,如果留空使用当前对象的上下文 | | transformer | Transformer | Transformer.TEXT | 转换器,将当前上下文中的元素以什么形式填充到属性中 | ### Transformer > 如果自带的一些转换器不满足需求,可以使用ELEMENT转换器,或者直接创建自己的转换器:实现ValueTransformer接口,修改Transformer枚举类放入自己的转换器实例 #### TEXT 默认使用的转换器,将当前上下文中第一个元素的文本内容填充到属性 #### HTML 将当前上下文中第一个元素的HTML内容填充到属性 #### ATTR 将当前上下文中第一个元素的Attribute填充到属性。 通过 `AttributeTransformer.AttributeName` 注解指定Attribute名称,未指定时使用属性名称 如果属性类型是 `Map` 会将所有的Attribute填充到属性 #### ELEMENT > 该转换器适用于所有转换器都无法满足需求时,需要直接拿到Element获取数据的清空 将当前上下文填充到属性 如果属性类型为 `List` 、`Element[]` 、`Elements` 时,可以获取当前上下文的所有元素 如果属性类型为 `Element` 时,获取当前上下文的第一个元素 #### DEEP 通常用于解析嵌套对象 如果属性是自定义类型时,需要深入解析,那么使用该转换器设置类型的上下文,此时上下文可能为多个元素,为每个元素创建一个该类型的实例进行解析 ### DocumentProvider > 文档提供者,为WebSpider提供文档数据。 > > 所有Provider属性如果没有在构造期内要求提供,都不是必须设置的 #### StringProvider 基于字符串的提供者对象,负责将字符串HTML内容转换为Document #### WebProvider 基于URL的提供者对象,负责通过HttpConnection将远程页面转换为Document 该提供者只能获取静态页面数据,如果页面的数据是由JS渲染的,那么无法获取 | 属性 | 类型 | 说明 | | ---------- | --------------------- | ----------------------------------- | | timeout | int | 获取页面的超时时间,毫秒。默认为30秒 | | userAgent | String | 设置用户代理。含有默认值 | | headers | Map\ | 设置请求头。含有默认值 | | cookies | Map\String, String> | 设置Cookie | | customizer | Consumer\ | 自定义器,在请求之前会调用该自定义器自定义HttpConnection | #### HtmlUnitProvider 使用HtmlUnit模拟一个浏览器,抓取由JS渲染的页面。每次启动一个WebClient时成本较高,所以内部包含的WebClient不会自动关闭,需要手动调用 `close` 进行关闭。如果需要爬取多个页面,用完后再关闭该Provider | 属性 | 类型 | 说明 | | -------------- | -------------------------------- | ------------------------------------------------------ | | timeout | int | 加载页面的超时时间,毫秒。默认为30秒 | | browserVersion | BrowserVersion | 需要HtmlUnit模拟的浏览器 | | headers | Map\ | 请求头 | | customizer | Consumer\ | 自定义器,在WebClient第一次启动时会执行该自定义器进行自定义 | | pageCustomizer | BiConsumer\ | 页面自定义器,在WebClient获取到页面后执行该自定义器进行自定义页面,通常可以用于模拟表单操作等... | | delay | long | 加载页面后等待多少毫秒再进行解析,抓取动态页面时必须等待,等待页面渲染完后再进行解析 | ## 简单例子 ```html
  • 用户1

    user1

    • 这是我给用户2的备注
  • 用户2

    user2

    • 这是我给用户1的备注
``` ```java // 为获取到的所有li元素创建Li对象,并将对应的li元素作为这个Li对象的上下文 List
  • liList = webSpider.parse("ul#list > li", Li.class); public class Li { // selector属性没有填写,那么属性的上下文使用Li对象的,也就是li元素 // 使用ATTR转换器取出元素属性,如果没有指定名称,使用属性名 @Context(transformer = Transformer.ATTR) // 指定需要取出的元素属性名称 @AttributeTransformer.AttributeName("data-userid") private String userId; // 基于当前上下文(也就是li元素),查询.username,使用默认的TEXT转换器取出文本内容 @Context(selector = ".username") private String username; // 同上 @Context(selector = ".nickname") private String nickname; // 深入解析,同parse方法,为每个li都创建一个Friend对象 @Context(selector = "ul.friends > li", transformer = Transformer.DEEP) private List friends; } public class Friend { @Context(transformer = Transformer.ATTR) @AttributeTransformer.AttributeName("data-userid") private String userId; @Context private String remark; } ```