找回密码

火车采集器软件交流官方论坛

搜索
火车采集器V9版免费下载火车浏览器 - 可视采集,万能群发,全自动脚本工具
查看: 9380|回复: 11

中国联通采集实例

[复制链接]
发表于 2010-12-26 20:39:13 | 显示全部楼层 |阅读模式
采集的目标站,中国联通http://shop.10010.com/number/searchNumber.action



这个网站列表分页无变化,要解决分页问题,就要找到能够提供给我们分页信息的网址,这个地址栏的地址只是个障眼法了

列表分页无变化,可能是2种情况,一种是点分页直接post请求,更新整个页面的,这样的更新了整个页面,所以源代码我吗看到可能和服务器返回的数据相符,这样的直接在浏览器查看源码是真实的返回数据;

而另一种是ajax请求,是在不知不觉间页面的某些地方已经发生了变化,ajax请求只更新页面的一部分,理路只更新分页里德内容,这种请求的返回数据不能通过直接查看源码的方式,看返回的数据,因为ajax已经把返回的数据进行了处理了,真实的返回数据并不是你在浏览器查看源码说看到的,要看到这真实的返回数据,借助火车的模拟httppost提交工具才行

说明:这个网站分页就是ajax的,而内容页的请求时直接post的,好在这些网址都可以用get方式访问
通过抓包获得的数据,post数据中的每个参数代表的意识,通过下面的分析,可以得出各自的作用:这要仔细全面的分析源码,js文件,把该页面全部保存
这是全部的js文件,这个网站函数等都封装在了js文件,直接源码里看不到,通过js文件名字,可以大致了解各自的用途,下面在现有的地方就要找这些函数事件了


首先进入这个页面,要采集的3g和2g号码的区域,这个区域是最重要的,主要要分析这个区域,这个区域包含2个层,3g内容列表和2g内容列表层,而你在点击,这2个东西的时候,其实2个层时在互换的,也就是说3g和2g的层是重叠在一起的,点3g条,显示3g层,隐藏2g层;而它们都有个自的页脚部分,列表内容,就是说3g分页和2g是独立的,当你点击搜索,分页时只有的一种网络类型的数据的提交是有用的,而这个判断是3g网络还是2g网络,是由表单
  1. <form id="defaultnumber" name="defaultnumber" method="post" action="/number/searchNumber.action">
复制代码
里德一个表单项来判断,

首先把这个表单
  1. <form id="defaultnumber" name="defaultnumber" method="post" action="/number/searchNumber.action">
  2.                         <input type="hidden" name="searchNumberInfo.order"              id="order"              value="0"/>
  3.                         <input type="hidden" name="searchNumberInfo.order2g"            id="order2g"            value="0"/>                       
  4.                         <input type="hidden" name="pageInfo.currPage"                   id="currPage"           value="0" />
  5.                         <input type="hidden" name="pageInfo.totalPager"                 id="totalPager"         value="88"/>
  6.                         <input type="hidden" name="formname"                            id="formname"           value="defaultnumber" />
  7.                         <input type="hidden" name="searchNumberInfo.currPage2g"         id="currPage2g"         value="0" />
  8.                         <input type="hidden" name="searchNumberInfo.totalPager2g"       id="totalPager2g"       value="1011"/>
  9.                         <input type="hidden" name="searchNumberInfo.oldnumberCardId"    id="oldnumberCardId"    value=""/>
  10.                         <input type="hidden" name="searchNumberInfo.oldnumberCardId2g"  id="oldnumberCardId2g"  value=""/>
  11.                         <input type="hidden" name="formname"                            id="formname2g"         value="defaultnumber" />
  12.                         <input type="hidden" name="searchNumberInfo.cardID" />
  13.                         <input type="hidden" name="searchNumberInfo.isreserve" />
  14.                         <input type="hidden" name="searchNumberInfo.saleCost" />
  15.                         <input type="hidden" name="searchNumberInfo.numbercountryId" />
  16.                         <input type="hidden" name="searchNumberInfo.numbercityId" />
  17.                         <input type="hidden" name="searchNumberInfo.ruleID" />
  18.                         <input type="hidden" name="searchNumberInfo.startCost" />
  19.                         <input type="hidden" name="searchNumberInfo.onnetlong" />
  20.                         <input type="hidden" name="searchNumberInfo.lowestcost" />
  21.                         <input type="hidden" name="searchNumberInfo.nCardcost" />   
  22.                         <input type="hidden" name="searchNumberInfo.payType" />                             
  23.                         <input type="hidden" id="selnetType" value=''/>                                             
  24.                         <input type="hidden" id="subprocessType" name="searchNumberInfo.processType" value="numbercard" />
  25.                         
  26.                         
  27.                         <input type="hidden" name="searchNumberInfo.netType" id="netType" value='01'/>
复制代码
这些是这个表单的隐藏的项,这些项的意识可以通过一个个事件函数的执行过程,了解到它们的意识,所以当你触发了一个事件时,路点了搜索时这些项的值都可能已被重新设置,而你在源码中依然看不出这些改变,

下面是上面各个隐藏项的意识的是这样得出的:
1
  1. searchNumberInfo.netType
复制代码
项代表什么:当点击3g和2g互换的tab时,
  1. <div id="lab1" class="lab_pg_number_act" onclick="setTab(1)" style="width: 281px; margin-right: 1px;">3G号码</div>
  2.                                                                         <div id="lab2" class="lab_pg_number_nor" onclick="setTab(2)" style="width: 282px;">2G号码</div>
复制代码
可以知道触发了
  1. setTab
