我正在编写一个使用Node的Web抓取工具,并考虑使用像Cheerio或JSDom这样的模块将HTML解析为DOM以获取一组URL。但是,我有一个必要的特定功能。
我的目标是构建一个可以在网站上抓取多个类似页面的刮刀,以获取一些关键信息。但是,我有一些包含这些信息的示例数据,我想使用它们为这些页面动态构建模型,然后使用该模型抓取其余部分。
澄清一下,如果网站上有三个页面,每个页面都包含不同的产品:
第1页:
<html>
<body>
<h1>Product 1</h1>
<p>Desc</p>
<small>$2.05</small>
</body>
</html>
第2页:
<html>
<body>
<h1>Product 2</h1>
<p>Desc</p>
<small>$8.05</small>
</body>
</html>
第3页:
<html>
<body>
<h1>Product 3</h1>
<p>Desc</p>
<small>$5.07</small>
</body>
</html>
说我已经拥有第一个产品的数据(我知道产品名称,描述和价格)。我想使用第一页获取每个元素的选择器,然后使用这些选择器从其他页面中获取数据。
鉴于DOM中标记的内容,我如何获得该元素的CSS选择器?例如:
<html>
<body>
<h1>Hello world</h1>
</body>
</html>
如何为Cheerio / JSDom提供类似&#34; Hello world&#34;的字符串。并让它返回元素所在的DOM中的CSS Selector?
有没有一种简单的方法可以做到这一点(包括使用另一个框架),或者只是循环遍历整个DOM对象并单独检查每个元素的值?
答案 0 :(得分:0)
使用SAX模型完成此操作最简单,最有效,但可以应用于DOM遍历。
var match, path = [];
parser.on('start', function(tag) { currentPath.push(tag); });
parser.on('end', function(tag) { currentPath.pop(); });
parser.on('text', function(text) {
if (!match && text === 'Hello world') {
match = path.join('/');
}
});
如果你还需要构建DOM,你可以使用XPath来查找节点(内部只循环整个DOM),然后循环父节点。
var path = [];
var node = document.xpath('//*[.="Hello world"]')[0];
do {
path.push(node.tag);
} while (node = node.parent);
var match = path.reverse().join('/');
第二种方法效率低得多,特别是如果要查找许多不同的节点。 SAX方法可以一次性覆盖所有这些方法,但可能会因格式错误的输入而受到影响,具体取决于解析器的实现。
对于CSS选择器,请将'/'
替换为' > '
。