这是一个问题,我总是在浏览器中获得特定的XPath。
假设我要从Google图片搜索或Pinterest等网站中提取所有图片。当我使用Inspect element
然后使用copy XPath
获取图像的XPath时,它会给我一些如下内容:
//*[@id="rg_s"]/div[13]/a/img
我是通过Google搜索中的图片得到的。当我想在我的spider
中使用它时,我使用了Selector
和HtmlXPathSelector
以及以下XPath,但它们都不起作用!
//*[@id="rg_s"]/div/a/img
//div[@id="rg_s"]/div[13]/a/img
//[@class="rg_di rg_el"]/a/img #i change this based on the raw html of page
#hxs.select(xpath).extract()
#Selector(response).xpath('xpath')
.
.
我已经阅读了很多问题,但是我找不到如何在Scrapy中使用从Web浏览器获取的XPath的一般答案。
答案 0 :(得分:2)
通常,盲目地遵循浏览器关于如何定位元素的建议是不安全可靠的。
首先,开发人员工具生成的XPath表达式通常是绝对的 - 从所有父项的父项html
标记开始,这使得它更依赖于页面结构(好吧,{{1} }也可以根据firebug
属性制作表达式。
此外,您在浏览器中看到的HTML代码与Scrapy收到的HTML代码差异很大,因为网站页面加载的异步性和浏览器中动态执行的javascript。 id
不是浏览器,"看到"只有页面的初始HTML代码,在" dynamic"之前。一部分。
相反,检查Scrapy在响应中真正具有的内容:打开Scrapy Shell
,检查响应并调试XPath表达式和CSS选择器:
Scrapy
以下是我为谷歌图片搜索所获得的内容:
$ scrapy shell https://google.com
>>> response.xpath('//div[@id="myid"]')
...
答案 1 :(得分:1)
从浏览器中的插入点生成的XPath必然是脆弱的,因为有许多不同的XPath表达式可以到达任何给定节点,JavaScript可以修改HTML,并且浏览器不知道您的意图。
对于您提供的示例,
//*[@id="rg_s"]/div[13]/a/img
第13 div
特别容易破损。
尝试找到更接近目标的唯一识别特征。唯一的@id
属性是理想的,或者@class
唯一标识您的目标或目标的近祖先也可以正常工作。
例如,对于Google图片搜索,类似以下XPath
//div[@id='rg_s']//img[@class='rg_i']"
将在包含搜索结果的rg_i
中选择所有类div
的图片。
如果您愿意放弃复制粘贴方法并学习足够的XPath来概括您的选择,那么您将获得更好的结果。当然,标准免责声明适用于演示的变化,也需要更新刮削技术。使用直接API调用会更加健壮(也适当)。