当前位置: 代码网 > 服务器>服务器>Linux > nginx优化与防盗链配置过程

nginx优化与防盗链配置过程

2026年03月02日 Linux 我要评论
隐藏版本号隐藏nginx的版本号是一种安全实践,因为通过查看服务器的版本号,潜在攻击者可能会利用已知的漏洞来攻击服务器。curl -i http://192.168.41.10通过nginx配置文件v

隐藏版本号

隐藏nginx的版本号是一种安全实践,因为通过查看服务器的版本号,潜在攻击者可能会利用已知的漏洞来攻击服务器。

curl -i http://192.168.41.10

通过nginx配置文件

vim /usr/local/nginx/conf/nginx.conf

在nginx的配置文件(通常是nginx.conf)中添加或修改server_tokens指令。这个指令控制nginx在http响应头中是否显示版本号。

http {
    server_tokens off;
    # other configurations...
}

server_tokens设置为off将隐藏版本号。在修改配置后,重新加载nginx配置以使更改生效。

修改nginx.h源码文件重新编译安装

vim /opt/nginx-1.22.0/src/core/nginx.h
#define nginx_version  "1.22.0"

可以将其修改为一个自定义的字符串,例如:

#define nginx_version  "custom version"

重新编译

cd /opt/nginx-1.22.0/
./configure --prefix=/usr/local/nginx --user=nginx --group=nginx --with-http_stub_status_module
make && make install

分割日志文件

基于原日志文件分割当天日志

建立脚本

#!/bin/bash
#获取当前的日期,年-月-日
d=$(date +%y-%m-%d)

#定义存储的目录
dir="/usr/local/nginx/logs"

#定义分割的源日志
logs_file="/usr/local/nginx/logs/access.log"
logs_error="/usr/local/nginx/logs/error.log"

#定义出nginx的pid文件
pid_file='/usr/local/nginx/run/nginx.pid'

if [ ! -d "$dir" ]
then
  mkdir -p $dir
fi

#mv来对原日志文件重命名
mv ${logs_file} ${dir}/access_${d}.log
mv ${logs_error} ${dir}/error_${d}.log
#mv /usr/local/ngin/logs/access.log /usr/local/nginx/logs/access_2023_11_15.log

kill -usr1 $(cat ${pid_file})
#向nginx程序传送一个信号 usr1,让nginx重新生成一个新的日志文件

find ${dir} -mtime +30 -exec rm -rf {} \;
#把30天之前修改过的文件,删除。清楚一下过期的日志文件。

赋权执行脚本

chmod 777 nginxlog.sh
. nginxlog.sh

设置定时任务

crontab -e
0 0 * * * /opt/nginxlog.sh  

网页压缩

启用压缩:

在 nginx 配置文件中,你需要启用 gzip 模块。通常,这个模块已经默认启用,但你可以确保以下配置存在:

gzip on;

这将启用压缩功能。

设置压缩类型:

使用 gzip_types 指令来指定需要压缩的 mime 类型。例如:

gzip_types text/plain text/css application/json application/javascript text/xml application/xml application/xml+rss text/javascript;

这是一个示例,你可以根据你的应用程序的需要添加或移除适当的 mime 类型。

压缩级别:

通过 gzip_comp_level 设置压缩级别。级别范围是 1 到 9,级别越高,压缩效果越好,但 cpu 消耗也会增加。默认级别是 1。

gzip_comp_level 6;

最小压缩文件大小:

使用 gzip_min_length 指令设置允许压缩的最小文件大小。小于该大小的文件将不会被压缩。

gzip_min_length 1000;

压缩缓冲区大小:

使用 gzip_buffers 指令设置压缩缓冲区的大小。

gzip_buffers 4 16k;

这里的 4 表示缓冲区的数量,16k 表示每个缓冲区的大小。

禁用压缩的 user-agent:

如果有一些 user-agent 不支持压缩,你可以使用 gzip_disable 指令将其排除。

gzip_disable "msie [1-6]\.";

上述配置将禁用对 msie 6 及以下版本的 internet explorer 的压缩。

启用压缩的文件扩展名:

使用 gzip_proxied 指令来定义启用压缩的文件扩展名。

