本文目录一览:
如何在nginx上防止恶意的ddos抓取
自己写的网站,不知道为啥总是有很多恶意访问的ip,根本不是正常的用户访问之前也有想过是否可能是运营商的代理服务器出口ip,但是看起来好像也不像,先不管,ban掉再说
那如何来ban呢,规则比较简单,就是超过一个阈值之后,就用下面的iptables命令
iptables -I INPUT -s -j DROP
service iptables save
service iptables restart
那如何统计nginx的访问ip呢,目前来说比较简单就是读取nginx的access.log文件,然后分析一下,如果一天超过阈值,我们就执行上面的命令,ban掉ip。
有个问题是我们需要的是一直监视access.log 文件,而不是读一次,当然可以在每天快结束的时候事后来封住ip,但是这样不能给爬虫嚣张的气焰,所以
我觉得立即封掉是比较OK的。
之前写过一个类似tail读取一个文件的功能,就是打开的时候先定位到文件大小的位置,然后就开始循环读行来处理,这次的处理有点不一样,我是直接使用tail 把那个文件的流定位到我的程序的 sys.stdin ,这样就简单的可以读到所有的流了
tail /var/log/nginx/access.log | python .py
但是nginx的access.log每天都会做一次logrotate,它是怎么做的呢,nginx官网的推荐方式
mv access.log access.log.0
kill -USR1 `cat master.nginx.pid`
sleep 1
gzip access.log.0 # do something with access.log.0
我的vps上面使用的是logrotated来处理的,可以在/etc/logrotate.d/nginx
/var/log/nginx/*.log {
daily
missingok
rotate 52
compress
delaycompress
notifempty
create 640 nginx adm
sharedscripts
postrotate
[ -f /var/run/nginx.pid ] kill -USR1 `cat /var/run/nginx.pid`
endscript
}
这里表示的create表示文件会重新创建。其实这样老的文件就没有新数据了,但是因为使用的是tail,也没有eof, 这样直接读的时候会发现 file.readline() 的函数会卡住,导致程序假死,这样程序就不能主动退出了,后面选择了用select来处理,加了一个10秒的超时,从目前的流量来看,基本上每秒都好多的请求,10秒都没有数据就是出问题了。
while sys.stdin in select.select([sys.stdin], [], [], 10)[0]:
然后如果没有select上的话,说明基本上是nginx log文件rotate掉了,所以遇到这样的情况,我就直接跳出程序,然后把程序终结掉。终结掉怎么办呢,本来想在程序里面重新启动一下程序,但是感觉可能不妥,所以使用crontab来处理了,每隔2分钟检查一下,为了防止多次启动就用了flock来防止程序重新启动
*/2 * * * * flock -xn /dev/shm/blocker.lock -c "sh /srv/www/beauty/daemon/nginx_ip_blocker.sh"
这里附上代码
#coding=utf-8
import sys
import re
import os
import urllib
import urllib2
import datetime
import time, os
import logging
import json
import select
logging.basicConfig(level=logging.DEBUG, datefmt='%Y%m%d %H:%M:%S', format='[%(asctime)s] %(message)s')
"""
iptables -I INPUT -s -j DROP
service iptables save
service iptables restart
本脚本主要是用来把恶意访问nginx的ip ban掉的脚本
"""
MAX_IP=7000
def get_date():
return time.strftime("%Y%m%d")
def ban_one_ip(ip):
os.system("iptables -I INPUT -s %s -j DROP ; service iptables save ; service iptables restart"%ip)
def find_ip_and_ban():
for ip in ip_map:
if ip_map.get(ip)MAX_IP:
print "ban ip, count %s:%s"%(ip_map.get(ip),ip)
ip_map[ip] = 0
ban_one_ip(ip)
today = None
ip_map = {}
def process_log(lines):
global ip_map;
global today;
now = get_date()
if now != today:
today = now
ip_map = {}
for line in lines:
ip = line.split(" ")[0]
count = ip_map.get(ip,0)
count += 1
ip_map[ip]=count;
find_ip_and_ban()
COUNT=50
def main():
brk=False
while True:
tmp = 0;
lines =[]
brk=False
while sys.stdin in select.select([sys.stdin], [], [], 10)[0]:
line = sys.stdin.readline()
if not line:
brk=True
print 'read to eof'
break
lines.append(line)
tmp+=1
if tmpCOUNT:
break
else:
brk=True
print 'read time out'
break
process_log(lines)
print "read lines:%s"%len(lines)
if brk:
break
if brk:
print "break out"
if __name__ == "__main__":
main()
nginx怎么防止ddos攻击cc攻击等流量攻击
nginx防止攻击,分流量攻击和cc攻击,如果是拒绝服务,只能判断然后限制一个ip,只访问几次 1. ngx_http_limit_conn_module 可以用来限制单个IP的连接数 2. ngx_http_limit_req_module 可以用来限制单个IP每秒请求数 3. nginx_limit_speed_module 可以用来对IP限速 试试ngx_lua_waf 功能: 防止sql注入,本地包含,部分溢出,fuzzing测试,xss,SSRF等web攻击 防止svn/备份之类文件泄漏 防止ApacheBench之类压力测试工具的攻击 屏蔽常见的扫描黑客工具,扫描器 屏蔽异常的网络请求 屏蔽图片附件类目录php执行权限 防止webshell上传
如何设置nginx允许跨站请求?
添加如下location:123location / { add_header Access-Control-Allow-Origin *;}。会在响应头中添加Access-Control-Allow-Origin字段以允许跨域。
nginx简介
Nginx ("engine x") 是一个高性能的HTTP和 反向代理 服务器,也是一个IAP/POP3/SMTP 服务器。 Nginx 是由 Igor Sysoev 为俄罗斯访问量第二的 Rambler.ru 站点开发的,第一个公开版本0.1.0发布于2004年10月4日。其将源代码以类BSD许可证的形式发布,因它的稳定性、丰富的功能集、示例配置文件和低系统资源的消耗而闻名。2011年6月1日,nginx 1.0.4发布。
Nginx是一款轻量级的Web 服务器/反向代理服务器及电子邮件(IMAP/POP3)代理服务器,并在一个BSD-like 协议下发行。由俄罗斯的程序设计师Igor Sysoev所开发,供俄国大型的入口网站及搜索引擎Rambler(俄文:Рамблер)使用。其特点是占有内存少,并发能力强,事实上nginx的并发能力确实在同类型的网页服务器中表现较好,中国大陆使用nginx网站用户有:百度、新浪、网易、腾讯、 淘宝等。
nginx现在有什么方法防止跨站
Nginx防跨目录与跨站配置方法
Nginx有一个缺陷,就是没有像apache的php_value_basedir给我们限制php文件访问目录,PHP低版本下,fastcgi 模式
下open_base设置无效,PHP在PHP5.3.3以上已经增加了HOST配置,可以起到防跨站、跨目录的问题
如果你是PHP 5.3.3以上的版本,可以修改/usr/local/php/etc/php.ini在末尾里加入:
[HOST=111cn.net]
代码如下 复制代码
open_basedir=/home/wwwroot/111cn.net/:/tmp/
[PATH=/home/wwwroot/111cn.net]
open_basedir=/home/wwwroot/111cn.net/:/tmp/
修改好了。
最后重启下php-fpm:sudo /etc/init.d/php-fpm restart
OK,。这样设置后。就能增强系统的安全性,PHP目前,折腾也只能在他所在的目录下设置啦
如果你不是php5.3.3以上版本我们就只能如下操作了
1、解压php源代码不细说了。
2、执行编译./configure -- (自带参数)
3、修改源代码。此文件位于main/fopen_wrappers.c
代码如下 复制代码
/* {{{ php_check_open_basedir
*/
PHPAPI int php_check_open_basedir_ex(const char *path, int warn TSRMLS_DC)
{
/* Only check when open_basedir is available */
if (PG(open_basedir) *PG(open_basedir)) {
char *pathbuf;
char *ptr;
char *end;
char *env_doc_root;
if(PG(doc_root)){
env_doc_root = estrdup(PG(doc_root));
}
else{
env_doc_root = sapi_getenv("DOCUMENT_ROOT", sizeof("DOCUMENT_ROOT")-1 TSRMLS_CC);
}
if(env_doc_root){
int res_root = php_check_specific_open_basedir(env_doc_root, path TSRMLS_CC);
efree(env_doc_root);
if (res_root == 0) {
return 0;
}
if (res_root == -2) {
errno = EPERM;
return -1;
}
}
// 添加的内容结束
pathbuf = estrdup(PG(open_basedir));
ptr = pathbuf;
while (ptr *ptr) {
end = strchr(ptr, DEFAULT_DIR_SEPARATOR);
if (end != NULL) {
*end = '';
end++;
}
if (php_check_specific_open_basedir(ptr, path TSRMLS_CC) == 0) {
efree(pathbuf);
return 0;
}
ptr = end;
}
if (warn) {
php_error_docref(NULL TSRMLS_CC, E_WARNING, "open_basedir restriction in effect. File(%s) is not
within the allowed path(s): (%s)", path, PG(open_basedir));
}
efree(pathbuf);
errno = EPERM; /* we deny permission to open it */
return -1;
}
/* Nothing to check... */
return 0;
}
/* }}} */
然后执行
代码如下 复制代码
make ZEND_EXTRA_LIBS='-liconv' make install
cp php.ini-dist /usr/local/php/etc/php.ini最后修改php.ini中的open_basedir改为:open_basedir =
"/var/tmp/:/tmp/"