首页 > 其他分享 >(转)goquery HTML解析

(转)goquery HTML解析

时间:2023-03-13 15:26:05浏览次数:52  
标签:lang zh Find goquery HTML div 解析 选择器

原文:https://www.jiangguo.net/c/447/pd9.html

goquery将jQuery的语法和特性引入进来,所以可以更灵活地选择采集内容的数据项,就像jQuery那样的方式来操作DOM文档,使用起来非常的简便。goquery主要的结构:

0

type Document struct {
	*Selection
	Url      *url.URL
	rootNode *html.Node
}

0

Document 嵌入了Selection 类型,因此,Document 可以直接使用 Selection 类型的方法。我们可以通过下面四种方式来初始化得到*Document对象。

0

func NewDocumentFromNode(root *html.Node) *Document 
func NewDocument(url string) (*Document, error) 
func NewDocumentFromReader(r io.Reader) (*Document, error) 
func NewDocumentFromResponse(res *http.Response) (*Document, error)

0

Selection 是重要的一个结构体,解析中最重要,最核心的方法方法都由它提供。

0

type Selection struct {
	Nodes    []*html.Node
	document *Document
	prevSel  *Selection
}

0

下面我们开始了解下怎么使用goquery:

0

  • 首先,要确定已经下载安装这个第三方包:go get github.com/PuerkitoBio/goquery
  • 接下来在代码中导入包:import "github.com/PuerkitoBio/goquery"

0

goquery的主要用法是选择器,需要借鉴jQuery的特性,多加练习就能很快掌握。限于篇幅,这里只能简单介绍了goquery的大概情况。

0

goquery可以直接发送url请求,获得响应后得到HTML代码。但goquery主要擅长于HTML代码分析,而Colly在爬虫抓取管理调度上有优势,所以下面以Colly作为爬虫框架,goquery作为HTML分析器,看看怎么抓取并分析页面内容:

0

package main
import (
	"bytes"
	"fmt"
	"log"
	"net/url"
	"time"
	"github.com/PuerkitoBio/goquery"
	"github.com/gocolly/colly"
)
func main() {
	urlstr := "https://news.baidu.com"
	u, err := url.Parse(urlstr)
	if err != nil {
		log.Fatal(err)
	}
	c := colly.NewCollector()
	// 超时设定
	c.SetRequestTimeout(100 * time.Second)
	// 指定Agent信息
	c.UserAgent = "Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/63.0.3239.108 Safari/537.36"
	c.OnRequest(func(r *colly.Request) {
		// Request头部设定
		r.Headers.Set("Host", u.Host)
		r.Headers.Set("Connection", "keep-alive")
		r.Headers.Set("Accept", "*/*")
		r.Headers.Set("Origin", u.Host)
		r.Headers.Set("Referer", urlstr)
		r.Headers.Set("Accept-Encoding", "gzip, deflate")
		r.Headers.Set("Accept-Language", "zh-CN, zh;q=0.9")
	})
	c.OnHTML("title", func(e *colly.HTMLElement) {
		fmt.Println("title:", e.Text)
	})
	c.OnResponse(func(resp *colly.Response) {
		fmt.Println("response received", resp.StatusCode)
		// goquery直接读取resp.Body的内容
		htmlDoc, err := goquery.NewDocumentFromReader(bytes.NewReader(resp.Body))
		// 读取url再传给goquery,访问url读取内容,此处不建议使用
		// htmlDoc, err := goquery.NewDocument(resp.Request.URL.String())
		if err != nil {
			log.Fatal(err)
		}
		// 找到抓取项 <div class="hotnews" alog-group="focustop-hotnews"> 下所有的a解析
		htmlDoc.Find(".hotnews a").Each(func(i int, s *goquery.Selection) {
			band, _ := s.Attr("href")
			title := s.Text()
			fmt.Printf("热点新闻 %d: %s - %s\n", i, title, band)
			c.Visit(band)
		})
	})
	c.OnError(func(resp *colly.Response, errHttp error) {
		err = errHttp
	})
	err = c.Visit(urlstr)
}

0

