0%

nginx杂谈

Nginx的模块从功能上分为如下三类:Handlers处理器模块、Filters过滤器模块、Proxies代理类模块。

Nginx收集

一、列表

  1. Max retries exceeded with url

    • 可能原因
      • http连接太多没有关闭导致的。
      • 机器的内存不够了。
      • 由于请求频率过快,被目标网站封IP了
      • 请求的url地址错误
    • 解决方案
      • 增加重试连接次数:requests.adapters.DEFAULT_RETRIES = 5
      • 关闭多余的连接:requests使用了urllib3库,默认的http connection是keep-alive的,requests设置False关闭。
  2. upstream response is buffered to a temporary file

  3. FastCGI sent in stderr: “Unable to open primary script

  4. 配置

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
#字符集
charset utf-8;
#域名长度限制加长
server_names_hash_bucket_size 128;
#client 报头和包体设置
client_header_buffer_size 2k;
large_client_header_buffers 4 4k;
client_max_body_size 20m;
#出错时调起报错邮件发送
sendfile off;
#设置超时
keepalive_timeout 180;
tcp_nodelay on;
#开启压宿
gzip on;
gzip_disable "MSIE [1-6]\.(?!.*SV1)";
gzip_min_length 1k;
gzip_buffers 4 16k;
gzip_http_version 1.0;
gzip_comp_level 2;
gzip_types text/plain application/x-javascript text/css
#fastcgi的相关设置
fastcgi_connect_timeout 300;
fastcgi_send_timeout 300;
fastcgi_read_timeout 300;
  1. 常见日志处理

    • 统计每个ip访问的次数awk '{i=$1;a[i]+=1;}END{for(i in a)printf("%d %s \n",a[i],i)}' access.log
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    2093 192.168.10.1
    2 192.168.10.2
    2 192.168.10.3
    1 127.0.0.1
    1259 127.0.0.1
    1 192.168.10.10
    2 192.168.10.4
    2 192.168.10.5
    2 192.168.10.6
    2 192.168.10.7
    2 192.168.10.8
    1 192.168.10.9
    1 192.168.10.18
    1 192.168.10.0
    • 统计访问最多的前10个ipawk '{i=$1;a[i]+=1;}END{for(i in a)printf("%d %s \n",a[i],i)}' access.log | sort -nr |head -n 10
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    2093 192.168.10.1
    1259 127.0.0.1
    2 192.168.10.8
    2 192.168.10.7
    2 192.168.10.6
    2 192.168.10.5
    2 192.168.10.4
    2 192.168.10.3
    2 192.168.10.2
    1 192.168.10.9
    • 获取具体时间段内的日志

      • 日志格式access.log((打印Jun15-20号的日志,不做年份的限制))
      1
      10.2.24.141 - - [19/Jun/2020:09:56:57 +0800] "POST /index.php?mod=api&ver=0.1&SESSION=%7B%22rid%22:%228201_186%22,    %22sec%22:%228201%22,%22pGroup%22:%22default%22,%22tls%22:0%7D HTTP/1.1" 200 121 "-" "-" "-"
      • 处理脚本awk '{split($4, a, "/"); d=substr(a[1],2); if(d>=15 && d<=20 && a[2]=="Jun") { print $0;} }' access.log
      • 日志格式打印Apr 26号的日志)
      1
      127.0.0.1 - - [26/Apr/2018:11:12:48 +0800] "GET /inc.php HTTP/1.1" 200 62437 "-" "Mozilla/5.0 (Macintosh; Intel    Mac OS X  10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/90.0.4430.85 Safari/537.36"
      • 处理脚本awk '{split($4, a, "/"); d=substr(a[1],2); if(d==26 && a[2]=="Apr") { print $0;} }' access.log
  2. 502 upstream sent too big header while reading response header from upstream ...

    1
    2
    3
    4
    5
    6
    7
    fastcgi_intercept_errors off;
    fastcgi_buffer_size 16k;
    fastcgi_buffers 4 16k;

    proxy_buffer_size 128k;
    proxy_buffers 16 256k;
    proxy_busy_buffers_size 256k;
  3. epoll:举个例子:假设进程有10万个TCP连接,且只有几百个连接是有事件需要处理的。那么在每一个时刻进程只需要处理这几百个有事件(即TCP连接上有数据需要交互)需要处理的连接即可。

    • select和poll这样处理的:在某一时刻进程收集所有的连接,并把所有连接的套接字传给操作系统(这个过程其实是用户态内存到内核态内存的复制),而由操作系统内核寻找这那几百个有事件需要处理的连接并处理,然后返回数据给用户。
      • 这个过程需要操作系统把全部的连接处理一边,极大浪费系统资源。
    • epoll是这样做的:
      • 调用epoll_creat函数建立一个epoll对象(一颗红黑树,一个准备就绪list链表)。
      • 调用epoll_ctl函数把socket放到红黑树上,给内核中断处理程序注册一个回调函数,告诉内核如果这个句柄的中断到了,就把这个socket放到准备就绪list链表里。
      • 调用epoll_wait到准备就绪list链表中处理socket,并把数据返回给用户。
        • 不需要把全部的连接处理一遍,只需要去list链表里处理socket。
  4. reported about an closed connection (54: Connection reset by peer)

  1. 高并发nginx调优
    • 调整worker_processes数量
      • 意为生成的worker数量,最佳实践是每个CPU运行1个工作worker。
    • 调整worker_connections数量
      • 意为同时提供服务的客户端数量,一般设为1024
    • 启用Gzip压缩
      • 压缩文件大小,减少了客户端HTTP请求的传输带宽,提高了加载速度
    • 启用静态文件缓存
      • 减少传输带宽提升速度
    • 设置timeout
      • client_header_timeout:指定等待client发送一个请求头的超时时间
        • 如果在超时时间内client没发送任何东西,nginx返回HTTP状态码408(“Request timed out”)
      • client_body_timeout:设置请求体的读超时时间。
        • 超时后,nginx返回HTTP状态码408(“Request timed out”)
      • keepalive_timeout:指定client的keep-alive连接超时时间,服务器将会在这个时间后关闭连接。
        • keepalive可减少打开和关闭连接所需的CPU和网络开销
      • send_timeout:指定客户端的响应超时时间。
        • 如果在这段时间内客户端没有读取任何数据,nginx就会关闭连接。
    • 关闭access_logs

