记一次Go爬取小说

本文记录了一次使用Go语言进行网络小说爬取的实战经历,目标站点为m.999xs.com。分析了小说网页的结构,发现章节被分页并组织成目录。设计了BookerWorker、DirectoryWorker、ChapterWorker和PageWorker四个工作组件来实现自顶向下的爬取策略。执行过程中注意到了可能对网站造成的非正常访问,并表达了歉意。
摘要由CSDN通过智能技术生成

原始需求

原始需求:https://m.999xs.com/files/article/html/69/69208/index.html
在线看不方便,而且浏览器还有强制广告
ps: 在实战过程中,对m.999xs.com造成了非正常的访问,由此带来的服务端压力和问题在此说声Sorry。

分析

打开链接,我们发现一本被分成了很多章节,在菜单目录中20章节为一页。
每一章节又被分为多个子页。
分级关系描述如下:
page1,page2…->Chapter
Chapter1,Chapter2…(<=20)->Directory
Directory1,Directory2…->Book

实战

非常自然的,我们自顶向下的设计思路有出来了。
在这里插入图片描述

Workers

定义一个workers目录,按照分析过程中的层级关系,添加如下4个worker

BookerWorker

package workers

import (
	"io/ioutil"
	"log"
	"net/http"
	"os"
	"regexp"
	"strings"
)

/*
	Booker
	职责:
		1. 获取Title,书名即最终的文本文件名
		2. 初始化 DirectoryWorker
		3. 接收最终 DirectoryWorker 和 PageWorker 解析出来的内容,并生成文本文件
*/

/*
	BookWorker.Contents的描述
	[]byte					========>Chapter				========>每章中的内容,每个章节包含多页,在章节中合并,章节=章节名+页1+页2+...
	[][]byte				========>Directory				========>每个菜单目录,[章节1,章节2...]
	[][][]byte				========>Book					========>整本书,[目录1,目录2...]
*/

type BookWorker struct {
	DefaultUrl      string               //初始url,https://m.999xs.com/files/article/html/69/69208/index.html
	Contents        [][][]byte           //index页面获取到的html流,
	FileName        string               //书名
	PageContentChan chan PageContentItem //接收处理的Page结果
	Host            string
}

type PageContentItem struct {
	Content    []byte
	PageNum    int
	SubPageNum int
}

func (b *BookWorker) Run() error {
	defer log.Println("booker worker down")
	//initial Receiver
	downchan := make(chan int)
	go b.ReceiveContents(downchan)

	resp, err := http.DefaultClient.Get(b.Host + b.DefaultUrl)
	if err != nil {
		return err
	}
	buf, err := ioutil.ReadAll(resp.Body)
	if err != nil {
		return err
	}

	b.getTitle(buf)

	err = b.StartDirectoryWorker(buf, b.DefaultUrl)
	if err != nil {
		return err
	}
	close(b.PageContentChan)
	<-downchan

	return nil
}

func (b *BookWorker) getTitle(contents []byte) {
	//处理BookTitle
	titlepat := `id="
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值
>