上面代码中,goquery先通过 goquery.NewDocumentFromReader 生成文档对象htmlDoc。有了htmlDoc就可以使用选择器,而选择器的目的主要是定位:htmlDoc.Find(".hotnews a").Each(func(i int, s *goquery.Selection),找到文档中的。

0

有关选择器Find()方法的使用语法,是不是有些熟悉的感觉,没错就是jQuery的样子。

0

在goquery中,常用大概有以下选择器:

0

选择器说明
Find(“div[lang]“) 筛选含有lang属性的div元素
Find(“div[lang=zh]“) 筛选lang属性为zh的div元素
Find(“div[lang!=zh]“) 筛选lang属性不等于zh的div元素
Find(“div[lang¦=zh]“) 筛选lang属性为zh或者zh-开头的div元素
Find(“div[lang*=zh]“) 筛选lang属性包含zh这个字符串的div元素
Find(“div[lang~=zh]“) 筛选lang属性包含zh这个单词的div元素,单词以空格分开的
Find(“div[lang$=zh]“) 筛选lang属性以zh结尾的div元素,区分大小写
Find(“div[lang^=zh]“) 筛选lang属性以zh开头的div元素,区分大小写

0

parent>child选择器 如果我们想筛选出某个元素下符合条件的子元素,我们就可以使用子元素筛选器,它的语法为Find("parent>child"),表示筛选parent这个父元素下,符合child这个条件的最直接(一级)的子元素。

0

prev+next相邻选择器 假设我们要筛选的元素没有规律,但是该元素的上一个元素有规律,我们就可以使用这种下一个相邻选择器来进行选择。

0

prev~next选择器 有相邻就有兄弟,兄弟选择器就不一定要求相邻了,只要他们共有一个父元素就可以。

0

Colly + goquery 是抓取网络内容的利器,使用上极其方便。如今动态渲染的页面越来越多,爬虫们或多或少都需要用到headless browser来渲染待爬取的页面,这里推荐chromedp,开源网址:https://github.com/chromedp/chromedp

标签:lang,zh,Find,goquery,HTML,div,解析,选择器
From: https://www.cnblogs.com/liujiacai/p/17211544.html

相关文章

  • HTML中的颜色单位:RGB值
    颜色单位:在css中可以直接使用颜色名来设置各种颜色如:red、green、blue......但是在css中直接使用颜色名来命名是非常不方便的-RGB值:......
  • 【漏洞复现】Apache HTTPD 换行解析漏洞 (CVE-2017-15715)
    ApacheHTTPD换行解析漏洞(CVE-2017-15715)0x01漏洞描述ApacheHTTPD是一款HTTP服务器,它可以通过mod_PHP来运行PHP网页。其2.4.0~2.4.29版本中存在一个解析漏洞,在解......
  • HTML中的长度单位:像素、百分比、em、rem
    长度单位:像素-屏幕(显示器)实际上是由一个一个的小点点构成的-不同屏幕的像素大小是不同的,像素越小的屏幕显示的效果越清晰-所以同样的2......
  • HTML5简介与基础骨架
    HTML5简介与基础骨架 HTML5介绍HTML5是用来描述网页的一种语言,被称为超文本标记语言.用HTML5编写的文件,后缀以.html结尾HTML是一种标记语言,标记语言是一套标记标......
  • HTML-邮件
    <!doctypehtml><html><head><title>收件箱</title><linkrel="stylesheet"href="https://cdn.staticfile.org/twitter-bootstrap/3.3.7/css/bootstrap.min.......
  • HTML-示例)
    <!doctypehtml><html><head><title>Bootstrap实例-堆叠的水平</title><linkrel="stylesheet"href="https://cdn.staticfile.org/twitter-bootstrap/3.3.7/css/boo......
  • HTML 邮箱
    <html><head><title>邮件</title><linkrel="stylesheet"href="https://cdn.staticfile.org/twitter-bootstrap/3.3.7/css/bootstrap.min.css">......
  • HTML 示例代码
    <html><head><title>邮件</title><linkrel="stylesheet"href="https://cdn.staticfile.org/twitter-bootstrap/3.3.7/css/bootstrap.min.css">......
  • html的规范
    1.所有的html标签都必须使用尖括号包裹起来,比如:<hr>2.html标签通常是成对出现的,双标签必须要有开始标签和结束标签,比如:<p></p>3.html标签不区分大小写(建议都使用小......
  • 如何禁用 HTML 或 CSS 中文本区域的大小调整
    在这个快速提示中,我们将向您展示2种不同的方法来禁用调整a的textarea大小,以防您不希望用户能够以这种方式控制它。这是一个相对较快的过程,只需一些使用resizeCSS属性......