能搜到的 方法,無外乎判斷 Http_referer 是否來源於本站和在網頁裏換行和回車後面添加本站名稱和隨機字符串。這兩個方法對於略懂http協議和正則替換的兄弟來說,完全沒用。對於我所知的和網上常用的幾種方法具體分析如下:
1 判斷http_referer
http_referer是http頭中的一段,不管使用VB/VC 的 winsock / inet transfer 控件,還是 使用asp服務器就可以用的 xmlHttpRequest 對象 ( for ajax ) , 抑或是php socket 、python urllib2, 都可以輕易的修改http header , 從而直接修改 http_referer的值。最偷懶的做法就是,把http_referer賦值爲你的網站根url或訪問的頁面url。VB 中的 WebBrowser 控件更是不存在這個問題……大不了抓的慢一些就是了
此方法唯一有效的,可能對採用Adodb.Stream對象的抓取
2 加入隨機字串/本站名稱/url
對於固定字串,如本站名稱和url,很多成型的網頁採集程序都直接提供選項可以替換掉,實現起來也很容易。被採集方由於有在頁面內放置不可見元素和堆砌關鍵字的嫌疑,有可能還會被搜索引擎認爲作弊,這招很不可取~
對於隨機字串,直接用字符串替換是不可以的,但是如果結合頁面源碼合理的運用正則表達式,一樣可以破掉。比如:匹配 [/w]{,16}<br> ,替換爲空,就可以刪掉處於<br>之前的16位隨機字母、數字字符串
3 在網頁內加入能中斷頁面運行的腳本
在網頁中加入 諸如 <script>alert("xxx")</script> 之類的腳本,用以阻斷頁面執行和顯示。想出這個方法來的兄弟一定很bt~ 但是又有些可笑。只要不是抓完就直接顯示頁面的,這個方法根本沒用。具體原因不再多說。而且這樣對於被採集方網站的用戶體驗是個很壞的方面。
-------------------------------------------------------------------------------------------------
4 我的方法
前幾日要求寫一個放採集的程序。要求使一個打印內容的列表頁面防採集。前思後想,認爲只有一個辦法,就是打亂表格的輸出次序,採用隨機順序輸出,在客戶端使用js操作dom調換順序。這樣,服務器端輸出的html中的表格非常的亂,但是客戶查看和打印時又能正常顯示。缺點是,正確的順序依然要輸出到頁面上,如果採集方根據這個規律也將表格內容重新排序,仍然是可以讀取的。
實現方法如下
dim c
c = a
a = b
b = c
end function
dim nam,tempRND,orders
redim orders(nRS + 1)
redim order(UBound(aRS,1))
orders(0) = join(array(1,2,3,4,5,6,7,8,9,0),",")
randomize
rnd()
i = 0
do while i <= nRS
for j = 0 to ubound(order)
order(j) = j
next
for j = 0 to ubound(order)' step 2
tempRND = int(rnd() * (UBound(order) + 1))
call swap(order(j),order(tempRND))
next
orders(i + 1) = join(order,",")
%>
<tr>
<%
' for j = 0 to UBound(order)
response.write "<td >"
response.Write aRS(order(j),i)
response.write "</td>"
next
' Response.write "</tr><tr>"
%>
</tr>
<%
i = i + 1
loop
%>
var aOrd = [[<%= join(orders,"],[") %>]];
reOrder("tblList",aOrd);
</script>
客戶端重新組合方法如下:
{
var o = document.getElementById(sObj).childNodes[0];
{
try{
var t = o.childNodes.length;
}catch(E){
alert(E.description);
return;
}
}
for(var i = 1; i < o.childNodes.length ;i++){
var aReOrder = new Array();
var tr = o.childNodes[i];
for(var j = 0; tr.hasChildNodes() ;j++){
aReOrder[aOrder[i][j]] = tr.removeChild(tr.childNodes[0]);
}
for(var j = 0; j < aReOrder.length;j++){
tr.appendChild(aReOrder[j]);
}
}
}
</script>
雖然這個不是完全一勞永逸的方法,至少可以難倒大批的不會js的程序員……