随记——Nginx学习笔记

一、Nginx

  • Nginx:轻量级、高性能的HTTP反向代理服务器,也是IMAP/POP3/SMTP代理服务器
  • 官方测试支持5万并发
  • 特点:cpu、内存消耗小,并发能力强

Nginx 可以解决的问题

  • 高并发
  • 负载均衡
  • 高可用
  • 虚拟主机
  • 伪静态
  • 动静分离

二、对比Nginx 和Apache

Apache:同步多进程模型,一个连接对应一个进程,一个进程对应一个线程;

Nginx:异步,多个连接(万级别)对应一个进程,一个进程对应多个线程。

Nginx优点

- 轻量级,同样起web服务,比apache占用更少的内存及资源
- 抗并发,Nginx处理请求时异步非阻塞(I/O)的,而apache是阻塞的,高并发下nginx拥有低消耗高性能
- 高度模块化设计,编写模块相对简单
- 社区活跃,各种高性能模块产出迅速
- 配置简洁

Apache优点

* 相比Nginx,rewrite更加强大
* 模块多,功能完善,基本想要的功能都有
* bug较少

rewrite :即url重写,如将http://xxx/index.html?p=123 改写为http://xxx/index.html/p/123.html,使其对浏览器更友好

Nginx与Apache进程调度

前提:cpu同时内核数为4,只能同时处理四个进程

nginx:异步处理

当有四个用户发起请求时,每个进程处理一个用户请求;
当第五个用户接入时,没有空闲进程,选择一个进程,开启新的线程交由操作系统内核去处理(磁盘I/O、网络I/O),进程只负责监控状态,进行转发,从而减少了cpu进程调度的时间

Apache:同步处理

当有四个用户发起请求时,每个进程处理一个用户请求;
当第五个用户接入时,没有空闲进程,选择一个进程,抢占cpu资源,cpu通过进程调度来处理请求

三、相关资源文档

  • Tengine下载和文档

​ http://tengine.taobao.org/

  • Nginx官网和文档

​ http://nginx.org

  • Tengne :对Nginx进行了封装与扩展,基本配置相同

四、安装Tengine

注意:安装前需要安装系统依赖组件 gcc openssl-devel pcre-devel zlib-devel

安装:yum install gcc openssl-devel pcre-devel zlib-devel -y

  1. 将下载好的安装包(tengine-2.3.1.tar.gz)上传服务器,并解压

tar -zxvf tengine-2.3.1.tar.gz

  1. 文件目录中的可执行文件configure:用来配置tengine相关参数

    [root@VM-16-11-centos tengine-2.3.1]# ./configure --prefix=/usr/local/tengine
    #配置成功,显示相关配置
    Configuration summary
      + using system PCRE library
      + using system OpenSSL library
      + using system zlib library
      + jemalloc library is disabled
    
      nginx path prefix: "/usr/local/tengine"
      nginx binary file: "/usr/local/tengine/sbin/nginx"
      nginx modules path: "/usr/local/tengine/modules"
      nginx configuration prefix: "/usr/local/tengine/conf"
      nginx configuration file: "/usr/local/tengine/conf/nginx.conf"
      nginx pid file: "/usr/local/tengine/logs/nginx.pid"
      nginx error log file: "/usr/local/tengine/logs/error.log"
      nginx http access log file: "/usr/local/tengine/logs/access.log"
      nginx http client request body temporary files: "client_body_temp"
      nginx http proxy temporary files: "proxy_temp"
      nginx http fastcgi temporary files: "fastcgi_temp"
      nginx http uwsgi temporary files: "uwsgi_temp"
      nginx http scgi temporary files: "scgi_temp"
    
    
  2. 编译并安装

    make && make install

  3. 安装完成可以在/usr/local/中找到tengine目录

    使用/usr/local/tengine/sbin目录中的nginx命令启动tengine

    [root@VM-16-11-centos sbin]# ./nginx 
    [root@VM-16-11-centos sbin]#              #不报错,即启动成功
    
    

    在浏览器使用IP访问:http://xx.xx.xx.xx/,出现如下页面,表示安装成功

    [外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-44TCqhZJ-1617118860756)(.\image\nginx默认页面.png)]

  4. 停止nginx

    nginx没有停止命令,只能直接杀掉进程

    [root@VM-16-11-centos sbin]# ps -ef | grep nginx
    root     15432     1  0 20:31 ?        00:00:00 nginx: master process ./nginx    #主进程
    nobody   15433 15432  0 20:31 ?        00:00:00 nginx: worker process     #工作线程
    root     16697 32742  0 20:40 pts/1    00:00:00 grep --color=auto nginx
    [root@VM-16-11-centos sbin]# kill -9 15432 15433  #主进程与 工作线程都要杀掉
    [root@VM-16-11-centos sbin]# ps -ef | grep nginx
    root     16794 32742  0 20:41 pts/1    00:00:00 grep --color=auto nginx
    [root@VM-16-11-centos sbin]# 
    
    