Nginx状态码

一、基础

      HTTP状态码(英语:HTTP Status Code)是用以表示网页服务器超文本传输协议响应状态的3位数字代码。它由RFC 2616规范定义的,并得到RFC 2518、RFC 2817、RFC 2295、RFC 2774与RFC 4918等规范扩展。所有状态码的第一个数字代表了响应的五种状态之一。所示的消息短语是典型的,但是可以提供任何可读取的替代方案。除非另有说明,状态码是HTTP/1.1标准(RFC 7231)的一部分。HTTP状态码的官方注册表由互联网号码分配局(Internet Assigned Numbers Authority)维护。

http请求

二、常见错误码

  1. 400

    • Bad Request,往往因为语法错误而无法被服务端理解
  2. 413

    • Request Entity Too Large,请求体过大,一般出现在上传大文件请求

    • 解决办法

      • 修改nginx配置文件
      1
      client_max_body_size 8M; ## 设置客户端请求体最大值
      • 修改php.ini
      1
      2
      post_max_size = 8M       # 整个表单提交的最大限制
      upload_max_filesize = 2M # 上传单个文件的最大限制
  3. 499

    • nginx独有,表示在收到客户端完整的HTTP request前,客户端试图关闭TCP连接导致

    • 下载nginx-1.16.1.tar.gz,解压到nginx-1.16.1目录,打开nginx-1.16.1/src/http/ngx_http_request.h文件,见499定义:

      1
      2
      3
      4
      5
      6
      7
      /*
      * HTTP does not define the code for the case when a client closed
      * the connection while we are processing its request so we introduce
      * own code to log such situation when a client has closed the connection
      * before we even try to send the HTTP header to it
      */
      #define NGX_HTTP_CLIENT_CLOSED_REQUEST 499
    • 复现

      • 定义处理请求脚本index.php,直接加入sleep(10);
      • 通过curl请求 curl -m 2 http://localhost/index.php
      • 查看访问日志 tail -n 10 access.log
  4. 500

  5. 502:Bad Gateway是指错误网关,无效网关

    • 一般可通过是杀死php-fpm进程再请求web来复现
  6. 503
    Service Temporarily Unavailable,即服务暂时不可用,一般由于临时的服务器维护或者过载,服务器当前无法处理请求。

  7. 504

  8. 403

    • 由于启动用户和nginx工作用户不一致所致
    • 缺少index.html或者index.php文件
    • 权限问题,如果nginx没有web目录的操作权限
    • SELinux设置为开启状态(enabled)的原因
  9. nginx状态码定义

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
#define NGX_HTTP_CONTINUE                  100
#define NGX_HTTP_SWITCHING_PROTOCOLS 101
#define NGX_HTTP_PROCESSING 102

