Ⅰ php如何防止网站内容被采集
1、限制IP地址单位时间的访问次数
分析:没有哪个常人一秒钟内能访问相同网站5次,除非是程序访问,而有这种喜好的,就剩下搜索引擎爬虫和讨厌的采集器了。
弊端:一刀切,这同样会阻止搜索引擎对网站的收录
适用网站:不太依靠搜索引擎的网站
采集器会怎么做:减少单位时间的访问次数,减低采集效率
2、屏蔽ip
分析:通过后台计数器,记录来访者ip和访问频率,人为分析来访记录,屏蔽可疑Ip。
弊端:似乎没什么弊端,就是站长忙了点
适用网站:所有网站,且站长能够知道哪些是google或者网络的机器人
采集器会怎么做:打游击战呗!利用ip代理采集一次换一次,不过会降低采集器的效率和网速(用代理嘛)。
3、利用js加密网页内容
Note:这个方法我没接触过,只是从别处看来
分析:不用分析了,搜索引擎爬虫和采集器通杀
适用网站:极度讨厌搜索引擎和采集器的网站
采集器会这么做:你那么牛,都豁出去了,他就不来采你了
4、网页里隐藏网站版权或者一些随机垃圾文字,这些文字风格写在css文件中
分析:虽然不能防止采集,但是会让采集后的内容充满了你网站的版权说明或者一些垃圾文字,因为一般采集器不会同时采集你的css文件,那些文字没了风格,就显示出来了。
适用网站:所有网站
采集器会怎么做:对于版权文字,好办,替换掉。对于随机的垃圾文字,没办法,勤快点了。
5、用户登录才能访问网站内容
分析:搜索引擎爬虫不会对每个这样类型的网站设计登录程序。听说采集器可以针对某个网站设计模拟用户登录提交表单行为。
适用网站:极度讨厌搜索引擎,且想阻止大部分采集器的网站
采集器会怎么做:制作拟用户登录提交表单行为的模块
Ⅱ 爬虫与反爬虫技术
互联网的快速进步,离不开爬虫的贡献,但同时也潜藏着一些问题,尤其是恶意爬虫的侵扰。爬虫是什么?它是如何获取数据?如何防止被爬取?本文将深入解析这些问题。
互联网站点的流量中,30%至60%来源于爬虫,其中友好爬虫如搜索引擎、广告程序等与恶意爬虫并存。恶意爬虫对网站业务安全构成威胁,可能窃取核心文本、扰乱市场秩序、降低网站性能。为抵御恶意爬虫,出现了反爬虫技术,分为被动防御与主动防御。
被动防御主要通过检测HTTP请求头、封禁访问频率过高的IP地址。然而,这种方法存在缺陷,如检测流程单一、误判率高等。主动防御则通过动态变换网页底层代码,提升攻击难度,实现全方位防护。
网络爬虫获取数据的基本流程包括解析URL、发送HTTP请求、解析网页内容等步骤。网络爬虫架构中,种子URL作为起点,通过读取、解析、下载、存储、提取新URL等过程,直至待抓取队列为空。
基于自定义cookie的检测策略是主动抵御恶意爬虫的一种方式。通过在网站接口中增加加密参数,浏览器执行返回的JS代码生成时效性、机密性cookie。正常用户与恶意爬虫的交互过程存在差异,如真实的浏览器存在bug,而爬虫无法生成正确的cookie。此策略结合JavaScript混淆技术,代码可读性大幅降低。
JS代码混淆技术包括变量混淆、字符串混淆、控制流平坦化、无用代码注入、禁用控制台输出、调试保护、域名锁定等。混淆技术可以混淆代码结构、隐藏明文字符串、增加代码执行难度,达到保护目的。
JavaScript-obfuscator混淆工具提供代码混淆功能,输出压缩、混淆后的JS代码,降低可读性。混淆后代码结构包含大数组、数组移位、解密函数、核心代码、无限debugger自执行函数+死代码注入。混淆强度取决于这四段代码强度。常用混淆工具有YUI Compressor、Google Closure Compiler、UglifyJS、JScrambler等。
爬虫与反爬虫技术在互联网发展中互相影响。反爬虫技术正朝着综合性安全系统发展,以智能交互、实时计算、模型分析等能力应对挑战。未来,随着监管加强,爬虫技术的使用将更加规范,互联网环境将更加健康。
Ⅲ 如何应付不知名的爬虫骚扰
一、手工识别和拒绝爬虫的访问
有相当多的爬虫对网站会造成非常高的负载,因此识别爬虫的来源IP是很容易的事情。最简单的办法就是用netstat检查80端口的连接:
C代码 netstat -nt | grep youhostip:80 | awk '{print $5}' | awk -F":" '{print $1}'| sort | uniq -c | sort -r -n netstat -nt | grep youhostip:80 | awk '{print $5}' | awk -F":" '{print $1}'| sort | uniq -c | sort -r -n
这行shell可以按照80端口连接数量对来源IP进行排序,这样可以直观的判断出来网页爬虫。一般来说爬虫的并发连接非常高。
如果使用lighttpd做Web Server,那么就更简单了。lighttpd的mod_status提供了非常直观的并发连接的信息,包括每个连接的来源IP,访问的URL,连接状态和连接时间等信息,只要检查那些处于handle-request状态的高并发IP就可以很快确定爬虫的来源IP了。
拒绝爬虫请求既可以通过内核防火墙来拒绝,也可以在web server拒绝,比方说用iptables拒绝:
C代码 iptables -A INPUT -i eth0 -j DROP -p tcp --dport 80 -s 84.80.46.0/24 iptables -A INPUT -i eth0 -j DROP -p tcp --dport 80 -s 84.80.46.0/24
直接封锁爬虫所在的C网段地址。这是因为一般爬虫都是运行在托管机房里面,可能在一个C段里面的多台服务器上面都有爬虫,而这个C段不可能是用户宽带上网,封锁C段可以很大程度上解决问题。
有些人提出一种脑残的观点,说我要惩罚这些爬虫。我专门在网页里面设计动态循环链接页面,让爬虫掉进陷阱,死循环爬不出来,其实根本用不着设置陷阱,弱智爬虫对正常网页自己就爬不出来,这样做多此一举不说,而且会让真正的搜索引擎降低你的网页排名。而且运行一个爬虫根本不消耗什么机器资源,相反,真正宝贵的是你的服务器CPU资源和服务器带宽,简单的拒绝掉爬虫的请求是反爬虫最有效的策略。
二、通过识别爬虫的User-Agent信息来拒绝爬虫
有很多爬虫并不会以很高的并发连接爬取,一般不容易暴露自己;有些爬虫的来源IP分布很广,很难简单的通过封锁IP段地址来解决问题;另外还有很多各种各样的小爬虫,它们在尝试Google以外创新的搜索方式,每个爬虫每天爬取几万的网页,几十个爬虫加起来每天就能消耗掉上百万动态请求的资源,由于每个小爬虫单独的爬取量都很低,所以你很难把它从每天海量的访问IP地址当中把它准确的挖出来。
这种情况下我们可以通过爬虫的User-Agent信息来识别。每个爬虫在爬取网页的时候,会声明自己的User-Agent信息,因此我们就可以通过记录和分析User-Agent信息来挖掘和封锁爬虫。我们需要记录每个请求的User-Agent信息,对于Rails来说我们可以简单的在app/controllers/application.rb里面添加一个全局的before_filter,来记录每个请求的User-Agent信息:
Ruby代码 logger.info "HTTP_USER_AGENT #{request.env["HTTP_USER_AGENT"]}" logger.info "HTTP_USER_AGENT #{request.env["HTTP_USER_AGENT"]}"
然后统计每天的proction.log,抽取User-Agent信息,找出访问量最大的那些User-Agent。要注意的是我们只关注那些爬虫的User-Agent信息,而不是真正浏览器User-Agent,所以还要排除掉浏览器User-Agent,要做到这一点仅仅需要一行shell:
Ruby代码 grep HTTP_USER_AGENT proction.log | grep -v -E 'MSIE|Firefox|Chrome|Opera|Safari|Gecko' | sort | uniq -c | sort -r -n | head -n 100 > bot.log grep HTTP_USER_AGENT proction.log | grep -v -E 'MSIE|Firefox|Chrome|Opera|Safari|Gecko' | sort | uniq -c | sort -r -n | head -n 100 > bot.log
统计结果类似这样:
C代码 57335 HTTP_USER_AGENT Baispider+(+ http://www..com/search/spider.htm)56639 HTTP_USER_AGENT Mozilla/5.0 (compatible; Googlebot/2.1; + http://www.google.com/bot.html)42610 HTTP_USER_AGENT Mediapartners-Google 19131 HTTP_USER_AGENT msnbot/2.0b (+ http://search.msn.com/msnbot.htm)57335 HTTP_USER_AGENT Baispider+(+ http://www..com/search/spider.htm) 56639 HTTP_USER_AGENT Mozilla/5.0 (compatible; Googlebot/2.1; + http://www.google.com/bot.html) 42610 HTTP_USER_AGENT Mediapartners-Google 19131 HTTP_USER_AGENT msnbot/2.0b (+ http://search.msn.com/msnbot.htm)
从日志就可以直观的看出每个爬虫的请求次数。要根据User-Agent信息来封锁爬虫是件很容易的事情,lighttpd配置如下:
C代码 $HTTP["useragent"] =~ "qihoobot|^Java|Commons-HttpClient|Wget|^PHP|Ruby|Python" { url.rewrite = ( "^/(.*)" => "/crawler.html" ) } $HTTP["useragent"] =~ "qihoobot|^Java|Commons-HttpClient|Wget|^PHP|Ruby|Python" { url.rewrite = ( "^/(.*)" => "/crawler.html" ) }
使用这种方式来封锁爬虫虽然简单但是非常有效,除了封锁特定的爬虫,还可以封锁常用的编程语言和HTTP类库的User-Agent信息,这样就可以避免很多无谓的程序员用来练手的爬虫程序对网站的骚扰。
还有一种比较常见的情况,就是某个搜索引擎的爬虫对网站爬取频率过高,但是搜索引擎给网站带来了很多流量,我们并不希望简单的封锁爬虫,仅仅是希望降低爬虫的请求频率,减轻爬虫对网站造成的负载,那么我们可以这样做:
C代码 $HTTP["user-agent"] =~ "Baispider+" { connection.delay-seconds = 10 } $HTTP["user-agent"] =~ "Baispider+" { connection.delay-seconds = 10 }
对网络的爬虫请求延迟10秒钟再进行处理,这样就可以有效降低爬虫对网站的负载了。
三、通过网站流量统计系统和日志分析来识别爬虫
有些爬虫喜欢修改User-Agent信息来伪装自己,把自己伪装成一个真实浏览器的User-Agent信息,让你无法有效的识别。这种情况下我们可以通过网站流量系统记录的真实用户访问IP来进行识别。
主流的网站流量统计系统不外乎两种实现策略:一种策略是在网页里面嵌入一段js,这段js会向特定的统计服务器发送请求的方式记录访问量;另一种策略是直接分析服务器日志,来统计网站访问量。在理想的情况下,嵌入js的方式统计的网站流量应该高于分析服务器日志,这是因为用户浏览器会有缓存,不一定每次真实用户访问都会触发服务器的处理。但实际情况是,分析服务器日志得到的网站访问量远远高于嵌入js方式,极端情况下,甚至要高出10倍以上。
现在很多网站喜欢采用awstats来分析服务器日志,来计算网站的访问量,但是当他们一旦采用Google Analytics来统计网站流量的时候,却发现GA统计的流量远远低于awstats,为什么GA和awstats统计会有这么大差异呢?罪魁祸首就是把自己伪装成浏览器的网络爬虫。这种情况下awstats无法有效的识别了,所以awstats的统计数据会虚高。
其实作为一个网站来说,如果希望了解自己的网站真实访问量,希望精确了解网站每个频道的访问量和访问用户,应该用页面里面嵌入js的方式来开发自己的网站流量统计系统。自己做一个网站流量统计系统是件很简单的事情,写段服务器程序响应客户段js的请求,分析和识别请求然后写日志的同时做后台的异步统计就搞定了。
通过流量统计系统得到的用户IP基本是真实的用户访问,因为一般情况下爬虫是无法执行网页里面的js代码片段的。所以我们可以拿流量统计系统记录的IP和服务器程序日志记录的IP地址进行比较,如果服务器日志里面某个IP发起了大量的请求,在流量统计系统里面却根本找不到,或者即使找得到,可访问量却只有寥寥几个,那么无疑就是一个网络爬虫。
分析服务器日志统计访问最多的IP地址段一行shell就可以了:
C代码 grep Processing proction.log | awk '{print $4}' | awk -F'.' '{print $1"."$2"."$3".0"}' | sort | uniq -c | sort -r -n | head -n 200 > stat_ip.log grep Processing proction.log | awk '{print $4}' | awk -F'.' '{print $1"."$2"."$3".0"}' | sort | uniq -c | sort -r -n | head -n 200 > stat_ip.log
然后把统计结果和流量统计系统记录的IP地址进行对比,排除真实用户访问IP,再排除我们希望放行的网页爬虫,比方Google,网络,微软msn爬虫等等。最后的分析结果就就得到了爬虫的IP地址了。以下代码段是个简单的实现示意:
Ruby代码 whitelist = [] IO.foreach("#{RAILS_ROOT}/lib/whitelist.txt") { |line| whitelist << line.split[0].strip if line } realiplist = [] IO.foreach("#{RAILS_ROOT}/log/visit_ip.log") { |line| realiplist << line.strip if line } iplist = [] IO.foreach("#{RAILS_ROOT}/log/stat_ip.log") do |line| ip = line.split[1].strip iplist << ip if line.split[0].to_i > 3000 && !whitelist.include?(ip) && !realiplist.include?(ip) end Report.deliver_crawler(iplist) whitelist = [] IO.foreach("#{RAILS_ROOT}/lib/whitelist.txt") { |line| whitelist << line.split[0].strip if line } realiplist = [] IO.foreach("#{RAILS_ROOT}/log/visit_ip.log") { |line| realiplist << line.strip if line } iplist = [] IO.foreach("#{RAILS_ROOT}/log/stat_ip.log") do |line| ip = line.split[1].strip iplist << ip if line.split[0].to_i > 3000 && !whitelist.include?(ip) && !realiplist.include?(ip) end Report.deliver_crawler(iplist)
分析服务器日志里面请求次数超过3000次的IP地址段,排除白名单地址和真实访问IP地址,最后得到的就是爬虫IP了,然后可以发送邮件通知管理员进行相应的处理。
四、网站的实时反爬虫防火墙实现策略
通过分析日志的方式来识别网页爬虫不是一个实时的反爬虫策略。如果一个爬虫非要针对你的网站进行处心积虑的爬取,那么他可能会采用分布式爬取策略,比方说寻找几百上千个国外的代理服务器疯狂的爬取你的网站,从而导致网站无法访问,那么你再分析日志是不可能及时解决问题的。所以必须采取实时反爬虫策略,要能够动态的实时识别和封锁爬虫的访问。
要自己编写一个这样的实时反爬虫系统其实也很简单。比方说我们可以用memcached来做访问计数器,记录每个IP的访问频度,在单位时间之内,如果访问频率超过一个阀值,我们就认为这个IP很可能有问题,那么我们就可以返回一个验证码页面,要求用户填写验证码。如果是爬虫的话,当然不可能填写验证码,所以就被拒掉了,这样很简单就解决了爬虫问题。
用memcache记录每个IP访问计数,单位时间内超过阀值就让用户填写验证码,用Rails编写的示例代码如下:
Ruby代码 ip_counter = Rails.cache.increment(request.remote_ip) if !ip_counter Rails.cache.write(request.remote_ip, 1, :expires_in => 30.minutes) elsif ip_counter > 2000 render :template => 'test', :status => 401 and return false end ip_counter = Rails.cache.increment(request.remote_ip) if !ip_counter Rails.cache.write(request.remote_ip, 1, :expires_in => 30.minutes) elsif ip_counter > 2000 render :template => 'test', :status => 401 and return false end
这段程序只是最简单的示例,实际的代码实现我们还会添加很多判断,比方说我们可能要排除白名单IP地址段,要允许特定的User-Agent通过,要针对登录用户和非登录用户,针对有无referer地址采取不同的阀值和计数加速器等等。
此外如果分布式爬虫爬取频率过高的话,过期就允许爬虫再次访问还是会对服务器造成很大的压力,因此我们可以添加一条策略:针对要求用户填写验证码的IP地址,如果该IP地址短时间内继续不停的请求,则判断为爬虫,加入黑名单,后续请求全部拒绝掉。为此,示例代码可以改进一下:
Ruby代码 before_filter :ip_firewall, :except => :test def ip_firewall render :file => "#{RAILS_ROOT}/public/403.html", :status => 403 if BlackList.include?(ip_sec) end before_filter :ip_firewall, :except => :test def ip_firewall render :file => "#{RAILS_ROOT}/public/403.html", :status => 403 if BlackList.include?(ip_sec) end
我们可以定义一个全局的过滤器,对所有请求进行过滤,出现在黑名单的IP地址一律拒绝。对非黑名单的IP地址再进行计数和统计:
Ruby代码 ip_counter = Rails.cache.increment(request.remote_ip) if !ip_counter Rails.cache.write(request.remote_ip, 1, :expires_in => 30.minutes) elsif ip_counter > 2000 crawler_counter = Rails.cache.increment("crawler/#{request.remote_ip}") if !crawler_counter Rails.cache.write("crawler/#{request.remote_ip}", 1, :expires_in => 10.minutes) elsif crawler_counter > 50 BlackList.add(ip_sec) render :file => "#{RAILS_ROOT}/public/403.html", :status => 403 and return false end render :template => 'test', :status => 401 and return false end ip_counter = Rails.cache.increment(request.remote_ip) if !ip_counter Rails.cache.write(request.remote_ip, 1, :expires_in => 30.minutes) elsif ip_counter > 2000 crawler_counter = Rails.cache.increment("crawler/#{request.remote_ip}") if !crawler_counter Rails.cache.write("crawler/#{request.remote_ip}", 1, :expires_in => 10.minutes) elsif crawler_counter > 50 BlackList.add(ip_sec) render :file => "#{RAILS_ROOT}/public/403.html", :status => 403 and return false end render :template => 'test', :status => 401 and return false end
如果某个IP地址单位时间内访问频率超过阀值,再增加一个计数器,跟踪他会不会立刻填写验证码,如果他不填写验证码,在短时间内还是高频率访问,就把这个IP地址段加入黑名单,除非用户填写验证码激活,否则所有请求全部拒绝。这样我们就可以通过在程序里面维护黑名单的方式来动态的跟踪爬虫的情况,甚至我们可以自己写个后台来手工管理黑名单列表,了解网站爬虫的情况。
这个策略已经比较智能了,但是还不够好!我们还可以继续改进:
1、用网站流量统计系统来改进实时反爬虫系统
还记得吗?网站流量统计系统记录的IP地址是真实用户访问IP,所以我们在网站流量统计系统里面也去操作memcached,但是这次不是增加计数值,而是减少计数值。在网站流量统计系统里面每接收到一个IP请求,就相应的cache.decrement(key)。所以对于真实用户的IP来说,它的计数值总是加1然后就减1,不可能很高。这样我们就可以大大降低判断爬虫的阀值,可以更加快速准确的识别和拒绝掉爬虫。
2、用时间窗口来改进实时反爬虫系统
爬虫爬取网页的频率都是比较固定的,不像人去访问网页,中间的间隔时间比较无规则,所以我们可以给每个IP地址建立一个时间窗口,记录IP地址最近12次访问时间,每记录一次就滑动一次窗口,比较最近访问时间和当前时间,如果间隔时间很长判断不是爬虫,清除时间窗口,如果间隔不长,就回溯计算指定时间段的访问频率,如果访问频率超过阀值,就转向验证码页面让用户填写验证码。
最终这个实时反爬虫系统就相当完善了,它可以很快的识别并且自动封锁爬虫的访问,保护网站的正常访问。不过有些爬虫可能相当狡猾,它也许会通过大量的爬虫测试来试探出来你的访问阀值,以低于阀值的爬取速度抓取你的网页,因此我们还需要辅助第3种办法,用日志来做后期的分析和识别,就算爬虫爬的再慢,它累计一天的爬取量也会超过你的阀值被你日志分析程序识别出来。
总之我们综合运用上面的四种反爬虫策略,可以很大程度上缓解爬虫对网站造成的负面影响,保证网站的正常访问。