开机启动

chkconfig --list
chkconfig --add nginx
chkconfig nginx on
#时间同步
service ntpd status

配置nginx启动脚本

  • 在/etc/init.d/nginx文件中编写启动脚本,脚本内容如下,文件不存在则创建,文件路径不能修改
  • 赋予可执行权限 : chmod 777 ./nginx
  • 启动命令
service Nginx start #启动服务
service Nginx stop #停止服务
service Nginx status #查看状态
service Nginx reload #动态重载配置文件

#centos7 中可以使用下面命令
systemctl start nginx
systemctl stop nginx  
systemctl status nginx  
systemctl daemon-reload  #重新加载启动脚本
#nginx启动脚本内容,需要针对自己的安装目录进行修改
#!/bin/sh
#
# nginx - this script starts and stops the nginx daemon
#
# chkconfig:   - 85 15 
# description:  Nginx is an HTTP(S) server, HTTP(S) reverse \
#               proxy and IMAP/POP3 proxy server
# processname: nginx
# config:      /etc/nginx/nginx.conf
# config:      /etc/sysconfig/nginx
# pidfile:     /var/run/nginx.pid
 
# Source function library.
. /etc/rc.d/init.d/functions
 
# Source networking configuration.
. /etc/sysconfig/network
 
# Check that networking is up.
[ "$NETWORKING" = "no" ] && exit 0
 
nginx="/usr/local/tengine/sbin/nginx"
prog=$(basename $nginx)
 
NGINX_CONF_FILE="/usr/local/tengine/conf/nginx.conf"
 
[ -f /etc/sysconfig/nginx ] && . /etc/sysconfig/nginx
 
lockfile=/var/lock/subsys/nginx
 
make_dirs() {
   # make required directories
   user=`nginx -V 2>&1 | grep "configure arguments:" | sed 's/[^*]*--user=\([^ ]*\).*/\1/g' -`
   options=`$nginx -V 2>&1 | grep 'configure arguments:'`
   for opt in $options; do
       if [ `echo $opt | grep '.*-temp-path'` ]; then
           value=`echo $opt | cut -d "=" -f 2`
           if [ ! -d "$value" ]; then
               # echo "creating" $value
               mkdir -p $value && chown -R $user $value
           fi
       fi
   done
}
 
start() {
    [ -x $nginx ] || exit 5
    [ -f $NGINX_CONF_FILE ] || exit 6
    make_dirs
    echo -n $"Starting $prog: "
    daemon $nginx -c $NGINX_CONF_FILE
    retval=$?
    echo
    [ $retval -eq 0 ] && touch $lockfile
    return $retval
}
 
stop() {
    echo -n $"Stopping $prog: "
    killproc $prog -QUIT
    retval=$?
    echo
    [ $retval -eq 0 ] && rm -f $lockfile
    return $retval
}
 
restart() {
    configtest || return $?
    stop
    sleep 1
    start
}
 