#define NGX_HTTP_OK 200
#define NGX_HTTP_CREATED 201
#define NGX_HTTP_ACCEPTED 202
#define NGX_HTTP_NO_CONTENT 204
#define NGX_HTTP_PARTIAL_CONTENT 206

#define NGX_HTTP_SPECIAL_RESPONSE 300
#define NGX_HTTP_MOVED_PERMANENTLY 301
#define NGX_HTTP_MOVED_TEMPORARILY 302
#define NGX_HTTP_SEE_OTHER 303
#define NGX_HTTP_NOT_MODIFIED 304
#define NGX_HTTP_TEMPORARY_REDIRECT 307
#define NGX_HTTP_PERMANENT_REDIRECT 308

#define NGX_HTTP_BAD_REQUEST 400
#define NGX_HTTP_UNAUTHORIZED 401
#define NGX_HTTP_FORBIDDEN 403
#define NGX_HTTP_NOT_FOUND 404
#define NGX_HTTP_NOT_ALLOWED 405
#define NGX_HTTP_REQUEST_TIME_OUT 408
#define NGX_HTTP_CONFLICT 409
#define NGX_HTTP_LENGTH_REQUIRED 411
#define NGX_HTTP_PRECONDITION_FAILED 412
#define NGX_HTTP_REQUEST_ENTITY_TOO_LARGE 413
#define NGX_HTTP_REQUEST_URI_TOO_LARGE 414
#define NGX_HTTP_UNSUPPORTED_MEDIA_TYPE 415
#define NGX_HTTP_RANGE_NOT_SATISFIABLE 416
#define NGX_HTTP_MISDIRECTED_REQUEST 421
#define NGX_HTTP_TOO_MANY_REQUESTS 429


/* Our own HTTP codes */

/* The special code to close connection without any response */
#define NGX_HTTP_CLOSE 444

#define NGX_HTTP_NGINX_CODES 494

#define NGX_HTTP_REQUEST_HEADER_TOO_LARGE 494

#define NGX_HTTPS_CERT_ERROR 495
#define NGX_HTTPS_NO_CERT 496

/*
* We use the special code for the plain HTTP requests that are sent to
* HTTPS port to distinguish it from 4XX in an error page redirection
*/
#define NGX_HTTP_TO_HTTPS 497

/* 498 is the canceled code for the requests with invalid host name */

/*
* HTTP does not define the code for the case when a client closed
* the connection while we are processing its request so we introduce
* own code to log such situation when a client has closed the connection
* before we even try to send the HTTP header to it
*/
#define NGX_HTTP_CLIENT_CLOSED_REQUEST 499


#define NGX_HTTP_INTERNAL_SERVER_ERROR 500
#define NGX_HTTP_NOT_IMPLEMENTED 501
#define NGX_HTTP_BAD_GATEWAY 502
#define NGX_HTTP_SERVICE_UNAVAILABLE 503
#define NGX_HTTP_GATEWAY_TIME_OUT 504
#define NGX_HTTP_VERSION_NOT_SUPPORTED 505
#define NGX_HTTP_INSUFFICIENT_STORAGE 507

三、参考

  1. 参考一
  2. 参考二