复制代码
函数,
  1. function setTab(lab) {
  2.     if (lab == 1) {
  3.         document.getElementById("lab1").className  = "lab_pg_number_act";
  4.         document.getElementById("lab2").className  = "lab_pg_number_nor";
  5.         $("#number3g").css("display","block");
  6.         $("#number2g").css("display","none");
  7.         $("#netType").val("01");
  8.         $("#selnetType").val("01");
  9.         //          $("#nettypespan").html("3g");
  10.         // 显示首页左边3g套餐推荐
  11.         $(window.parent.document).find('#set_recommendation_div').show();
  12.         $(window.parent.document).find('#frame_2gpackage_div').hide();
  13.     } else {
  14.         document.getElementById("lab1").className  = "lab_pg_number_nor";
  15.         document.getElementById("lab2").className  = "lab_pg_number_act";
  16.         $("#number3g").css("display","none");
  17.         $("#number2g").css("display","block");
  18.         $("#netType").val("00");
  19.         $("#selnetType").val("00");
  20.         //          $("#nettypespan").html("2g");
  21.         // 显示首页左边2g套餐推荐
  22.         $(window.parent.document).find('#set_recommendation_div').hide();
  23.         $(window.parent.document).find('#frame_2gpackage_div').show();
  24.     }
  25. }
复制代码
通过这个函数可以知道,一方面实现了相互的切换,另一方面设置了
  1. $("#netType").val("00");
  2.         $("#selnetType").val("00");
复制代码
id为netType和selnetType对象的值,而这2者正是上面表单里德隐藏项的
  1. searchNumberInfo.netType
复制代码
  1. <input type="hidden" id="selnetType" value=''/>
复制代码
,表单提交时有name属性的才会被提交,当点击3g触发
  1. setTab(1)
复制代码
,根据
  1. if (lab == 1)
复制代码
可知,点3g  searchNumberInfo.netType和selnetType的值被赋予01;相反点2g
  1. setTab(2)
复制代码
,可知被赋予了00,从而可知
  1. searchNumberInfo.netTyp
复制代码
表单项代表当前选择
的号码网络,01代表3g网络,00代表2g网络,这2个值在post时是3g和2g网络数据请求的标志,所以说当选择一种网络,post数据中的一些关于另一种网络的参数是可以去掉的


2
  1. <input type="hidden" name="searchNumberInfo.order"              id="order"              value="0"/>
复制代码
项代表什么

往往它的名字就代表了它的意识,不知道的单词,用google翻译下,order是排序,可大至了解它的意识是对结果的排序,

,这需要看这2个切换的事件,
  1. <div id="sorttime"></div>
  2.                     <div id="sortcost"></div>
复制代码
,这是2者的位置,它们在js文件里绑定了事件,注意这2个是3g层里的,所以这些设置的表单项是3g的,不是2g的,2g和3g的基本方法都是相同的,表单项名字带2g的就是关于2g的,而不带的就是3g的,以下都是以3g层里触发的事件做说明:

按时间排序被点击触发的函数:
  1. $('#sorttime').bind('click', function(){
  2.         $('#order').val("0");
  3.         $('#sorttime').addClass('sort_on');   $('#sorttime').html("按上架时间排序");
  4.         $('#sortcost').removeClass('sort_on').addClass('sort_out');  $('#sortcost').html("按预存款排序");
  5.         gotopage3g();
  6.     });
复制代码
看到
  1.    $('#order').val("0");
复制代码
,id为order的对象就是表单的
  1. name="searchNumberInfo.order"              id="order"  
复制代码
,可见searchNumberInfo.order=0带表按时间排序;

按预付款排序被点击触发的函数:
  1. $('#sortcost').bind('click', function(){
  2.         var order = $('#order').val();
  3.         if(order == '0' || order == '2'){
  4.             $('#order').val("1");
  5.             $('#sorttime').removeClass('sort_on').addClass('sort_out');  $('#sorttime').html("按上架时间排序");
  6.             $('#sortcost').addClass('sort_on');   $('#sortcost').html("按预存款排序&nbsp;&darr;");
  7.             gotopage3g();
  8.         }else{
  9.             $('#order').val("2");
  10.             $('#sorttime').removeClass('sort_on').addClass('sort_out');  $('#sorttime').html("按上架时间排序");
  11.             $('#sortcost').addClass('sort_on');   $('#sortcost').html("按预存款排序&nbsp;&uarr;");
  12.             gotopage3g();
  13.         }
  14.     });
复制代码
,可知预付款时是1,2互换的,都可以,同时也发生了ajax请求
  1. gotopage3g()
复制代码
3.,这个函数在点击搜索按钮时会触发
  1. check()
复制代码


3g搜索按钮源码<input type="button" class="btn" style="cursor: hand"
                                                                                                        onclick="javascript:return check();" />
  1. function check(){
  2.     //自定义号码有输入值则检查是否数字
  3.     if((($("#cardID").val()!='号码自定义:如生日,纪念日等')&&($("#cardID").val()!='如生日,纪念日等')) && ($("#cardID").val()!='')){
  4.         if(/^\d+$/.test($("#cardID").val()) == false){
  5.             errDiv("自定义号码只能输入数字!");
  6.             return false;
  7.         }
  8.     }
  9.     //没输入值提交字定义号码为空值
  10.     if($("#cardID").val()=='号码自定义:如生日,纪念日等'||$("#cardID").val()=='如生日,纪念日等'){
  11.         $("#cardID").val("");
  12.     }
  13.     $("#currPage").val("0");
  14.     //    document.defaultnumber.submit();
  15.     getNumberList();        // lizl
  16. }
复制代码
首先对自定义输入内容的检查,自定义号码只能输入数字,没输入值提交字定义号码为空值,
  1. $("#currPage").val("0");
复制代码
,就把表单
  1. pageInfo.currPage
复制代码
值设置0,也就是第一页,是从0开始的,然后触发
  1. getNumberList();
复制代码
,这个函数就是具体的ajax请求了,是核心函数

