我将展示我的确切示例,但我认为这对于您必须抓取一个其 url 将您定向到不同页面的页面的一般情况可能是一个问题。
我要抓取的页面位于此网址http://www.oxygenboutique.com/Shoes-All.aspx下,但不是您直接点击此链接时获得的页面。我想要的是你点击“显示全部”时看到的那个。
我怎样才能让我的蜘蛛从我想要的那个开始?
谢谢
我将展示我的确切示例,但我认为这对于您必须抓取一个其 url 将您定向到不同页面的页面的一般情况可能是一个问题。
我要抓取的页面位于此网址http://www.oxygenboutique.com/Shoes-All.aspx下,但不是您直接点击此链接时获得的页面。我想要的是你点击“显示全部”时看到的那个。
我怎样才能让我的蜘蛛从我想要的那个开始?
谢谢
“显示全部”链接是对网页上的 Javascript 函数的调用,它的调用方式如下:
__doPostBack('ctl00$ContentPlaceHolder1$PGN01','')
我的主要浏览器是 Firefox,它有很多你可以使用的插件。我使用了“Web Developer”插件。
在具有该页面的选项卡中,然后执行以下操作:让鼠标光标悬停在显示全部链接上。然后右键单击并选择“Web 开发人员”>“信息”>“查看 Javascript Alt+Shift+J” Firefox 将打开一个新选项卡,其中包含该页面正在使用的所有 Javascript。
在选项卡中 - 快速搜索找到 __doPostBack 函数,其编码如下:
function __doPostBack(eventTarget, eventArgument) {
if (!theForm.onsubmit || (theForm.onsubmit() != false)) {
theForm.__EVENTTARGET.value = eventTarget;
theForm.__EVENTARGUMENT.value = eventArgument;
theForm.submit();
}
}
如果 if 语句中的测试结果为真,那么 JavaScipt 函数可以简化为下面的 JavaScript 代码,并且我们使用函数调用中的参数:
theForm.__EVENTTARGET.value = 'ctl00$ContentPlaceHolder1$PGN01';
theForm.__EVENTARGUMENT.value = '';
theForm.submit();
现在我们需要知道“theForm”是什么。
下面的代码位于 __doPostBack 函数的正上方:
var theForm = document.forms['aspnetForm'];
if (!theForm) {
theForm = document.aspnetForm;
}
我们现在知道'theForm'是对'form' HTML标签的引用,它具有id属性'aspnetForm'(id='aspnetForm'),这意味着我们要在HTML文档中寻找像这样开始的东西:
<form id="aspnetForm"
要知道该标签是如何编写的,我将使用 Firefox 浏览器查看您感兴趣的页面的修改后的 HTML。 这里我使用的是 FireBug 插件。
HTML 表单的开始标签如下所示:
<form id="aspnetForm" onsubmit="javascript:return WebForm_OnSubmit();"
action="/Shoes-All.aspx" method="post" name="aspnetForm">
所以这个动作是使用同一个 HTML 文档!
让我们看看 WebForm_OnSubmit() 函数在做什么:
function WebForm_OnSubmit() {
if (typeof(ValidatorOnSubmit) == "function" && ValidatorOnSubmit() == false)
return false;
return true;
}
让我们看一下 ValidatorOnSubmit() 函数和它使用的一个有趣的变量:
var Page_ValidationActive = false;
// ...
function ValidatorOnSubmit() {
if (Page_ValidationActive) {
return ValidatorCommonOnSubmit();
}
else {
return true;
}
}
这意味着该函数将始终返回“true”,因此我们现在可以将表单 start-tag 重写为:
<form id="aspnetForm" onsubmit="javascript:return true;"
action="/Shoes-All.aspx" method="post" name="aspnetForm">
由此我们可以得出结论,需要从网络服务器重新加载网页。
现在我们需要知道在 HTTP POST 请求中使用了哪些变量和值。
为此,我再次使用 Firefox 并打开了 JavaScript。另外,我正在使用很棒的 Firebug 插件。 在第一个 div 标签的 Form-element 中,我们发现:
<div>
<input id="__EVENTTARGET" type="hidden"
value="" name="__EVENTTARGET">
<input id="__EVENTARGUMENT" type="hidden" value="" name="__EVENTARGUMENT">
<input id="__LASTFOCUS" type="hidden" value="" name="__LASTFOCUS">
<input id="__VIEWSTATE" type="hidden"
value="(lots of data here)" name="__VIEWSTATE">
</div>
如果你还记得我们之前的精简 javascript 代码,它修改了表单中 2 个 input-tags 的 value 属性,所以 HTML 已经被那个函数修改了,所以它真的是:
<div>
<input id="__EVENTTARGET" type="hidden"
value="ctl00$ContentPlaceHolder1$PGN01" name="__EVENTTARGET">
<input id="__EVENTARGUMENT" type="hidden" value="" name="__EVENTARGUMENT">
<input id="__LASTFOCUS" type="hidden" value="" name="__LASTFOCUS">
<input id="__VIEWSTATE" type="hidden"
value="(lots of binary data here)" name="__VIEWSTATE">
</div>
您当然需要对 id 为“_VIEWSTATE”的输入标签的 value 属性的内容进行逐字复制。
仅供参考,Firefox 说 _VIEWSTATE 输入标签 XPath 是:
//*[@id="__VIEWSTATE"]
...并且它的 CSS 选择器是:
form#aspnetForm div input#__VIEWSTATE
从网络服务器下载所有项目后,您将需要解析 HTML 页面。
有趣的内容深深地嵌入到表单中。它是一个 HTML 表格。
该表的相关 XPath 是:
//*[@id="ctl00_ContentPlaceHolder1_dlList"]
...而CSS选择器是
table#ctl00_ContentPlaceHolder1_dlList
它包含一个 tbody、tr、td、div 和另一个表格(=更糟糕的设计 - 有人需要了解无表格设计。HTML 表格在智能手机和平板电脑上看起来很糟糕。)
我认为此时您应该使用 Beautiful Soup 4 解析器。