reload() {
    configtest || return $?
    echo -n $"Reloading $prog: "
    killproc $nginx -HUP
    RETVAL=$?
    echo
}
 
force_reload() {
    restart
}
 
configtest() {
  $nginx -t -c $NGINX_CONF_FILE
}
 
rh_status() {
    status $prog
}
 
rh_status_q() {
    rh_status >/dev/null 2>&1
}
 
case "$1" in
    start)
        rh_status_q && exit 0
        $1
        ;;
    stop)
        rh_status_q || exit 0
        $1
        ;;
    restart|configtest)
        $1
        ;;
    reload)
        rh_status_q || exit 7
        $1
        ;;
    force-reload)
        force_reload
        ;;
    status)
        rh_status
        ;;
    condrestart|try-restart)
        rh_status_q || exit 0
            ;;
    *)
        echo $"Usage: $0 {start|stop|status|restart|condrestart|try-restart|reload|force-reload|configtest}"
        exit 2
esac

五、相关配置

/usr/local/tengine/conf/nginx.conf nginx配置文件

#如果不配置,默认当前登录的用户,尽量不要使用root用户运行,
user  nobody;
user www www; #指定nginx运行的用户和用户组
#允许nginx同时处理的最大进程数,建议设置为等于cpu的总核心数,最大化利用资源,避免cpu频繁切换进行
worker_processes 8;
#一个进程能处理的最大连接数,并发量即为:进程数*连接数,官方号称可以处理5万并发,实际需要考虑系统磁盘I/O和网络I/O。
#events表示基于事件,异步网络I/O是基于事件的
events {
    worker_connections  1024;
}
#linux内核能打开的文件句柄个数,总连接数要小于这个数字
[root@VM-16-11-centos conf]# cat /proc/sys/fs/file-max 
177079
#当前使用句柄数
cat /proc/sys/fs/file-nr
#修改句柄数
ulimit -SHn 65535
#查看系统资源限制
ulimit -a

#并发总数是 worker_processes 和 worker_connections 的乘积

#即 max_clients = worker_processes * worker_connections

#在设置了反向代理的情况下,max_clients = worker_processes * worker_connections / 4 
#为什么上面反向代理要除以4,应该说是一个经验值
#全局错误日志定义类型,[ debug | info | notice | warn | error | crit ]
error_log /var/log/nginx/error.log info;
#进程文件
pid /var/run/nginx.pid;
#一个nginx进程打开的最多文件描述符数目,理论值应该是最多打开文件数(系统的值ulimit -n)与nginx进程数相除,但是nginx分配请求并不均匀,所以建议与ulimit -n的值保持一致。

worker_rlimit_nofile 65535;

http

#文件扩展名与文件类型映射表,include 可以引入其他配置
#通过配置文件类型,可以指定页面加载方式:下载或直接打开
include mime.types; 

default_type application/octet-stream; #默认文件类型

charset utf-8; #默认编码

client_header_buffer_size 32k; #上传文件大小限制
#sendfile指令:文件传输模式,指定nginx是否调用sendfile函数来输出文件
#sendfile on; 开启高效文件传输模式,对普通应用设为on
#如果用来进行下载等应用磁盘IO重负载应用,可设置为off,以平衡磁盘与网络I/O处理速度,降低系统的负载
#如果图片显示不正常改为off。

#操作本地磁盘文件时
sendfile on 相当于 ctrl+x
sendfile off 相当于 ctrl+c

#操作网络文件时
sendfile on:app向内核发送一个指令,由内核去磁盘读取文件,并发送给网卡
sendfile off:app从磁盘读取文件,发送给内核,内核再发送给网卡,多一层I/O

tcp_nopush 在linux/Unix系统中优化tcp数据传输,批处理,仅在sendfile开启时有效

autoindex on;#开启目录列表访问,合适下载服务器,默认关闭。

keepalive_timeout 120;#长连接超时时间,单位是秒

gzip

`gzip on;` 开启gzip压缩输出