gzip_proxied any;

这将允许任何请求启用压缩。

开启压缩的 http 版本:

使用 gzip_http_version 指令可以指定在哪个 http 版本下启用压缩。

gzip_http_version 1.1;

重启 nginx:

修改配置后,确保重新加载或重启 nginx 以使更改生效:

sudo systemctl reload nginx

请注意,启用压缩可能会增加 cpu 的负担,因此在生产环境中应该根据服务器的性能和网络带宽来调整相关配置。适当的配置可以显著提高页面加载速度,特别是对于具有大量文本内容的网页。

图片缓存

nginx 可以通过配置来缓存图片以提高网站性能和加载速度。这种缓存可以减少对后端服务器的请求,提升用户体验

设置缓存路径:

首先,需要定义用于存储缓存的路径。可以在 nginx 配置文件中添加类似如下的配置:

proxy_cache_path /path/to/cache levels=1:2 keys_zone=my_cache:10m max_size=10g inactive=60m use_temp_path=off;
  • /path/to/cache 是用于存储缓存的路径。
  • levels=1:2 指定存储目录的层次结构。
  • keys_zone=my_cache:10m 定义缓存键值对的名称和大小。
  • max_size=10g 设置缓存的最大大小。
  • inactive=60m 定义缓存文件在一定时间内未被访问时被认为是不活跃的,nginx会删除这些不活跃的缓存文件。
  • use_temp_path=off 禁用临时路径。

配置缓存规则:

接下来,需要为图片文件配置缓存规则。在 nginx 配置文件中的 server 块中添加类似如下的配置:

location ~* \.(png|jpg|jpeg|gif|ico)$ {
    proxy_cache my_cache;
    proxy_cache_valid 200 60m;
    proxy_cache_key "$scheme$request_method$host$request_uri";
    proxy_pass http://backend_server;
}
  • location 指定了匹配图片文件的位置。
  • proxy_cache my_cache; 将图片文件缓存到名为 my_cache 的缓存区域。
  • proxy_cache_valid 200 60m; 定义缓存的有效期,这里是 60 分钟。
  • proxy_cache_key 设置缓存键值,这里使用了一些请求信息作为键值。
  • proxy_pass 定义了后端服务器的地址。

重启 nginx:

修改配置后,确保重新加载或重启 nginx 以使更改生效:

sudo systemctl reload nginx

这样配置后,nginx 将会缓存图片文件,当有用户请求图片时,nginx 会先检查缓存中是否存在对应的文件,如果存在且在有效期内,就会直接返回缓存的文件,而不去请求后端服务器。这有助于提高网站性能和减少对服务器的请求压力。记得根据实际需求和服务器资源进行适当的调整。

并发设置,连接超时

nginx 的并发设置涉及到多个配置参数,其中最重要的是 worker_processesworker_connections。这两个参数用于配置 nginx 的工作进程和每个工作进程的最大并发连接数。

worker_processes:

worker_processes 指令用于设置 nginx 启动时的工作进程数。一般来说,可以设置为服务器的 cpu 核心数,以充分利用系统资源。例如,如果你的服务器有 4 个 cpu 核心,可以设置为:

worker_processes 4;

注意:设置过多的工作进程可能会导致系统资源不足,而设置过少可能无法充分利用服务器性能。建议根据服务器的硬件配置和负载情况进行调整。

worker_connections:

worker_connections 指令用于设置每个工作进程的最大并发连接数。这个值的设定取决于服务器硬件资源和系统的 ulimit(打开文件描述符限制)。通常,可以设置为 1024 或更高。例如:

events {
    worker_connections 1024;
}

在高并发情况下,可能需要进一步增加这个值,但要确保不超过系统的 ulimit 限制。

还可以通过修改系统的 ulimit 设置来提高文件描述符的限制。例如,在 linux 系统中,可以通过以下命令修改:

ulimit -n 4096

这样会将打开文件描述符的限制提高到 4096。

优化其他配置:

在高并发环境下,还可以通过优化其他一些配置来提高性能,如:

  • 启用事件驱动模型:在 nginx.conf 文件中,确保 use epoll;use kqueue;(根据系统类型)已启用。
  • 启用 sendfile:在 nginx.conf 文件中,确保 sendfile on; 已启用。
  • 启用 tcp nodelay:在 nginx.conf 文件中,确保 tcp_nodelay on; 已启用。
  • 启用 tcp nopush:在 nginx.conf 文件中,确保 tcp_nopush on; 已启用。

总体而言,nginx 的并发设置需要根据具体的服务器硬件、网络环境和应用负载来进行调整,因此需要不断优化和测试以达到最佳性能。

http {
...... 
    keepalive_timeout 65 180;  #指定tcp链接最多可以保持65秒
    client_header_timeout 80;  #请求头
    client_body_timeout 80;    #请求体
...... 
} 

keepalive_timeout 65 180;

  • 这个指令用于配置http keep-alive连接的超时时间。
  • 第一个参数 65 表示在连接空闲时间超过 65 秒后,连接可能被关闭。
  • 第二个参数 180 表示一个连接上允许的最大空闲时间,即连接在空闲时间达到 180 秒后,可能被强制关闭。

client_header_timeout 80;

  • 这个指令用于配置客户端发送http请求头的超时时间。
  • 参数 80 表示客户端在发送请求头的过程中,如果在 80 秒内没有完成发送,连接可能被关闭。
  • 如果客户端在指定时间内没有发送任何内容,nginx 返回 http 408(request timed out)。

client_body_timeout 80;

  • 这个指令用于配置客户端发送http请求体的超时时间。
  • 参数 80 表示客户端在发送请求体的过程中,如果在 80 秒内没有完成发送,连接可能被关闭。

连接保持与会话保持

连接保持(connection keep-alive):

特点:

  • 是一种通过在单个tcp连接上保持多个http请求/响应的机制。

  • 允许在同一连接上发送多个请求,而无需为每个请求都重新建立tcp连接,从而减少了连接的开销。

  • 提高了性能,尤其是在多个资源需要加载的情况下,因为可以重用同一连接。

实现:

  • 通过在http头中包含 connection: keep-alive 字段来实现。

  • web服务器和客户端都必须支持并启用连接保持。

会话保持(session persistence):

特点:

  • 是确保用户的一系列请求都被路由到同一台服务器的机制。

  • 在负载均衡环境中,避免用户在不同服务器之间失去会话状态。

  • 常用于需要用户保持登录状态或其他会话信息的应用程序。

实现:

  • 通过在负载均衡器上维护会话信息,确保相同用户的请求都被路由到同一台服务器。

  • 常见的实现方式包括基于ip地址的粘滞会话(sticky sessions)或使用会话标识符在服务器之间进行共享。

区别:

焦点不同:

  • 连接保持关注的是在单个tcp连接上重用http请求和响应,以减少连接建立和关闭的开销。

  • 会话保持关注的是确保用户的所有请求都被路由到同一台服务器,以保持应用程序的会话状态。

应用场景不同:

  • 连接保持通常用于提高性能,减少重复的tcp连接建立和关闭。

  • 会话保持通常用于确保在负载均衡环境中保持用户会话状态。

实现方式不同:

  • 连接保持是通过http头中的 connection: keep-alive 实现的。

  • 会话保持通常是在负载均衡器上实现的,使用ip地址、会话标识符等来确保请求路由到同一台服务器。

在某些情况下,这两个机制可能会一起使用,以提供更好的性能和用户体验。

nginx中当cpu频繁切换时怎么办

查看cpu的核心数,根据核心数来设置工作进程数

查看cpu核数
cat /proc/cpuinfo |grep processor|wc -l

cat /proc/cpuinfo |grep -c processor

cat /proc/cpuinfo | grep -c "physical id"

worker_processes最多开启8个,8个以上性能就不会再提升了,而且稳定性会变的更低,因此8个进程够用了

可以使用进程绑定。进程绑定是指将一个进程或线程绑定到特定的cpu核心上,以确保它只在该核心上运行。这可以提高性能,减少由于上下文切换引起的开销。

vim /usr/local/nginx/conf/nginx.conf
worker_processes  4;                #修改为核数相同或者2倍
worker_cpu_affinity 0001 0010 0100 1000;    
#worker_cpu_affinity 是一个用于设置 worker 进程绑定到指定 cpu 的指令。
将 nginx worker 进程绑定到特定的 cpu 核心,以提高性能和避免 cpu cache 的伪共享。