getNumberList函数:这个我略去了一部分代码
  1. / ajax获取符合用户搜索条件的号码      lizl
  2. var getNumberList = function(){
  3.     var netType = $("#netType").val();          // 网络类型     00:2g   01:3g
  4.     var urlStr = '/number/doGetNumberList.action';
  5.     var params = $("#defaultnumber").serialize();
  6.     if(netType=='00'){
  7.         $('#loadbox2g').show();
  8.     }else{
  9.         $('#loadbox').show();
  10.     }
  11.     $.ajax({
  12.         async:true,
  13.         type:'post',
  14.         url:urlStr,
  15.         cache: false ,
  16.         data:params,
  17.         timeout:5000,
  18.         dataType:'json',
  19.         success: function(data){
  20.             getNumberListCallBack(data, netType);
  21.             if(netType=="00"){
  22.                 findPageButton2g(data.pager);
  23.                 $('#loadbox2g').hide();
  24.             }else{
  25.                 findPageButton(data.pager);
  26.                 $('#loadbox').hide();
  27.             }
  28.         },
  29.         error: function(XMLHttpRequest, textStatus, errorThrown) {
复制代码
通过可以check()搜索和getNumberLis,可以知道点搜索发生了ajax请求,post方式,地址
  1. var urlStr = '/number/doGetNumberList.action';
复制代码
另外还有请求成功时的回调函数
  1. getNumberListCallBack(data, netType);
复制代码
,这个函数的作用就是处理服务器返回数据,处理后设置在3g层中,所以这是ajax与直接post的不同,重要的还是冲服务器返回的数据,里面一定有我们需要的东西,但ajax要用火车的模拟posthttp工具,来查看返回的数据,这样才能设置规则,获取内容页,有关这个工具的用法,论坛里有


再来看getNumberListCallBack函数,才能知道是潞河处理返回数据的,我用get提交可以返回和post提交相同的效果,这样可以请求是一个 文件,下载后用记事本打开看,返回的是一个对象,这个对象包含info和paper2个对象,info是一个数组,数组的每个成员又是一个包含号码信息的对象,info是包含内容的数据,paper是包含页面总页数等信息的,
  1. // 回调方法         lizl
  2. function getNumberListCallBack(data, netType){
  3.     var list01 = "";
  4.     var list02 = "";
  5.     var list03 = "";
  6.     var infoList = data.info;
  7.     if(0 == infoList.length || null == infoList){
  8.         if(netType=="00"){
  9.             $("#2gnumberShow").empty().html("<tr><td colspan='6'>没有符合条件的号码</td></tr>");
  10.         }else{
  11.             $("#3gnumberShow").empty().html("<tr><td colspan='6'>没有符合条件的号码</td></tr>");
  12.         }
  13.     }else{
  14.         var table3gStr =
  15.             "<tbody>" +
  16.             "<tr>" +
  17.             "<td style='border-bottom: 2px #999999 solid; font-weight: bold; width: 100px; height: 23px;'>号码</td>" +
  18.             "<td style='border-bottom: 2px #999999 solid; font-weight: bold; width: 80px; height: 23px;'>预存款</td>" +
  19.             "<td style='border-bottom: 2px #999999 solid; font-weight: bold; width: 100px; height: 23px;'>号码</td>" +
  20.             "<td style='border-bottom: 2px #999999 solid; font-weight: bold; width: 83px; height: 23px;'>预存款</td>" +
  21.             "<td style='border-bottom: 2px #999999 solid; font-weight: bold; width: 100px; height: 23px;'>号码</td>" +
  22.             "<td style='border-bottom: 2px #999999 solid; font-weight: bold; width: 80px; height: 23px;'>预存款</td>" +
  23.             "<td style='border-bottom: 2px #999999 solid; font-weight: bold; width: 20px;'>&nbsp;</td>" +
  24.             "</tr>" +
  25.             "<tr>" +
  26.             "<td colspan='6' height='5' style='height: 5px'>" +
  27.             "</td>" +
  28.             "</tr>" +
  29.             "</tbody>" +
  30.             "<tbody id='3gnumberShow'>" +
  31.             "<tr>" +
  32.             "<td colspan='2' style='border-right: 1px #CCCCCC solid;width: 180px' valign='top'>" +
  33.             "<table width='180px' border='0' cellspacing='0'  id='3glist01' cellpadding='0' style='line-height: 190%;'>" +
  34.             "</table>" +
  35.             "</td>" +
  36.             "<td colspan='2' style='border-right: 1px #CCCCCC solid;width: 180px' valign='top'>" +
  37.             "<table width='180px' border='0' cellspacing='0'  id='3glist02' cellpadding='0' style='line-height: 190%;'>" +
  38.             "</table>" +
  39.             "</td>" +
  40.             "<td colspan='2' style='width: 180px' valign='top'>" +
  41.             "<table width='180px' border='0' cellspacing='0'  id='3glist03' cellpadding='0' style='line-height: 190%;'>" +
  42.             "</table>" +
  43.             "</td>" +
  44.             "</tr>" +
  45.             "</tbody>";
  46.         var table2gStr =
  47.             "<tbody>" +
  48.             "<tr>" +
  49.             "<td style='border-bottom: 2px #999999 solid; font-weight: bold; width: 100px; height: 23px;'>号码</td>" +
  50.             "<td style='border-bottom: 2px #999999 solid; font-weight: bold; width: 80px; height: 23px;'>预存款</td>" +
  51.             "<td style='border-bottom: 2px #999999 solid; font-weight: bold; width: 100px; height: 23px;'>号码</td>" +
  52.             "<td style='border-bottom: 2px #999999 solid; font-weight: bold; width: 83px; height: 23px;'>预存款</td>" +
  53.             "<td style='border-bottom: 2px #999999 solid; font-weight: bold; width: 100px; height: 23px;'>号码</td>" +
  54.             "<td style='border-bottom: 2px #999999 solid; font-weight: bold; width: 80px; height: 23px;'>预存款</td>" +
  55.             "<td style='border-bottom: 2px #999999 solid; font-weight: bold; width: 20px;'>&nbsp;</td>" +
  56.             "</tr>" +
  57.             "<tr>" +
  58.             "<td colspan='6' height='5' style='height: 5px'>" +
  59.             "</td>" +
  60.             "</tr>" +
  61.             "</tbody>" +
  62.             "<tbody id='2gnumberShow'>" +
  63.             "<tr>" +
  64.             "<td colspan='2' style='border-right: 1px #CCCCCC solid;width: 180px' valign='top'>" +
  65.             "<table width='180px' border='0' cellspacing='0'  id='2glist01' cellpadding='0' style='line-height: 190%;'>" +
  66.             "</table>" +
  67.             "</td>" +
  68.             "<td colspan='2' style='border-right: 1px #CCCCCC solid;width: 180px' valign='top'>" +
  69.             "<table width='180px' border='0' cellspacing='0'  id='2glist02' cellpadding='0' style='line-height: 190%;'>" +
  70.             "</table>" +
  71.             "</td>" +
  72.             "<td colspan='2' style='border-right: 1px #CCCCCC solid;width: 180px' valign='top'>" +
  73.             "<table width='180px' border='0' cellspacing='0'  id='2glist03' cellpadding='0' style='line-height: 190%;'>" +
  74.             "</table>" +
  75.             "</td>" +
  76.             "</tr>" +
  77.             "</tbody>";
  78.         var cardID = "";
  79.         var isreserve = "";
  80.         var saleCost = "";
  81.         var numbercountryId = "";
  82.         var numbercityId = "";
  83.         var ruleID = "";
  84.         var startCost = "";
  85.         var onnetlong = "";
  86.         var lowestcost = "";
  87.         var nCardcost = "";
  88.         var payType = "";
  89.         for(var attr in infoList){
  90.             cardID = infoList[attr].cardID;
  91.             isreserve = infoList[attr].isreserve;
  92.             saleCost = infoList[attr].saleCost;
  93.             numbercountryId = infoList[attr].numbercountryId;
  94.             numbercityId = infoList[attr].numbercityId;
  95.             ruleID = infoList[attr].ruleID;
  96.             startCost = infoList[attr].startCost;
  97.             onnetlong = infoList[attr].onnetlong;
  98.             lowestcost = infoList[attr].lowestcost;
  99.             nCardcost = infoList[attr].nCardcost==undefined?"0":infoList[attr].nCardcost;
  100.             payType = infoList[attr].payType;
  101.             var numberMess =
  102.                 "<tr style='cursor: pointer;' onmousemove="this.style.background='#FFE2AC'""+
  103.                 "  onmouseout="this.style.background='#fff'" onclick="defaultnumber[\'searchNumberInfo.cardID\'].value=\'"+cardID+"\'"+
  104.                 "  ;defaultnumber[\'searchNumberInfo.isreserve\'].value=\'"+isreserve+"\'"+
  105.                 "  ;defaultnumber[\'searchNumberInfo.saleCost\'].value=\'"+saleCost+"\'"+
  106.                 "  ;defaultnumber[\'searchNumberInfo.numbercountryId\'].value=\'"+numbercountryId+"\'"+
  107.                 "  ;defaultnumber[\'searchNumberInfo.numbercityId\'].value=\'"+numbercityId+"\'"+
  108.                 "  ;defaultnumber[\'searchNumberInfo.ruleID\'].value=\'"+ruleID+"\'"+
  109.                 "  ;defaultnumber[\'searchNumberInfo.startCost\'].value=\'"+startCost+"\'"+
  110.                 "  ;defaultnumber[\'searchNumberInfo.onnetlong\'].value=\'"+onnetlong+"\'"+
  111.                 "  ;defaultnumber[\'searchNumberInfo.lowestcost\'].value=\'"+lowestcost+"\'"+
  112.                 "  ;defaultnumber[\'searchNumberInfo.nCardcost\'].value=\'"+nCardcost+"\'"+
  113.                 "  ;defaultnumber[\'searchNumberInfo.payType\'].value=\'"+payType+"\'"+
  114.                 "  ;defaultnumber.action=\'searchOneNumber.action\'"+
  115.                 "  ;defaultnumber.submit();">"+
  116.                 "    <td width='100px' style='text-align:right;'>"+
  117.                 cardID+
  118.                 "    </td>"+
  119.                 "    <td width='80px' style='text-align:center;'>"+
  120.                 startCost+
  121.                 "    元</td>"+
  122.                 "</tr>";
  123.             if(attr%3==0){
  124.                 list01 += numberMess;
  125.             }
  126.             if(attr%3==1){
  127.                 list02 += numberMess;
  128.             }
  129.             if(attr%3==2){
  130.                 list03 += numberMess;
  131.             }
  132.         }
  133.         if(netType=="00"){
  134.             $('#numberList2g').empty().html(table2gStr);
  135.             $("#2glist01").empty();
  136.             $("#2glist02").empty();
  137.             $("#2glist03").empty();
  138.             $("#2glist01").html(list01);
  139.             $("#2glist02").html(list02==""?"<tr><td></td></tr>":list02);
  140.             $("#2glist03").html(list03==""?"<tr><td></td></tr>":list03);
  141.         }else{
  142.             $('#numberList').empty().html(table3gStr);
  143.             $("#3glist01").empty();
  144.             $("#3glist02").empty();
  145.             $("#3glist03").empty();
  146.             $("#3glist01").html(list01);
  147.             $("#3glist02").html(list02==""?"<tr><td></td></tr>":list02);
  148.             $("#3glist03").html(list03==""?"<tr><td></td></tr>":list03);
  149.         }
  150.     }
  151. }
复制代码
这个函数执行后是,路过请求3g网络,则把格式化后的数据,设置在3g层,相反2g
  1. if(netType=="00")
复制代码
,则设置2g层,这都要看netType的值,所以说它很关键


这个函数里
  1.   var numberMess =
  2.                 "<tr style='cursor: pointer;' onmousemove="this.style.background='#FFE2AC'""+
  3.                 "  onmouseout="this.style.background='#fff'" onclick="defaultnumber[\'searchNumberInfo.cardID\'].value=\'"+cardID+"\'"+
  4.                 "  ;defaultnumber[\'searchNumberInfo.isreserve\'].value=\'"+isreserve+"\'"+
  5.                 "  ;defaultnumber[\'searchNumberInfo.saleCost\'].value=\'"+saleCost+"\'"+
  6.                 "  ;defaultnumber[\'searchNumberInfo.numbercountryId\'].value=\'"+numbercountryId+"\'"+
  7.                 "  ;defaultnumber[\'searchNumberInfo.numbercityId\'].value=\'"+numbercityId+"\'"+
  8.                 "  ;defaultnumber[\'searchNumberInfo.ruleID\'].value=\'"+ruleID+"\'"+
  9.                 "  ;defaultnumber[\'searchNumberInfo.startCost\'].value=\'"+startCost+"\'"+
  10.                 "  ;defaultnumber[\'searchNumberInfo.onnetlong\'].value=\'"+onnetlong+"\'"+
  11.                 "  ;defaultnumber[\'searchNumberInfo.lowestcost\'].value=\'"+lowestcost+"\'"+
  12.                 "  ;defaultnumber[\'searchNumberInfo.nCardcost\'].value=\'"+nCardcost+"\'"+
  13.                 "  ;defaultnumber[\'searchNumberInfo.payType\'].value=\'"+payType+"\'"+
  14.                 "  ;defaultnumber.action=\'searchOneNumber.action\'"+
  15.                 "  ;defaultnumber.submit();">"+
复制代码
循环生成了格式化的代码,这个就是内容页提交时的模板,而这些项都是用ajax后返回的数据设置的,对应了上面表单的某些隐藏项,而当一个内容页被点击,发生的是表单的提交,首先用当前记录的设置对应的表单项的值,这次提交地址变了
  1. defaultnumber.action=\'searchOneNumber.action\'"
复制代码
根据名字就是说这个defaultnumber表单提交地址变成了单个号码请求的地址,这个地址是处理单个号码的,而这个地址也可以用get方式请求





还有就是点击分页时会发生什么:

4.gotopage3g()
  1. 这是3g的输入框源码到第</td>
  2.                         <td id="selectpageh" width="40px"><input id="inputpageh" type="text" style="color:#000000;text-align:center;" size="4" />  </td>
  3.                         <td>页</td>
  4.                         <td><input type="button" value="确定" class='page_btnbg' onclick="gotopage3gh();"/></td>
复制代码
,点击触发了
  1. gotopage3gh()
复制代码
  1. //3g分页跳转到第几页
  2. function gotopage3g(){
  3.     var inputpage=$("#inputpage").val();//输出的页数
  4.     var totalPager=$("#totalPager").val();//总页数

  5.     if(inputpage==""){
  6.         errDiv("请输入需要跳转的页数,当前满足条件的记录共有"+totalPager+"页。");
  7.     }else{
  8.         if(/^\d+$/.test(inputpage) == false){
  9.             $("#inputpage").val("");
  10.             $("#inputpageh").val(""); // lizl 2010-7-26
  11.             errDiv("请输入数字,当前满足条件的记录共有"+totalPager+"页。");
  12.             return false;
  13.         }
  14.         if(parseInt(inputpage)>parseInt(totalPager)){
  15.             errDiv("满足条件的号码只有"+totalPager+"页,请输入小于此数量的页数。");
  16.             $("#inputpage").val("");
  17.             $("#inputpageh").val(""); // lizl 2010-7-26
  18.         }else{
  19.             if(inputpage=="0"){
  20.                 $("#currPage").val("0");
  21.             }else{
  22.                 $("#currPage").val(parseInt(inputpage)-1);
  23.             }
  24.             getNumberList();
  25.         }
  26.     }
  27. }
复制代码
,getNumberList()前面已经说过了,检验输入是否和规范,然后是把输入的页码-1,做为currPage的值,然后ajax getNumberList(),可见页码和值差1,1 currPage=0,2currPage=1;

#inputpage  #inputpageh 分别是3g下输入框对象,上输入框对象,带h就是上面的


还有个问题,就是页面的3g的页码部分是什么样的,在源码里找不到,这些也是在ajax后设置的
  1. success: function(data){
  2.             getNumberListCallBack(data, netType);
  3.             if(netType=="00"){
  4.                 findPageButton2g(data.pager);
  5.                 $('#loadbox2g').hide();
  6.             }else{
  7.                 findPageButton(data.pager);
  8.                 $('#loadbox').hide();
  9.             }
  10.         },
复制代码
  1. findPageButton(data.pager);
复制代码
就是设置页码部分的,当然点的3g的,设置3g,2g不会被设置的,2者是独立的
  1. function findPageButton(pager){
  2.     var currPage = pager.currPage;
  3.     var totalPager = pager.totalPager;
  4.     var nowpage = totalPager == 0?0:currPage+1;
  5. //    $("#pager").pager({ pagenumber: currPage, pagecount: totalPager, buttonClickCallback: PageClick });
  6. //    $("#pagerh").pager({ pagenumber: currPage, pagecount: totalPager, buttonClickCallback: PageClick });
  7.     $("#pager").pager({ pagenumber: nowpage, pagecount: totalPager, buttonClickCallback: PageClick });
  8.     $("#pagerh").pager({ pagenumber: nowpage, pagecount: totalPager, buttonClickCallback: PageClick });

  9.     $('#totalnumpage').empty().html("共" + totalPager + "页&nbsp;到第");
  10.     $('#totalnumpageh').empty().html(nowpage + "&frasl;" + totalPager + "页&nbsp;到第");
  11.     $('#totalPager').val(totalPager);
  12.     $("#currPage").val(currPage);
  13.     $("#inputpage").val(currPage+1);
  14.     $("#inputpageh").val(currPage+1);
  15. }
复制代码
data.pager是ajax返回的对象中的pager对象,具体可以把那个返回的文件打开,在最后就可以看到
  1. $("#pager").pager({ pagenumber: currPage, pagecount: totalPager, buttonClickCallback: PageClick });
复制代码
等是设置上一页下一页按钮的
  1. $('#totalPager').val(totalPager);
复制代码
可知表单
  1. <input type="hidden" name="pageInfo.totalPager"                 id="totalPager"         value="88"/>
复制代码
,pageInfo.totalPager就是符合条件的3g的总页数,
  1. $("#currPage").val(currPage);
复制代码
当前页,页就是说它代表3g的页码,这个就代表重要的分页了,注意是3g的


还有就是用户可以选择的一些下拉框,之定义的,表单项了,还是3g的为例,
  1. 靓号类型<select name="searchNumberInfo.searchRuleID"
  2.                                id="ruleID"
复制代码
  1. 预存款<select name="searchNumberInfo.numberStartCost"
  2.                                id="startCost"
复制代码
  1. 号码自定义<input type="text" name="searchNumberInfo.numberCardId"
  2.                                                                                                                 id="cardID" value="" size="15" maxlength="11"
  3.                                                                
复制代码
路过想设置这些,对应源码里德值设置

到这里,基本已经结束了,内容页的请求前面也有说过了,可是还有一个重要的地方,那就是地区城市,好像在分页时没有表单项代表城市的
  1. <input type="hidden" name="searchNumberInfo.numbercountryId" />
  2.                         <input type="hidden" name="searchNumberInfo.numbercityId" />
复制代码
,这2个是在请求内容页时被设置的,与列表分页无关,我试着设置了,不行

这就要分析当切换城市时发生的事件了,,切换城市,鼠标悬停在城市上,状态栏可以看到
  1. javascript:changeCity("002","002001")
复制代码
就是这个事件了

在left js文件里我找到这个函数,
  1. var changeCity = function (province, cityCode) {
  2.        
  3.         clearCookie();
  4.         $.cookie("city", province + "|" + cityCode, {expires:200000, path:"/"});
  5.        
  6.         var winurl = window.location.href;
  7.         if (index === 7 || index === 10 && endsWith(winurl, 'searchNumber.action')) {
  8.                 toInfo(winurl);
  9.         } else {
  10.                 window.location.reload();
  11.         }
  12. };
复制代码
  1. var endsWith = function(winurl, str){
  2.         if (winurl.indexOf(str) > 0) {
  3.                 return true;
  4.         }
  5.     return false;
  6. }
复制代码
肯定是返回true了,toInfo(winurl);应该执行了
  1. var toInfo = function(url)
  2. {       
  3.         var cityCode = $.cookie("city");
  4.         if (typeof cityCode === 'undefined' || cityCode === 'undefined|undefined' || cityCode === null || cityCode === '' || cityCode === '|') {
  5.                 cityCode = '002|002001';
  6.         }
  7.         var area = cityCode.split('|');               
  8.         var varform = window.document.createElement("form");
  9.         varform.name="infoform";
  10.         varform.action=url;
  11.         varform.method="post";
  12.         varform.style.display="none";
  13.         window.document.body.appendChild(varform);

  14.         var text1 = window.document.createElement("input");
  15.         text1.type="hidden";
  16.         text1.value=area[1];
  17.         text1.name="searchNumberInfo.cityno";
  18.         varform.appendChild(text1);

  19.         varform.submit();
  20. }
复制代码
冲这个函数看出当切换城市时有个表单被提交了,发生post请求,不过这个表单是新建的,和上面的不是一个,只提交了searchNumberInfo.cityno参数,代表城市代码,所有城市代码在mydata js文件里,这里的城市名字是编码的,可以找个解码网站


这里有个 $.cookie("city");是从cookie里提取城市信息的,这里我只截取了被执行的部分,其他的看的不懂,总之else部分应该被执行了
  1. jQuery.cookie = function(name, value, options) {

  2. else { // only name given, get cookie
  3.         var cookieValue = null;
  4.         if (document.cookie && document.cookie != '') {
  5.             var cookies = document.cookie.split(';');
  6.             for (var i = 0; i < cookies.length; i++) {
  7.                 var cookie = jQuery.trim(cookies[i]);
  8.                 // Does this cookie string begin with the name we want?
  9.                 if (cookie.substring(0, name.length + 1) == (name + '=')) {
  10.                     cookieValue = decodeURIComponent(cookie.substring(name.length + 1));
  11.                     break;
  12.                 }
  13.             }
  14.         }
  15.         return cookieValue;
  16.     }
  17. };
复制代码
这个函数是遍历cooike的所有字段,当找到city字段时,截取出它的值,因为这个值是经过encodeURIComponent() 函数编码的,
  1. cookieValue = decodeURIComponent(cookie.substring(name.length + 1));
复制代码
,所以他用 decodeURIComponent解码,然后返回了
  1. cookieValue
复制代码



抓包获得的cooike:
  1. Cookie: WT_FPC=id=276c7ba14f71224a4cf1293353299905:lv=1293353960968:ss=1293353299905; city=002%7C002001; CheckCode=nylnL/oquq1wjqv2TA1vPIumIAocn40M; JSESSIONID=5tgJNXDCD2qSgh6xHKXmLnY4NP4pKcFfhCqhYJr3X182GdS9XGLR!887917931
复制代码
  1. city=002%7C002001
复制代码
,解码后002|002001,%7C就是|,002是省份代码,002001是城市代码,这些都在mydata js文件里了


当你进入这个网站,它的默认城市是北京选号入网
  1. <script language="JavaScript" type="text/JavaScript">
  2.                                                                                                                 var cityCode = $.cookie('city');
  3.                                                                                                                 if (typeof cityCode == 'undefined' || cityCode == null || cityCode == '') {
  4.                                                                                                                         document.write("[北京]");
  5.                                                                                                                 }else{
  6.                                                                                                                         var area = cityCode.split('|');
  7.                                                                                                                         var cityName = cityData[area[1]].cityName;
  8.                                                                                                                         cityName="["+cityName+"]";
  9.                                                                                                                         document.write(cityName);
  10.                                                                                                                 }
  11.                                                                         </script>
复制代码
就是这段代码的效果,通过这些可以知道当你切换了城市的时候,由于changeCity("002","002001")里执行了clearCookie();
  1. function clearCookie() {  
  2.   var expires = new Date();  
  3.   expires.setDate(expires.getDate() - 1);
  4.   document.cookie = 'city=null;expires=' + expires.toGMTString();
  5. }
复制代码
,这个清理的以前的cooike,这个cooike过期了,包含新的城市的cooike被设置了

我发现了这个网站的搜索内容页等与cooike是有很大的关系,路过你切换了城市,那摩采集规则里采集到的就是该城市的号码;我试过用抓包获取不同城市时的cooike,目标站设置登录,可以采集同时采集不同的城市,还有时不行了,页不知道是地址太长,有换行,刚开始我把抓包的post数据连在提交地址后面,就是因为复制时有换行和空格,导致几种错误情况的发生

而服务器总是在判断当前用户浏览器选择的城市,路过这时请求地址不符合当前城市,会提示当前号码所在城市已转移;

3g列表页分页点击post数据:这里我点了3g的第10页,看到
  1. pageInfo.currPage=9
复制代码
了吧,就是3g的分页参数,注意这里的
  1. searchNumberInfo.netType=01
复制代码
了,为什么是01,因为是请求的3g号码
  1. searchNumberInfo.order=0&searchNumberInfo.order2g=0&pageInfo.currPage=9&pageInfo.totalPager=88&formname=defaultnumber&searchNumberInfo.currPage2g=0&searchNumberInfo.totalPager2g=1011&searchNumberInfo.oldnumberCardId=&searchNumberInfo.oldnumberCardId2g=&formname=defaultnumber&searchNumberInfo.cardID=&searchNumberInfo.isreserve=&searchNumberInfo.saleCost=&searchNumberInfo.numbercountryId=&searchNumberInfo.numbercityId=&searchNumberInfo.ruleID=&searchNumberInfo.startCost=&searchNumberInfo.onnetlong=&searchNumberInfo.lowestcost=&searchNumberInfo.nCardcost=&searchNumberInfo.payType=&searchNumberInfo.processType=numbercard&searchNumberInfo.netType=01&searchNumberInfo.searchRuleID=&searchNumberInfo.numberStartCost=&searchNumberInfo.numberCardId=%E5%A6%82%E7%94%9F%E6%97%A5%2C%E7%BA%AA%E5%BF%B5%E6%97%A5%E7%AD%89&searchNumberInfo.searchRuleID2g=&searchNumberInfo.numberStartCost2g=&searchNumberInfo.numberCardId2g=
复制代码
2g列表页分页点击post数据:这里我点了2g的第5页,看到
  1. searchNumberInfo.currPage2g=4
复制代码
了吧,就是2g的分页参数,注意这里的
  1. searchNumberInfo.netType=00
复制代码
了,为什么是00,因为是请求的2g号码,这样3g,2g是通过searchNumberInfo.netType判断的,那摩当选择3g请求,对应的2g的参数应该是可以不要的,这样数据就不那摩多了
  1. searchNumberInfo.order=0&searchNumberInfo.order2g=0&pageInfo.currPage=9&pageInfo.totalPager=90&formname=defaultnumber&searchNumberInfo.currPage2g=4&searchNumberInfo.totalPager2g=1011&searchNumberInfo.oldnumberCardId=&searchNumberInfo.oldnumberCardId2g=&formname=defaultnumber&searchNumberInfo.cardID=&searchNumberInfo.isreserve=&searchNumberInfo.saleCost=&searchNumberInfo.numbercountryId=&searchNumberInfo.numbercityId=&searchNumberInfo.ruleID=&searchNumberInfo.startCost=&searchNumberInfo.onnetlong=&searchNumberInfo.lowestcost=&searchNumberInfo.nCardcost=&searchNumberInfo.payType=&searchNumberInfo.processType=numbercard&searchNumberInfo.netType=00&searchNumberInfo.searchRuleID=&searchNumberInfo.numberStartCost=&searchNumberInfo.numberCardId=%E5%A6%82%E7%94%9F%E6%97%A5%2C%E7%BA%AA%E5%BF%B5%E6%97%A5%E7%AD%89&searchNumberInfo.searchRuleID2g=&searchNumberInfo.numberStartCost2g=&searchNumberInfo.numberCardId2g=
复制代码
这个是我用get连接提交地址主城的获取2g分页的列表网址:里面的参数我做了裁剪,把和3g有关的参数去掉了,测试也可行
  1. http://shop.10010.com/number/doGetNumberList.action?&searchNumberInfo.numbercityId=008010&searchNumberInfo.order2g=0&searchNumberInfo.currPage2g=【2g分页】&searchNumberInfo.netType=00&searchNumberInfo.searchRuleID2g=&searchNumberInfo.numberStartCost2g=&searchNumberInfo.numberCardId2g=
复制代码
内容页自定义网址格式:
  1. http://shop.10010.com/number/searchOneNumber.action?searchNumberInfo.cardID=[参数1]&searchNumberInfo.numbercityId=[参数2]&searchNumberInfo.netType=00
复制代码
,注意这3个参数都不可以少,而且要符合当前城市和网络类型
是2g的,当然
  1. searchNumberInfo.netType=00
复制代码
,改为01提示系统繁忙,就是错误,
当然内容页的post数据我也做了裁剪,我想定位一个号码,有网络类型,所属城市,和号码id就足够了,而提交了其他的路3g当前页,总页数,2g当前页,总页数,号码的价格等参数是没有必要的,测试可以


这个是我用get连接提交地址主城的获取3g分页的列表网址:里面的参数我做了裁剪,把和2g有关的参数去掉了,测试也可行
  1. http://shop.10010.com/number/doGetNumberList.action?searchNumberInfo.order=0&pageInfo.currPage=【3g分页】&searchNumberInfo.netType=01&searchNumberInfo.searchRuleID=&searchNumberInfo.numberStartCost=&searchNumberInfo.numberCardId=
复制代码
路这个就是列表的第4页:可以浏览器打开,下载文件,记事本打开,就是该页请求返回的数据
  1. http://shop.10010.com/number/doGetNumberList.action?searchNumberInfo.order=0&pageInfo.currPage=3&searchNumberInfo.netType=01&searchNumberInfo.searchRuleID=&searchNumberInfo.numberStartCost=&searchNumberInfo.numberCardId=
复制代码
内容页自定义网址格式:
  1. http://shop.10010.com/number/searchOneNumber.action?searchNumberInfo.cardID=[参数1]&searchNumberInfo.numbercityId=[参数2]&searchNumberInfo.netType=01
复制代码
,注意这3个参数都不可以少,而且要符合当前城市和网络类型
是3g的,当然
  1. searchNumberInfo.netType=01
复制代码
,改为00提示系统繁忙,就是错误,同样做了裁剪


可以尝试用登录,用抓包的cooike,分别抓取不同城市的cooike,也许可行,同时进行多个城市的采集,要不不用登录,浏览器切换城市后,你采集时就是这个城市的号码






下面是post参数的说明,可以对应设置
  1. formname=defaultnumber--------表单名字

  2. searchNumberInfo.order------3g0按上架时间排序1,2互换按预存款排序,奇偶

  3. searchNumberInfo.order2g--------2g0按上架时间排序1,2互换按预存款排序,奇偶

  4. pageInfo.currPage-------3g当前页,等于输入页数-1

  5. pageInfo.totalPager=86-----3g总页数

  6. searchNumberInfo.currPage2g--------2g当前页,等于输入页数-1


  7. searchNumberInfo.totalPager2g=1012-------2g总页数


  8. searchNumberInfo.cardID---------号码

  9. searchNumberInfo.isreserve=00是保留ajax后设置


  10. searchNumberInfo.saleCost=0-------销售成本,ajax后设置

  11. searchNumberInfo.numbercountryId-------城市id

  12. searchNumberInfo.numbercityId ------------城市id

  13. searchNumberInfo.ruleID=-9999--------ajax后设置,靓号类型

  14. searchNumberInfo.startCost=0----------ajax后设置,预存款

  15. searchNumberInfo.onnetlong=0---------净长

  16. searchNumberInfo.lowestcost=0-----------最低价

  17. searchNumberInfo.nCardcost=0----------- nCardcost = infoList[attr].nCardcost==undefined?"0":infoList[attr].nCardcost;

  18. searchNumberInfo.payType=01--------支付类型,ajax后设置

  19. searchNumberInfo.processType=numbercard--------

  20. searchNumberInfo.netType=01---------网络类型     00:2g   01:3g选择3g 01,2g 00                                            
  21. searchNumberInfo.searchRuleID------------3g靓号类型
  22. searchNumberInfo.numberStartCost---------3g预存款

  23. searchNumberInfo.numberCardId-------3g自定义
  24. searchNumberInfo.searchRuleID2g-------2g靓号类型
  25. searchNumberInfo.numberStartCost2g--------2g预存款


  26. searchNumberInfo.numberCardId2g=--------2g自定义
复制代码
这个网站很整洁,还有注释,分析就比较方便,主要的几个js文件 searchnumber ;jquery.ajaxpager3g;jquery.ajaxpager2g;jquery.cookie;left;mydata

说的很多,要采集这个站这些参数的意识必须搞明白,才可以任意采集


本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有帐号?加入会员

x

评分

1

查看全部评分

发表于 2010-12-26 22:42:59 | 显示全部楼层
高手啊 但是新手未必看得懂啊
发表于 2010-12-26 23:56:04 | 显示全部楼层
楼主辛苦了
发表于 2010-12-27 14:17:46 | 显示全部楼层
直接用你那个规则采不了呀?
发表于 2010-12-27 21:43:53 | 显示全部楼层
这么楼主,真是有空啊.总是免费给人做事.佩服.
发表于 2011-1-19 11:09:27 | 显示全部楼层
这样的精神给力啊,支持啊
发表于 2011-2-17 11:04:07 | 显示全部楼层
楼主解释得非常详细。
发表于 2011-3-1 15:41:52 | 显示全部楼层
高手啊,现在还看不明白
发表于 2011-3-11 12:05:07 | 显示全部楼层
给力!!!!!!!
    虽然不是非常明白  !但是让我迷惑多天的问题有了解决方案了  大力支持
发表于 2011-3-27 13:27:30 | 显示全部楼层
顶!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
您需要登录后才可以回帖 登录 | 加入会员

本版积分规则

温馨提示:建议您联系官方定制服务,通过官方支付方式完成支付。您与其他非官方账号发生的交易,我方概不承担责任。网络有风险,交易需谨慎

QQ| 手机版|Archiver| 火车采集器官方站

Copyright © 2001-2013 Comsenz Inc.  Template by Comeings! All Rights Reserved.

Powered by Discuz! X3.4( 皖ICP备06000549 )

快速回复 返回顶部 返回列表