`gzip_min_length 1k;`  设置允许压缩的页面最小字节数,页面字节数从header头得content-length中进行获取。默认值是0,不管页面多大都压缩。建议设置成大于2k的字节数,小于2k可能会越压越大。  

`gzip_buffers 4 16k;` 设置系统获取几个单位的缓存用于存储gzip的压缩结果数据流。 例如 4 4k 代表以4k为单位,按照原始数据大小以4k为单位的4倍申请内存。 4 8k 代表以8k为单位,按照原始数据大小以8k为单位的4倍申请内存。    如果没有设置,默认值是申请跟原始数据相同大小的内存空间去存储gzip压缩结果。

`gzip_http_version 1.0; `压缩版本(默认1.1,前端如果是squid2.5请使用1.0)

`gzip_comp_level 2;` 压缩级别,1-10,数字越大压缩的越好,也越占用CPU时间  

`gzip_types text/plain application/x-javascript text/css application/xml;`
#压缩类型,默认就已经包含text/html,所以下面就不用再写了,写上去也不会有问题,但是会有一个warn。

 默认值: gzip_types text/html (默认不对js/css文件进行压缩) 

压缩类型,匹配MIME类型进行压缩 

设置哪压缩种文本文件可参考 conf/mime.types

 `gzip_disable "MSIE [1-6]\.";   `E6及以下禁止压缩

`gzip_vary on;  `给CDN和代理服务器使用,针对相同url,可以根据头信息返回压缩和非压缩副本  

server

http{
	server{
		#表示一个虚拟主机
	}
}
#虚拟主机是一种特殊的软硬件技术,它可以将网络上的每一台计算机分成多个虚拟主机,每个虚拟主机可以独立对外提供www服务,这样就可以实现一台主机对外提供多个web服务,每个虚拟主机之间是独立的,互不影响的

通过nginx可以实现虚拟主机的配置,nginx支持三种类型的虚拟主机配置

  • 基于ip的虚拟主机, (一块主机绑定多个ip地址)
  • 基于域名的虚拟主机(servername)
  • 基于端口的虚拟主机(listen如果不写ip端口模式)
#监听端口
listen       80; 
#服务名,域名可以有多个,用空格隔开
server_name www.mashibing.com mashibing.com; 
#编码集
charset koi8-r;
日志相关
access_log  "pipe:rollback logs/host.access_log interval=1d baknum=7 maxsize=2G"  main;

location

location / {#匹配规则
	root html; #根目录
	index index.html index.htm; #默认页面,依次查找,当访问路径中没有指定页面时返回
}

匹配规则:普通匹配 < 长路径匹配 < 正则匹配 < 短路匹配 < 精确匹配

当存在多个同类配置时

​ 正则匹配:与编辑顺序有关,匹配到第一个规则就停止后面的匹配

​ 其他匹配:与顺序无关,按最大前缀规则匹配

* /xxx #普通匹配,匹配当前路径及子路径
* /xxx/xxx #长路径匹配,即比普通匹配较长的路径,匹配当前路径及子路径
  • ~/xxx #正则匹配,区分大小写

    ~*/xxx #正则匹配,不区分大小写

  • ^~/xxx/ooo #短路匹配

  • =/xxx #精确匹配,只匹配当前路径

注意事项

  1. root 配置只能有一个,即所有location中的root配置必须相同,如果需要指定其他根目录,使用alias(虚拟目录)

  2. root与alias区别

    • 都是指定用来指定文件根目录,但是配置段不同,

      ​ root配置段:http、server、 location、if

      ​ alias配置段:location

    • nginx解析路径区别

      ​ root:root路径 + location路径

      ​ alias:使用alias 路径替换location路径

  3. location路径配置时需要注意,当配置路径与静态页面名称相同时,会有坑,如下