通过将 worker 进程绑定到特定的 cpu 核心,可以减少 cpu 切换(context switching)的开销,
并确保 worker 进程在一个独立的 cpu 核心上运行,避免了不同进程间的 cpu cache 竞争,从而提高了整体性能    

time_wait 优化

tcp连接生命周期(状态)

tcp(传输控制协议)是一种面向连接的协议,它在通信的两端创建一个可靠的、全双工的通信。tcp连接的状态是在通信的不同阶段中表示连接状态的一种标志。以下是常见的tcp连接状态:

  • closed(关闭): 初始状态,表示tcp连接未打开。
  • listen(监听): 服务器端的某个套接字处于监听状态,可以接受客户端的连接请求。
  • syn_sent(同步已发送): 客户端发送连接请求(syn)后等待确认。
  • syn_received(同步已接收): 服务器端收到客户端的连接请求并发送确认。
  • established(已建立): 连接已经建立,双方可以进行数据传输。
  • finwait1(等待对方的结束连接请求): 一方(通常是客户端)发送了结束连接请求,等待对方的确认。
  • finwait2(等待对方的结束连接请求): 一方接收到对方的结束连接请求,等待对方的确认。
  • close_wait(等待关闭): 一方已经关闭连接,另一方还在继续传输数据。
  • closing(关闭中): 两边同时尝试关闭连接,出现在一方发送结束连接请求,另一方也发送结束连接请求的情况。
  • last_ack(最后确认): 一方发送结束连接请求,等待对方的确认,同时仍然可以发送数据。
  • time_wait(时间等待): 连接已经关闭,但在一段时间内保持连接状态,以确保迟到的数据包不会引起混乱。

这些状态描述了tcp连接在建立、传输数据和关闭过程中的不同阶段。不同的状态之间的转换构成了tcp连接的生命周期。理解这些状态对于网络故障排查和性能优化非常重要。

  • timewait状态是tcp连接关闭(四次挥手)后,等待一段时间以确保对方收到最后的ack的状态,是tcp连接状态的一种,不是报错。在高并发的情况下,大量的timewait状态可能会导致端口耗尽等问题。
  • 在timewait状态下,tcp处于连接等待,等待一定的时间,确保所有数据全部传送完毕。如果需要继续传输数据,可以继续使用已建立的这个连接,无须再次发起连接请求。确保所有的连接。都是可靠的关闭。timewait在连接正常关闭之后,经历一段时间之后,会自动关闭,自动消失。占用资源非常小,对服务器的性能影响有限。大型网站会关注这个问题。

查看所有tcp的连接状态:

netstat -n | awk '/^tcp/ {++s[$nf]} end {for(a in s) print a, s[a]}'.

这是一个用于统计tcp连接状态的命令,通过结合netstatawk来实现。

  • netstat -n: 这部分命令用于显示网络统计信息,其中-n选项表示以数字形式显示地址和端口号,而不是尝试解析为域名和服务名。
  • |: 这是管道符号,它将netstat -n的输出传递给下一个命令。
  • awk '/^tcp/ {++s[$nf]} end {for(a in s) print a, s[a]}':这是一个用awk编写的脚本,用于对netstat -n的输出进行处理。
  • /^tcp/: 这是一个模式匹配,表示只处理以 "tcp" 开头的行。
  • {++s[$nf]}: 这是一个动作,对于匹配的行,它会自增一个数组s的元素,该元素的索引是最后一列($nf)的值。这相当于在数组s中统计每种tcp连接状态的数量。
  • end {for(a in s) print a, s[a]}: 在处理完所有行后,这个部分会在最终的总结阶段执行。它使用for循环遍历数组s,并打印出每种tcp连接状态及其对应的数量。

综合起来,该命令的目的是列出系统中各种tcp连接状态的数量。这在网络故障排查或性能监测时很有用,可以帮助识别系统中连接状态的分布情况。

tcp优化

查看当前sysctl参数:

使用以下命令查看当前系统的sysctl参数:

sysctl -a

