Nginx笔记——非常简单

Nginx

一、基础概念
  1. Nginx是一个高效的HTTP和反向代理服务器。作用于动静分离、API服务器和反向代理。反向代理里有负载均衡和缓存等功能。支持高并发5w/s,与keepalived联合使用支持高可用。
    在这里插入图片描述

  2. 优点:高性能,支持高并发、高可用,多模块和热部署。

    高性能的原因:多进程单线程结构,io多路复用。
    高可用,防止单点故障。可以配合keepalived一起使用

    与Apache的区别

    Apache则是一个进程对应一个连接,进程的创建切换是非常耗费资源低效的,代价太高,不可能应对几万几十万的流量。

  3. 日志文件

    配置文件nginx.conf、访问日志access.log和错误日志error.log。

    查看日志的工具goAccess

  4. 动静分离,api服务

    比如一个静态文件,html,css等可以直接由Nginx服务器提供服务,充当静态服务器,

    若涉及简单的缓存服务器,比如redis,也可以提供api服务去调用缓存服务器。

    OpenResty是对Nginx的封装,有很多lua语言的模块。

在这里插入图片描述

  1. 正向代理和反向代理

    nginx可以7也可以4层
    4层用的是NAT技术
    7层代理:需要读取并解析http请求内容,双向建立http连接,3次握手4次挥手
    它的反向代理有7层和4层,7层有http,cgi,fastcgi等,简单的memcached。4层tcp,udp等。使用的steam模块。对客户端Http,对真实服务器各自的。
    CGI程序的每一次web请求都会有启动和退出过程,也就是最为人诟病的fork-and-execute模式。
    fastcgi使用FastCGI进程管理器, 启动多个CGI解释器进程(php-cgi),等待来自Web Server的连接。

    正向代理通俗的说是代理客户端的,对于用而言需要配置代理服务器的相关信息。比如访问谷歌需要的特殊软件。对于服务器是透明的,服务器不知道真实的请求人是谁。

    反向代理是代理的是服务器,有反向代理服务器来决定请求由哪个具体的服务器处理。这个过程对于用户是无感的,客户不知道真实的服务器是哪台。

    下图所示,正向代理,代理服务器和客户端是一个整体。而反向代理相反。

在这里插入图片描述

  1. 缓存

    Nginx缓存有proxy-store、proxy-cache和memcached
    1.proxy-cache更加高级,存储路径设置,内存+磁盘,内存实际上是建立索引文件key,实际文件在磁盘,这都是在Nginx初始化的时候做的事情。同时它还有一些功能,比如什么情况不读取缓存,什么情况不缓存等,设置过期时间等高级功能,还有就是建立缓存索引和更新缓存。
    2.proxy-store可以理解是一个缓存镜像,仅仅缓存,没有就请求后端。不支持高级功能。
    3.memcached是一个缓存应用,在Nginx是可以作为一个简单的七层代理,可以简单的获取值。可以作为缓存功能。

    1、强缓存Expires、Cache-Control,协商缓存etag和if-none-match, last-modifid(服务端)和if-modified-since(客户端)。304,200
    Nginx缓存有proxy-store、proxy-cache和memcached

二、进阶理论
1、多进程单线程结构,io多路复用
  1. 多进程单线程

    nginx是多进程单线程的,一主master多从worker。

    master进程,管理和创建工作进程,接受信号等。起到一个全局管理者,一个进程挂了,则主进程会里面生成一个新的工作进程。

    worker进程,接受并处理连接。与cpu核心数一致。

    cache manager进程 :管理缓存

    cache loader进程:启动的时候,加载缓存。加载完就退出了。

    nginx是多进程单线程结构,而不是基于一个进程的多线程。

    原因:

    1、多线程模型中,某个线程的中断错误,会导致整个进程挂掉,这不符合nginx高可用高可靠的设计

    2、多线程有共享同一个地址空间,会产生锁等,阻塞等各种原因。效率不高。

    并发数,worker的个数*最大连接数之后除以2或者4