location / { #配置一
	root html; 
	index index.html index.htm;
}
location /doc {#配置二
	root html; 
	index doc.html index.htm;
}
http://xx.xx.xx.xx/doc.html;http://xx.xx.xx.xx/doc/doc.html #使用这两个连接访问时,nginx都会匹配到 配置二,
#IP访问控制
location  {
	   deny  IP /IP段
	   deny  192.168.1.109;
	   allow 192.168.1.0/24;192.168.0.0/16;192.0.0.0/8
	}
#用户认证访问,模块ngx_http_auth_basic_module 允许使用“HTTP基本认证”协议验证用户名和密码来限制对资源的访问。
location ~ (.*)\.avi$ {
        auth_basic  "closed site";
        auth_basic_user_file users;#默认在conf/目录下加载
    }
#安装httpd-tools
yum install httpd
#生成用户文件,将文件复制到conf目录下
htpasswd -c -d /usr/local/users zhangyang

#nginx访问状态监控
location /basic_status {
    stub_status on;
}
#动态代理服务器配置
location /test {
    Proxy_pass https://www.baidu.com/;
}

代理服务器:用户访问服务器时,不是直接访问而是通过一个中间服务器转发,这个服务器就叫代理服务器,从用户角度来看,叫做正向代理服务器,从服务器角度看叫反向代理服务器

动态代理转发请求的两种方式:

 * 用户发送请求给代理服务器,代理服务器将请求发送给服务器,并且将服务器返回的数据发送给用户,---请求转发
 * 用户发送请求给代理服务器,代理服务器将服务器地址发给用户,由用户直接请求服务器,---请求重定向(301,302)

负载均衡

#url要与proxy_pass相对应
upstream tomcat{
   url_hash; #负载均衡算法,默认轮询
   server 192.168.2.52:8080 weight=1 max_conns=800 dwon;
   server 192.168.2.53:8080 weight=10 backup;
 }
http{
	server{
		location /tomcat {
     		proxy_pass http://tomcat/;
		} 
	}
}
#weight 权重,越大访问越多
#down:表示当前的server暂时不参与负载
#backup: 其它所有的非backup机器down或者忙的时候,请求backup机器。
#max_conns: 最大连接数,防止服务器过载
#max_fails=3 fail_timeout=30s :30秒内请求失败连续3次,认为该应用宕机,不会再向该服务发起请求,30秒后,再次发起请求,若失败(仅一次)则继续等待30秒,循环,直到恢复。

负载算法:

  • 轮询+weight:

  • ip_hash:容易造成访问量偏移

  • url_hash :方便定向存储数据缓存

  • least_conn:

  • least_time

健康检查

upstream tomcat{
   server 192.168.2.52:8080 weight=1 max_conns=800;
   server 192.168.2.53:8080 weight=1;
   check interval=3000 rise=2 fall=5 timeout=1000 type=http;
   check_http_send "HEAD / HTTP/1.0\r\n\r\n";
   check_http_expect_alive http_2xx http_3xx;
 }
 
location /status {
    check_status;
}
#查看负载服务器状态

自动索引

location /art {
        alias  /var/data/www1/;#虚拟目录
        autoindex on;
 }
 #可以查看目录下的所有文件   

动静分离

location ~ .*\.(gif|jpg|jpeg|png|bmp|swf|html|htm|css|js)$ {
       root  /var/data/www1/;
	       
}

相关异常

启动脚本配置配置报错

#centos7报错,6不确定有没有
#错误信息
[root@VM-16-11-centos conf]# systemctl status nginx.service
● nginx.service - SYSV: Nginx is an HTTP(S) server, HTTP(S) reverse proxy and IMAP/POP3 proxy server
   Loaded: loaded (/etc/rc.d/init.d/nginx; bad; vendor preset: disabled)
   Active: failed (Result: timeout) since Sat 2021-03-13 21:41:58 CST; 11s ago
     Docs: man:systemd-sysv-generator(8)
  Process: 25154 ExecStart=/etc/rc.d/init.d/nginx start (code=exited, status=0/SUCCESS)
   CGroup: /system.slice/nginx.service
           ├─25184 nginx: master process /usr/local/tengine/sbin/nginx -c /usr/local/tengine/conf/nginx.conf
           └─25186 nginx: worker process