临时修改参数:

可以使用以下命令临时修改参数,这些修改在系统重启后会失效:

sysctl -w net.ipv4.tcp_syncookies=1
sysctl -w net.ipv4.tcp_tw_reuse=1
sysctl -w net.ipv4.tcp_tw_recycle=1
sysctl -w net.ipv4.tcp_fin_timeout=60

永久修改参数:

若要使更改永久生效,需要编辑系统的sysctl配置文件。配置文件通常位于 /etc/sysctl.conf/etc/sysctl.d/*.conf。使用文本编辑器打开文件:

sudo nano /etc/sysctl.conf

或者(如果存在):

sudo nano /etc/sysctl.d/99-custom.conf

在文件中添加或修改需要的参数,然后保存并关闭文件。

net.ipv4.tcp_syncookies=1
net.ipv4.tcp_tw_reuse=1
net.ipv4.tcp_tw_recycle=1
net.ipv4.tcp_fin_timeout=60

最后,运行以下命令使更改生效:

sudo sysctl -p

上述命令会重新加载sysctl配置文件,使新的参数生效。

请注意,修改内核参数可能会对系统性能产生影响,因此在修改之前,请确保你了解每个参数的作用及其可能的影响,并在生产环境中谨慎操作。

net.ipv4.tcp_syncookies=1

  • 含义:启用tcp syn cookies。

  • 解释:当系统面临syn队列溢出时,启动tcp syn cookies是一种防范机制。syn cookies允许服务器在syn队列溢出时继续接受连接请求,而不是拒绝请求。

net.ipv4.tcp_tw_reuse=1

  • 含义:允许重用time_wait状态的端口。

  • 解释:timewait状态是在连接关闭后,等待足够的时间确保远端收到连接关闭的确认。启用tcp_tw_reuse允许将timewait状态的端口快速重用,即使该端口还在time_wait状态,也可以为新的连接使用。

net.ipv4.tcp_tw_recycle=1

  • 含义:启用time_wait状态的快速回收。

  • 解释:timewait状态的快速回收意味着内核会更积极地尝试回收timewait状态,以释放系统资源。这个参数在某些情况下可能导致问题,因为它依赖于一些假设,因此在某些网络环境中可能不安全。

net.ipv4.tcp_fin_timeout=60

  • 含义:设置tcp连接的fin-wait-2状态的超时时间为60秒。

  • 解释:当一方发起关闭连接(发送fin包)后,进入fin-wait-2状态,等待另一方的确认。这个参数设置了在这个状态停留的最大时间。在这里,设置为60秒,表示如果另一端在这个时间内没有发送确认,连接将被强制关闭。

配置防盗链

方法一:使用ngx_http_referer_module模块

开启 ngx_http_referer_module 模块

在 nginx 配置文件中,在需要防盗链的位置,添加类似如下的代码:

location / {
    valid_referers none blocked example.com *.example.com;
    if ($invalid_referer) {
        return 403;
    }
    # 其他配置
}

这个配置会验证请求的来源,如果不是在 valid_referers 列出的域名中,就会返回 403 状态码,拒绝访问。

重新加载 nginx 配置

确保配置文件修改后,使用命令行执行 nginx -s reload 来重新加载配置文件。

方法二:使用secure_link模块

开启 secure_link 模块

这个模块需要在 nginx 编译时加入,可以在编译时通过添加 --with-http_secure_link_module 来启用。

生成链接

在需要进行防盗链的地方,可以通过类似如下的方式生成链接:

location / {
    secure_link $arg_md5,$arg_expires;
    secure_link_md5 "secret$uri$remote_addr$arg_expires";
    if ($secure_link = "") {
        return 403;
    }
    if ($secure_link = "0") {
        return 410;
    }
    # 其他配置
}

这个配置会验证链接的有效性,如果链接无效或过期,会返回相应的状态码。

生成链接参数

生成链接时需要包含 md5expires 参数,其中 md5 是链接的加密签名,expires 是链接的过期时间。

无论使用哪种方式,确保在配置完成后测试并检查 nginx 的日志文件以确保防盗链功能按预期工作。

盗图

配置防盗链

vim /usr/local/nginx/conf/nginx.conf

http {
...........
server{
...........
location ~* \.(jpg|gif|swf)$ {            
         root  html;
         expires 1d;
         valid_referers none blocked *.kgc.com kgc.com;   
         if ( $invalid_referer ) {
           rewrite ^/ http://www.kgc.com/error.png;
           }
        }
............
}
...............
}

这段配置是在 nginx 的 http 配置块中的一个 server 配置块中,针对请求以 .jpg.gif.swf 结尾的资源文件的 location 块。以下是对这段配置的解释:

http {
    # 其他 http 配置

    server {
        # 其他 server 配置

        location ~* \.(jpg|gif|swf)$ { #
            root html;  # 设置资源文件的根目录,资源文件应该存储在 nginx 的 html 目录下
            expires 1d;  # 设置浏览器缓存过期时间为 1 天

            valid_referers none blocked *.kgc.com kgc.com;  # 允许的合法引用者(referer),可以是 none(空)、blocked(空或错误的referer)、*.kgc.com 或 kgc.com。其他引用者会被视为非法

            if ($invalid_referer) {
                rewrite ^/ http://www.kgc.com/error.png;  # 如果引用者非法,则将请求重定向到 http://www.kgc.com/error.png
            }

            # 其他配置
        }

        # 其他 location 块和配置
    }

    # 其他 server 配置和其他 http 配置
}

这段配置的作用是限制对以 .jpg.gif.swf 结尾的资源文件的访问,只有在合法的引用者(referer)中才允许访问。如果引用者不在指定的合法引用者列表中,将请求重定向到 http://www.kgc.com/error.png。同时,设置了这些资源文件的缓存过期时间为 1 天。

  • location: 定义了一个匹配请求 url 路径的位置块。
  • ~*: 这是一个标志,表示进行大小写不敏感的正则表达式匹配。使用 ~* 可以确保无论路径中的字符是大写还是小写,都能成功匹配到相应的规则。
  • ~: 表示进行大小写敏感的正则匹配。
  • ~*: 表示进行大小写不敏感的正则匹配。
  • \.(jpg|gif|swf)$: 这是一个正则表达式,用来匹配以 .jpg.gif.swf 结尾的 url 路径。

因此,这个位置块会匹配类似于 example.com/image.jpgexample.com/files/file.swf 这样以 .jpg.gif.swf 结尾的 url 路径。

对于这些匹配的请求,配置中定义了相应的处理规则,比如限制访问权限或设置缓存等。

  • \.: 匹配一个点号,这里需要用反斜杠转义,因为点号在正则表达式中表示任意字符。
  • (jpg|gif|swf): 这是一个括号内的组,匹配文件扩展名,其中 | 表示或的关系,匹配 .jpg.gif.swf
  • $: 表示匹配字符串的结尾。

网页准备:

web源主机(192.168.41.10)配置:

cd /usr/local/nginx/html

/usr/local/nginx/html下创建俩文件(right.jpg error.jpg)

vim index.html

<img src="game.jpg"/>
</body>
</html>

echo "192.168.233.61 www.kgc.com" >> /etc/hosts 
echo "192.168.233.62 www.benet.com" >> /etc/hosts 

盗链网站主机(192.168.41.11):

cd /usr/local/nginx/html
vim index.html
...... 
<img src="http://www.kgc.com/right.jpg"/>
</body>
</html>

echo "192.168.41.10 www.kgc.com" >> /etc/hosts 
echo "192.168.14.11 www.benet.com" >> /etc/hosts 

在盗图网站主机上进行浏览器验证

http://www.benet.com

总结

以上为个人经验,希望能给大家一个参考,也希望大家多多支持代码网。

(0)

相关文章:

版权声明:本文内容由互联网用户贡献,该文观点仅代表作者本人。本站仅提供信息存储服务,不拥有所有权,不承担相关法律责任。 如发现本站有涉嫌抄袭侵权/违法违规的内容, 请发送邮件至 2386932994@qq.com 举报,一经查实将立刻删除。

发表评论

验证码:
Copyright © 2017-2026  代码网 保留所有权利. 粤ICP备2024248653号
站长QQ:2386932994 | 联系邮箱:2386932994@qq.com