在这里插入图片描述

  1. io多路复用

    一主master多从worker的。一般worker的与CPU核数一致最好。一个worker有一个主线程是来处理请求的,而该线程使用的IO多路复用,具体的事件驱动模型是epoll。

    linux一切皆文件
    一个连接过来就会有一个文件描述符FD
    IO多路复用,就是用一个线程去监听多个socket。

    select、poll、epoll
    1、select存放文件描述符有限,1024,使用bitmap。结构体不可重用。每次都全部遍历。每次都复制到内核态。
    2、poll则解决了数量和结构体重用,使用链表,但是还是要复制(用户到内核的开销)和遍历O(n)。
    3、epoll使用红黑树解决了数量和重用的问题,使用共享内存解决了用户态和内核态复制的问题。

    epoll的结构
    epoll_create:创建一个eventpoll结构体,里面有2个重要的数据结构,红黑树和链表
    epoll_ctl:每一个连接都是一个文件描述符fd,则调用control方法可以对fd增删改,并添加事件回调函数,有读写事件发生的时候,就放入到就绪队列中。
    epoll_wait:返回就绪队列中的,也就是有读写事件的fd,给线程去处理。

    水平触发:读写事件,若缓冲区还有数据没读,或者没写完,下次epoll_wait继续返回该fd。
    边缘触发:读写事件,若缓冲区还有数据没读,或者没写完,下次epoll_wait不再继续返回该fd,直到有新的读写事件才会返回fd。

在这里插入图片描述

  1. 惊群

    原因:
    一个socket的新连接进来,多个进程都想去accpet() 到这个连接,但只有一个进程能成功,这会消耗系统资源
    解决:

    Nginx提供了一个accept_mutex这个东西,这是一个加在accept上的一把互斥锁。即每个worker进程在执行accept()之前都需要先获取锁,accept()成功之后再解锁。有了这把锁,同一时刻,只会有一个进程执行accpet(),这样就不会有惊群问题了。

    accept_mutex是一个可控选项,我们可以显示地关掉,默认是打开的

在这里插入图片描述

2、负载均衡算法
  1. 算法

    它是指将请求负载分发到各个不同的服务器中

    Nginx的分发规则有
    轮询,加权轮询:平均的轮到每一个。加权之后,有的机器性能好,可以加权重,使其承担更多。
    iphash:根据请求ip进行hash,支持session。普通就是对个数取模,更优秀的是一致性哈希。
    least最少链接数
    fair最短处理时间

    lvs: 轮询、加权轮询、基于请求ip的hash,基于目标ip的hash,最少链接,加权最少链接

    操作系统的进程调度:先来先服务,最短处理时间,时间片、优先级。

3、内存管理
  1. 内存池是在真正使用内存之前,预先申请分配一定数量的、大小相等(一般情况下)的内存块留作备用。当有新的内存需求时,就从内存池中分出一部分内存块,若内存块不够用时**,再继续申请新的内存**。内存池的好处有减少向系统申请和释放内存的时间开销,解决内存频繁分配产生的碎片,提示程序性能,减少程序员在编写代码中对内存的关注等。

    nginx为每一个层级都会创建一个内存池,进行内存的管理,比如一个模板,tcp连接,http请求等,在对应的生命周期结束的时候会摧毁整个内存池,把分配的内存一次性归还给操作系统。

  2. 内存池的结构中有三个链表,分别是小数据的next指针,大数据的large指针和清洗数据的cleanup指针,分别都是一个链表。
    在这里插入图片描述

  3. 连接池,worker_connections

4、通信—共享内存
  1. worker进程之间的通信方式,比如一些fair策略的时候,共享这个信息。

  2. 内存的管理,SLAB内存管理器。那么内存的管理是基于BESTFIT策略,其中每页中的Slot就是为了内存对齐;共享内存,worker之间通信,比如负载均衡的最小相应时间策略fair,都是基于共享内存。
    在这里插入图片描述

在这里插入图片描述

5、通信—信号管理
  1. 各个指令
名字信号(kill)命令行
直接退出TERM / INTstop
优雅的退出QUITquit
重载配置文件HUPreload
日志切割USR1reopen
热部署USR2
让老master进程
发送信息
关闭老worker
WINCH
  1. 热加载配置文件的流程
    在这里插入图片描述

  2. 热部署的流程
    在这里插入图片描述