Mar 13 21:36:58 VM-16-11-centos systemd[1]: Starting SYSV: Nginx is an HTTP(S) server, HTTP(S) reverse proxy and IMAP/POP3 proxy server...
Mar 13 21:36:58 VM-16-11-centos nginx[25154]: /etc/rc.d/init.d/nginx: line 12: pidfile:: command not found
Mar 13 21:36:58 VM-16-11-centos nginx[25154]: Starting nginx: [  OK  ]
Mar 13 21:36:58 VM-16-11-centos systemd[1]: Can't open PID file /var/run/nginx.pid (yet?) after start: No such file or directory
Mar 13 21:41:58 VM-16-11-centos systemd[1]: nginx.service start operation timed out. Terminating.
Mar 13 21:41:58 VM-16-11-centos systemd[1]: Failed to start SYSV: Nginx is an HTTP(S) server, HTTP(S) reverse proxy and IMAP/POP3 proxy server.
Mar 13 21:41:58 VM-16-11-centos systemd[1]: Unit nginx.service entered failed state.
Mar 13 21:41:58 VM-16-11-centos systemd[1]: nginx.service failed.

原因:如上PID文件位置不对,修改PID文件路径即可解决

解决:

方法一:

修改/etc/init.d/nginx 配置的PID文件路径和nginx.conf文件中的PID路径一致,配置完不一定好使,建议多试几次

方式一:
PIDFILE=/usr/local/nginx/logs/nginx.pid
方式二:
pidfile: /usr/local/nginx/logs/nginx.pid

方法二:

1.修改/usr/local/nginx/conf/nginx.conf配置文件
拷贝一行代码 #pid logs/nginx.pid; ,修改为报错提示的路径,即:pid /var/run/nginx.pid

nginx请求转发异常

异常:413 Request Entity Too Large

原因:nginx默认请求体大小为1m,数据超过1m就会报错

解决:

# 指定请求体大小,默认1m,必须修改
client_max_body_size     50m;
# 指定请求处理时间,时间过小会报502 Bad Gateway,根据需求设置
client_header_timeout    1m; 
client_body_timeout      1m; 
proxy_connect_timeout     60s; 
proxy_read_timeout      1m; 
proxy_send_timeout      1m;

异常:504 Gateway Time-out

原因

nginx访问出现504 Gateway Time-out,一般是由于程序执行时间过长导致响应超时,例如程序需要执行90秒,而nginx最大响应等待时间为30秒,这样就会出现超时。
通常有以下几种情况导致:
1.程序在处理大量数据,导致等待超时。
2.程序中调用外部请求,而外部请求响应超时。
3.连接数据库失败而没有停止,死循环重新连。

解决:在nginx.config中配置如下参数

fastcgi_connect_timeout
#fastcgi连接超时时间,默认60秒

fastcgi_send_timeout
#nginx 进程向 fastcgi 进程发送请求过程的超时时间,默认值60秒

fastcgi_read_timeout
#fastcgi 进程向 nginx 进程发送输出过程的超时时间,默认值60秒

异常:502 Bad Gateway

原因:nginx反向代理,如果header过大,超出了默认的1k,就会引发upstream sent too big header异常

解决:nginx.config中添加/修改参数

http {
  ...
  #分配8*16k的空间来缓存请求数据,超出空间则会放进 临时文件:fastcgi_temp 中存储
  fastcgi_buffers 8 16k;
  #读取响应头需要的缓存空间
  fastcgi_buffer_size 32k;
  ...
}

问题: proxy_temp文件中没有报文

原因:nginx.conf中没有配置user user,新建的临时文件owner就是nobody了,就导致没有权限写进去这些临时文件

解决:nginx.conf中配置user user,删除proxy_temp下的文件,重新reload一下nginx就可以了,注意要使用管理员权限

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 2
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值