我试图从网站的 5 个不同的 div 中抓取文本,但问题是我无法使用类名或 ID。我观察到这些 div 的共同点是,这 5 个不同 div 的文本都封装在一个 span 属性中,并且该属性仅在我需要从中抓取文本的地方使用。到目前为止,这是我的代码,但我被困在抓取的开始:
const fs = require("fs/promises");
const express = require ("express");
const cors = require("cors");
const _ = require("lodash"); //pick a random item from an array
const { v4: uuid } = require("uuid"); //object destructuring; uuid to generate unique id
const { sample } = require("lodash");
const cheerio = require("cheerio");
const axios = require("axios");
async function performScraping(){
const app = express();
app.use(express.json()); //support json
app.use(express.cors());
//Downloading the target web page
//by performing an HTTP GET request in Axios
const axiosResponse = await axios.request({
method: "GET",
url: "https://wsa-test.vercel.app/",
headers: {
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/108.0.0.0 Safari/537.36"
}
});
//parsing the HTML source of the target web page with Cheerio
const $ = cheerio.load(axiosResponse.data);
//initializing the data structures
//that will contain the scraped data
//scraping
const descriptions = document.getElementsByTagName("span");
for(desc of descriptions){
}
app.listen(3000, () => console.log("API Server is running..."));
}
所以,tldr,我真正想要的是使用 Cheerio 提取文章的标题和简短描述,两者都在 span 属性中。我还附上了 HTML 图像和原因中的跨度:
我尝试使用不同的 DOM 元素,但没有成功。
您将无法通过直接请求静态 HTML 来获取该数据,因为您想要的数据是由 JS 异步加载的。始终在浏览器中检查
view-source:
或打印 HTML axios 为您提供的信息,以确保数据存在,而不是开发工具,后者显示页面加载后由 JS 加载的元素。
你可以使用 Puppeteer 来获取它:
const puppeteer = require("puppeteer"); // ^21.2.1
const url = "https://wsa-test.vercel.app/";
let browser;
(async () => {
browser = await puppeteer.launch();
const [page] = await browser.pages();
await page.goto(url, {waitUntil: "domcontentloaded"});
const sel = '[class^="group"]';
await page.waitForSelector(sel);
const data = await page.$$eval(sel, els =>
els.map(e => ({
name: e.querySelector("div").textContent,
desc: e.querySelector("div:nth-child(2)").textContent
}))
);
console.log(data);
})()
.catch(err => console.error(err))
.finally(() => browser?.close());