在 Bun 环境下使用 TypeScript 进行网页解析,除了 axios 和 cheerio 之外,还有其他一些解决方案。下面介绍几种常见的替代方案,并比较其优缺点。
1. 使用 node-fetch 和 jsdom
功能介绍
node-fetch:一个轻量级的 HTTP 请求库,类似于浏览器中的fetch。jsdom:一个用 JavaScript 实现的基于 DOM 的 HTML 解析和操作库,它可以在 Node. Js 环境中模拟一个完整的浏览器 DOM 环境。
安装
bun add node-fetch jsdom实现示例
import fetch from 'node-fetch';
import { JSDOM } from 'jsdom';
const url = 'https://example.com';
async function fetchHTML(url: string): Promise<string> {
const response = await fetch(url);
const data = await response.text();
return data;
}
async function parseHTML(html: string): Promise<void> {
const dom = new JSDOM(html);
const document = dom.window.document;
// 提取所有链接
const links = Array.from(document.querySelectorAll('a')).map(anchor => anchor.href);
console.log('Found links:', links);
// 提取所有h1标签的文本
const headings = Array.from(document.querySelectorAll('h1')).map(h1 => h1.textContent);
console.log('Found headings:', headings);
}
async function main() {
const html = await fetchHTML(url);
await parseHTML(html);
}
main();优缺点
- 优点:
jsdom提供了一个完整的 DOM 环境,可以执行和操作 JavaScript。- 更加接近浏览器行为,支持复杂的 DOM 操作和事件处理。
- 缺点:
- 相对较重,性能可能比
cheerio差一些。 - 内存占用较高,适合处理较少的页面而非大规模爬取。
- 相对较重,性能可能比
2. 使用 got 和 htmlparser2
功能介绍
got:一个功能丰富的 HTTP 请求库,支持 Promise 和异步操作,并具有更好的错误处理机制。htmlparser2:一个高效的 HTML 解析库,可以解析 HTML 并生成 DOM 树。
安装
bun add got htmlparser2实现示例
import got from 'got';
import { parseDocument } from 'htmlparser2';
import { selectAll, selectOne } from 'css-select';
import { DomUtils } from 'htmlparser2';
const url = 'https://example.com';
async function fetchHTML(url: string): Promise<string> {
const response = await got(url);
return response.body;
}
async function parseHTML(html: string): Promise<void> {
const document = parseDocument(html);
// 提取所有链接
const links = selectAll('a', document).map(element => DomUtils.getAttributeValue(element, 'href'));
console.log('Found links:', links);
// 提取所有h1标签的文本
const headings = selectAll('h1', document).map(element => DomUtils.textContent(element));
console.log('Found headings:', headings);
}
async function main() {
const html = await fetchHTML(url);
await parseHTML(html);
}
main();优缺点
- 优点:
got提供了更丰富的配置选项和更好的错误处理。htmlparser2解析速度快,内存占用低。
- 缺点:
htmlparser2操作相对底层,操作 DOM 不如cheerio或jsdom直观。- 需要手动管理和操作 DOM 节点。
3. 使用 puppeteer
功能介绍
puppeteer:一个基于 Headless Chrome 的 Node 库,提供了一个高层次的 API,用于控制浏览器进行自动化操作,如页面导航、截图、生成 PDF 等。
安装
bun add puppeteer实现示例
import puppeteer from 'puppeteer';
const url = 'https://example.com';
async function fetchHTML(url: string): Promise<string> {
const browser = await puppeteer.launch();
const page = await browser.newPage();
await page.goto(url);
const html = await page.content();
await browser.close();
return html;
}
async function parseHTML(html: string): Promise<void> {
const dom = new JSDOM(html);
const document = dom.window.document;
// 提取所有链接
const links = Array.from(document.querySelectorAll('a')).map(anchor => anchor.href);
console.log('Found links:', links);
// 提取所有h1标签的文本
const headings = Array.from(document.querySelectorAll('h1')).map(h1 => h1.textContent);
console.log('Found headings:', headings);
}
async function main() {
const html = await fetchHTML(url);
await parseHTML(html);
}
main();优缺点
- 优点:
- 支持完整的浏览器渲染,能够处理复杂的 JavaScript 渲染页面。
- 提供了强大的 API,适用于复杂的网页自动化任务。
- 缺点:
- 资源消耗大,性能相对较低,不适合高并发的爬取任务。
- 安装和运行需要更多的系统资源。
综合比较
| 方案 | 优点 | 缺点 |
|---|---|---|
| axios + cheerio | 简单、快速,API 友好,适用于大多数简单的网页爬取任务。 | 不能执行 JavaScript,无法处理动态内容。 |
| node-fetch + jsdom | 提供完整的 DOM 环境,支持复杂的 DOM 操作和事件处理。 | 性能较低,内存占用较高,适合处理较少的页面。 |
| got + htmlparser 2 | 高效、内存占用低,got 的请求功能强大。 | 操作 DOM 相对底层,不如 cheerio 或 jsdom 直观。 |
| puppeteer | 支持完整的浏览器渲染,能够处理动态内容和复杂的网页自动化任务。 | 资源消耗大,性能低,不适合高并发爬取任务。 |
每种方案都有其适用的场景和优缺点,选择合适的方案取决于你的具体需求和使用环境。如果需要处理大量静态页面,axios 和 cheerio 是一个不错的选择;如果需要处理动态内容,puppeteer 会更加适用。