三、模块和优化
1、http请求的11个过程
typedef enum {
    NGX_HTTP_POST_READ_PHASE = 0,   // 接收到完整的HTTP头部后处理的阶段
    NGX_HTTP_SERVER_REWRITE_PHASE,  // URI与location匹配前,改动URI的阶段,用于重定向
    NGX_HTTP_FIND_CONFIG_PHASE,     // 依据URI寻找匹配的location块配置项
    NGX_HTTP_REWRITE_PHASE,         // 上一阶段找到location块后再改动URI
    NGX_HTTP_POST_REWRITE_PHASE,    // 防止重写URL后导致的死循环
    NGX_HTTP_PREACCESS_PHASE,       // 下一阶段之前的准备
    NGX_HTTP_ACCESS_PHASE,          // 让HTTP模块推断是否同意这个请求进入Nginx服务器
    NGX_HTTP_POST_ACCESS_PHASE,     // 向用户发送拒绝服务的错误码,用来响应上一阶段的拒绝
    NGX_HTTP_TRY_FILES_PHASE,       // 为訪问静态文件资源而设置
    NGX_HTTP_CONTENT_PHASE,         // 处理HTTP请求内容的阶段,大部分HTTP模块介入这个阶段
    NGX_HTTP_LOG_PHASE              // 处理完请求后的日志记录阶段
} ngx_http_phases;

简化版本的过程

0.listen、内存池
1.rewrite:找到location;rewrite指令修改url,return返回新url。
2.鉴权和限流:
	限流limit_rate,指定向客户端传输数据的速度;
	限制并发数limit_conn,进行流量缓冲limit_req等,burst=5,设置了一个大小为5的缓冲队列,在缓冲队列中的请求会等待慢慢处理;
	控制访问ip等,白名单黑名单
	权限控制等;
3.请求后端:请求真实服务器,注意2点,请求内容和相应内容是否等待全部加载完。
4.过滤,对响应的内容进行修改,比如替换,新增相应头,gzip压缩等。日志:记录日志。
2、常见模块
upstream代理模块 ngx_http_upstream_module模块
缓存模块proxy_cache,proxy_store
还有就是简化过程中的各个步骤,如rewrite
gzip压缩模块ngx_http_gzip_module
ssl安全连接模块ngx_http_ssl_module
3、nginx优化

1、硬件

扩容机器,参数更高

2、软件

  1. CPU:解决惊群问题。分情况使用zip压缩,静态资源提前压缩。
  2. 内存:小数据块的空间利用率不高。还有sendfile,用户态和内核态来回切换。
  3. 磁盘IO:分片,客户端只要断点下载的时候,不需要全部下载到硬盘,硬盘转到内存。
4、高可用,高并发

本身高可用
多进程,一个worker挂了,master会里面生成一个新的。
主备的高可用
可以使用使用keepalived和Nginx,vrrp心跳检查来主备。

	--检测脚本,主要是判断Nginx是否存活
	vrrp_script chk_http_port {
	script "/usr/local/src/nginx_check.sh"
	interval 2	#(检测脚本执行的间隔)
	weight 2	
	}		
	>--虚拟IP的配置
	vrrp_instance VI_1 {
	state BACKUP # 主还是备MASTER
	priority 100 # 主备优先级
	virtual_ipaddress {
		192.168.17.131/24 dev ens33 label ens33:1 # 虚拟的IP,主备一致
		}
	}

高并发和高可用

​ 根据lvs和keepalived的联合使用实现高可用,对多台Nginx进行负载均衡实现高并发。

前4后4,具体看LVS和keepalived基础笔记——简单明了

四、配置文件
1、静态服务器
#user  nobody;
worker_processes  2;
events {
    worker_connections  1024;
}

http {
    include       mime.types;
    default_type  application/octet-stream;
 
    sendfile        on;
    #tcp_nopush     on;
    keepalive_timeout  65;
    # 新服务(静态网站)
    server {
        location / {
            root /data/www;
            index index.html index.php;
        }
        location /movie/ {
            root  /data1; # 加上movie
        }
        location /images/ {
            alias  /data2;# 不加上images,去除location配置的路径
        }
    }
}
2、api调用

​ 本身自己就一个服务器,提供api调用。利用openresty提供lua语言的一个服务器,lua语言可以编写逻辑进行处理。

3、反向代理-负载均衡-缓存
#定义nginx运行的用户和用户组
user  qsm qsm;
 
#设置nginx进程数,一般设置为cpu核心数,auto为自动检测
worker_processes  auto;
error_log  /var/log/nginx/error.log;

events {
    #单个进程最大连接数(最大连接数=连接数*进程数)
    worker_connections  2048;
    #设置用于复用客户端线程的轮训方法
    use epoll;
    #设置网路连接序列化,防止惊群现象发生,默认为on
    accept_mutex on;   
}
 
http {
    #文件扩展名与文件类型映射表
    include       mime.types;
    #默认文件类型
    default_type  application/octet-stream;
    
 	log_format  main  '$remote_addr - $remote_user [$time_local] "$request" '
                      '$status $body_bytes_sent "$http_referer" '
                      '"$http_user_agent" "$http_x_forwarded_for"';
	#设置nginx是否存储访问日志,关闭这个可以让读取磁盘IO操作更快
    access_log  /var/log/nginx/access.log  main;
 
    #开启高效文件传输模式,优化磁盘IO设置
    sendfile        on;
    #设置nginx在一个数据包里发送所有头文件,而不是一个接一个的发送
    tcp_nopush     on;
 
    # HTTP1.1支持持久连接alive
    # 降低每个连接的alive时间可在一定程度上提高可响应连接数量,所以一般可适当降低此值
    keepalive_timeout  60;
    
    #压缩
    #gzip  on;
    #缓存地址
    proxy_cache_path /path/to/cache levels=1:2 keys_zone=mycache:10m max_size=10g inactive=60m use_temp_path=off;
    
	upstream insure_server_upstream {
        ip_hash;
        server 192.168.11.68:20201;
        server 192.168.11.69:20201 weight=100 down;
        server 192.168.11.70:20201 weight=100;
        server 192.168.11.71:20201 weight=100 backup;
        server 192.168.11.72:20201 weight=100 max_fails=3 fail_timeout=30s;
	}
	upstream express_server_upstream {
        server 192.168.11.30 weight=1 max_fails=3 fail_timeout=30s;
        server 192.168.11.31 weight=5 max_fails=3 fail_timeout=30s;
	}
 
    #虚拟主机配置
    server {
        listen       80;
        #多域名用空格隔开
        server_name  localhost qsm.net www.qsm.net;
 
        #设置默认访问首页
        index index.php index.html;
        #默认编码
        charset utf-8;
 
        #定义本虚拟主机的访问日志
        access_log  logs/access.log;
        
        location /jd/insure {
        	proxy_set_header Host $http_host;
            proxy_set_header X-Real-IP $remote_addr;
            proxy_set_header X-Real-Port $remote_port;
            proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
            
        	#使用缓存,默认get和head缓存
            proxy_cache mycache;
            proxy_cache_key $scheme$proxy_host$request_uri;
            
            proxy_pass http://insure_server_upstream;        #引用upstream
        }
        location /jd/express {
            proxy_pass http://express_server_upstream;        #引用upstream
        }
        
        #错误设置
        error_page   500 502 503 504  /404.html;
        location = /404.html {
            root   html;
        }
    }
    #虚拟主机配置
    server {
        listen       8080;
        #多域名用空格隔开
        server_name  localhost qsm.net www.qsm.net;
 
        #设置默认访问首页
        index index.php index.html;
        #默认编码
        charset utf-8;
 
        #定义本虚拟主机的访问日志
        access_log  logs/access.log;
        
        location /jd/insure {
            proxy_pass http://insure_server_upstream;        #引用upstream
        }
        location /jd/express {
            proxy_pass http://express_server_upstream;        #引用upstream
            deny 127.0.0.1;  #拒绝的ip
           	allow 172.18.5.54; #允许的ip    
        }
        
        #错误设置
        error_page   500 502 503 504  /404.html;
        location = /404.html {
            root   html;
        }
    }
}
4、配置格式

1、配置文件的全局块:配置服务器整体运行的配置指令,比如worker的个数
2、events块:影响 Nginx 服务器与用户的网络连接,比如每个worker的最大连接数等
3、http 块
1、http 全局块:日志(格式、位置等)自定义等配置
2、server 块:相当于一个虚拟服务器,配置监听本虚拟主机的名称或IP配置等
1、location 块(多个):根据请求路径正则判断给不同的真实服务器请求。proxy_pass

查看版本号:./nginx -v
启动: ./nginx
停止: ./nginx -s stop
重新加载: ./nginx -s reload
以上都是在sbin命令中


【完】
喜欢就个赞吧

正在去BAT的路上修行

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值