• nginx安装、编译和参数讲解


    传统上基于进程或线程模型架构的web服务通过每个进程或每个线程处理并发连接请求,这势必会在网络I/O操作时产生阻塞,其另一个必然结果则是对内存或CPU的利用率低下。生成一个新的进程/线程需要实现备好其运行时环境,这包括为其分配堆内存和栈内存,以及为其创建新的执行上下文等。这些操作都需要占用CPU,而且过多的进程/线程还会带来线程抖动或频繁的上下文切换,系统性能也会由此进一步下降。

    在设计的最初阶段,nginx的主要着眼点就是其高性能以及对物理计算资源的高密度利用,因此其采用了不同的架构模型,受启发于多中操作系统设计中基于“事件”的高级处理机制,nginx采用了模块化、时间驱动、异步、单线程及非阻塞设计的架构,并大量采用了多路复用及时间通知机制。在nginx中,连接请求由为数不多的几个仅包含一个线程的进程worker以高效的回环(run-loop)机制进行处理,而每个worker可以并行处理数千个的并发连接及请求。

    如果负载以CPU密集型应用为主,如SSL或压缩应用,则worker数应与CPU数相同;如果负载以IO密集型为主,如相应大量内容给客户端,则worker数应该为CPU个数的1.5或2倍。

    nginx会按需同时运行多个进程;一个主进程(master)和几个工作进程(worker),配置了缓存时还会有缓存加载器进程(cache loader)和缓存管理器进程(cache manager)等,所有进程均是仅含有一个进程,并主要通过“共享内存”的机制实现进程间通信,主进程以root用户身份运行,而worker、cache loader 和cache manager 均应以非特权用户身份运行。

    主进程主要完成如下工作:
    1.读取并验证配置信息;
    2.创建、绑定及关闭套接字;
    3.启动、终止及维护worker进程的个数;
    4.无须终止服务而重新配置工作特性;
    5.控制非中断式程序升级,启用新的二进制程序并在需要时回滚至老版本;
    6.重新打开日志文件;
    7.编译嵌入式perl脚本;

    worker进程主要完成的任务包括:
    1.接收、传入并处理来自客户端的连接;
    2.提供反向代理及过滤功能;
    3.nginx任何能完成的其他任务;

    cache loader进程主要完成的任务包括:
    1.检查缓存存储中的缓存对象;
    2.使用缓存元数据建立内存数据库;

    cache manager 进程的主要任务:
    1.缓存的失效及过期检验;

    Nginx的配置有着几个不同的上下文:main、http、server、upstream和location(还有实现邮件伴服务反向代理的mail)。配置语法的格式和定义方式遵循所谓的C风格,因此支持嵌套,还有着逻辑清晰并已于创建、阅读和维护等优势。

    Nginx的代码是由一个核心和一系列的模块组成,核心主要用于提供web server的基本功能,以及web和mail反向代理的功能:还用于启用网络协议,创建必要的运行时环境以及确保不同的模块之间平滑地进行交互。不过,大多跟协议相关的功能和某引用特有的功能都是由nginx的模块实现的。这些功能模块大致可以分为事件模块、阶段性处理器、输出过滤器、变量处理器、协议、upstream和负载均衡几个类别,这些共同组成了nginx的http功能。事件模块主要用于提供OS独立的(不同操作系统 的事件机制有所不同)
    事件通知机制如kqueue或epoll等,协议模块则负责实现nginx通过http、tls/ssl、smtp、pop3以及imap与对应的客户端建立会话。

    用户请求过来了,先到达网卡,网卡将请求交给内核,内核将请求交给监听在80端口(套接字)上的应用程序(worker进程),worker进程发现请求通过连接建立,接入请求,分析发现用户请求是一个静态文件,然后进行系统调用(I/O),内核给用户进程准备缓冲空间,内核通过磁盘加载这个文件到缓冲当中。然后再将这个文件复制到进程自己的地址空间,然后这个程序就能封装一个小的报文(http响应首部),然后再将报文交给内核,由内核封装TCP首部,IP首部,最终响应给客户端。而sendfile机制就是省去了将静态文件交给用户空间这一步,直接再内核完成所有封装并响应给客户端,尽可能避免了数据拷贝操作。
    
    user
    group
    worker
    http {
        server {
            location {
                
            }
        }
    }
    mail {
        
    }
    

    1. 安装nginx

    # 1.解决依赖关系
    编译安装nginx需要实现需要安装开发包组“Development Tools”和“Development Libraries”.同时,还需要专门安装pcre-devel包:
    yum -y install pcre-devel
    
    # 2.安装
    首先添加用户nginx,实现以运行ngnix服务进程:
    # groupadd -r nginx
    # useradd -r -g nginx nginx
    接着开始编译和安装:
    # ./configure --prefix=/usr 
    --sbin-path=/usr/sbin/nginx 
    --conf-path=/etc/nginx/nginx.conf 
    --error-log-path=/var/log/nginx/error.log 
    --http-log-path=/var/log/nginx/access.log 
    --pid-path=/var/run/nginx/nginx.pid 
    --lock-path=/var/lock/nginx.lock 
    --user=nginx 
    --group=nginx 
    --with-http_ssl_module 
    --with-http_flv_module 
    --with-http_stub_status_module 
    --with-http_gzip_static_module 
    --http-client-body-temp-path=/var/tmp/nginx/client/ 
    --http-proxy-temp-path=/var/tmp/nginx/proxy/ 
    --http-fastcgi-temp-path=/var/tmp/nginx/fcgi/ 
    --http-uwsgi-temp-path=/var/tmp/nginx/uwsgi/ 
    --http-scgi-temp-path=/var/tmp/nginx/scgi 
    --with-pcre 
    --with-file-aio 
    
    
    解释参数:
    '''
    ./configure --prefix=/usr # 默认安装路径
    --sbin-path=/usr/sbin/nginx #nginx自身的可执行路径
    --conf-path=/etc/nginx/nginx.conf  # 主配置文件路径,如果不存在,会自动创建,该路径下还有其他几个nginx相关的配置文件
    --error-log-path=/var/log/nginx/error.log # 错误日志
    --http-log-path=/var/log/nginx/access.log  # 访问日志
    --pid-path=/var/run/nginx/nginx.pid  # pid文件
    --lock-path=/var/lock/nginx.lock # 锁文件
    --user=nginx 
    --group=nginx 
    --with-http_ssl_module # 使用此模块
    --with-http_flv_module 
    --with-http_stub_status_module 
    --with-http_gzip_static_module # 支持gzip压缩
    --http-proxy-client-body-temp-path=/var/tmp/nginx/client/  # 请求报文的主体,除了http首部
    --http-proxy-temp-path=/var/tmp/nginx/proxy/ # 代理目录
    --http-fastcgi-temp-path=/var/tmp/nginx/fcgi/ 
    --http-uwsgi-temp-path=/var/tmp/nginx/uwsgi/ # 如果不使用python框架,这个参数可以不启用
    --http-scgi-temp-path=/var/tmp/nginx/scgi 
    --with-pcre=/usr
    --with-file-aio
    --with-http_image_filter_module # 实现图片过滤
    
    
    
    使用 ./configure --help |less  查看具体都有哪些参数
    '''
    # make && make install
    说明:如果想使用nginx的perl模块,可以通过为configure脚本添加 --with-http_perl_module选项来实现,但目前此模块仍处于实验性使用阶段,可能会再运行中出现以外,因此,其实现方式这里不再介绍。如果想使用基于nginx的cgi功能,也可以基于FCGI来实现,具体实现方法请参照网上的文档。
    
    3.为nginx提供SysV init 脚本:
    
    新建文件/etc/rc.d/init.d/nginx,内容如下:
    #!/bin/bash
    # 
    # 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 networking configuration.
    . /etc/sysconfig/network
    
    # Check that networking is up.
    [ "$NETWORKING" = "no" ] && exit 0
    
    nginx="/usr/sbin/nginx"
    prog=$(basename $nginx)
    
    NGINX_CONF_FILE="/etc/nginx/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() {
        rh_status >/dev/null 2>&1
    }
    
    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|reload|force-reload|configtest}"
            exit 2
    esac
    
    而后为此脚本赋予执行权限:
    # chmod +x /etc/rc.d/init.d/nginx
    
    添加至服务管理列表,并让其开机自动启动:
    # chkconfig --add nginx
    # chkconfig nginx on
    
    而后就可以启动服务并测试了:
    # service nginx start
    
    二、安装mysql-5.5.28
    1.准备一个逻辑卷,并将其挂载至特定目录即可,这里不再给出过程。
    这里假设其逻辑卷的挂载目录为/mydata,而后需要创建/mydata/data目录作为mysql数据的存放目录。
    2.新建用户以安全方式运行进程:
    
    URI 路径:
    	http://www.baidu.com
    location [ = | ~ | ~* | ^~ ] uri {...}
    location URI {};
    	对当前路径及子路径下的所有对象都生效;
    location = URI {};
    	精确匹配指定路径,不包括子路径,因此,只对当前资源生效;
    location ~ URI {};
    location ~* URI {};
        模式匹配URI,此处的URI可使用正则表达式,~区分字符大小写,~*不区分字符大小写;
    location ^~ URI {};
    	不使用正则表达式
    
    location /bbs/ {
                root  /web;
                index index.html index.htm;
                auth_basic "Restricted Area..";  # 需要用户通过认证才能访问
                auth_basic_user_file /etc/nginx/.users;
            }
    需要创建需要认证的账户名和密码
    htpasswd -c -m /etc/nginx/.users tom # 第一次需要指定-c 创建.users文件,接下来的创建用户就不需要指定-c了
    htpasswd -m /etc/nginx/.users jerry
    
    nginx -s reload
    
    
    
    

    Paxos算法

    再网络拥塞控制领域,我们知道有个非常有名的算法叫做Nagle算法(Nagle algorithm),这是使用它的发明人John Nagle的名字来命名的,John Nagle 在1984年首次用这个算法来尝试解决福特汽车公司的网络拥塞问题(RFC 896),该问题的具体描述是:如果我们的应用程序一次产生1个字节的数据,而这个1个字节数据又以网络数据包的形式发送到远端服务器,那么就很容易导致网络由于太多的数据包而过载。比如,当用户使用Telnet连接到远程服务器时,每一次击键操作就会产生1个字节数据,进而发送出去一个数据包,所以,在典型情况下,传送一个只拥有1个字节有效数据的数据包,却要花费40个字节长包头(即IP头20字节+tcp头20字节)的额外开销,这种有效荷载(payload)利用率极其低下的情况被统称之为愚蠢窗口症候群(Silly Window Syndrome)。可以看到,这种情况对于轻负载的网络来说,可能还可以接受,但是对于重负载的网络而言,就极有可能承载不了而轻易的发生拥塞雍痪。针对上面提到的这个状况,Nagle算法的改进在于:如果发送端欲多次发送包含少量字符的数据包(一般情况下,后面同意称长度小于MSS的数据包为小包,与此相对,称长度等于MSS的数据包为大包,为了某些对比说明,还有中包,即长度比小包长,但又不是一个MSS的包),则发送端会先将第一个小包发送出去,而将后面到达的少量字符数据都缓存起来而不立即发送,直到收到接收端对前一个数据包报文段的ACK确认、或当前字符数据紧急数据,或者积攒到了一定数量的数据(比如缓存的字符数据已经到达数据包报文段的最大长度)等多种情况才将其组成一个较大的数据包发送出去。
    
    TCP中的Nagle算法默认是启用的,但是它并不是适合任何情况,对于telnet或rlogin这样的远程登录应用的确比较合适(原本就是为此而设计),但是在某些应用场景下我们却又需要关闭它。
    
    Nagle算法是指发送方发送的数据不会立即发出,而是先放在缓冲区,等缓存区满了再发出,发送完一批数据后,会等待接收方对这批数据的回应,然后再发送下一批数据。Nagle算法适用于发送方需要发送大批量数据,并且接收方会即使做出回应的场合,这种算法通过减少传输数据的次数来提高通信效率,如果发送方持续地发送小批量的数据,并且接受方不一定会立即发送响应数据,那么Nagle算法会使发送方运行很慢,对于GUI程序,如网络游戏程序(服务器需要实时跟踪客户端鼠标的移动),这个问题尤其突出,客户端鼠标位置改动的信息需要实时发送到服务器上,由于Nagle算法采用缓冲,大大减低了实时响应速度,导致客户程序运行很慢,这个时候就需要使用TCP_MODELAY选项。
    
  • 相关阅读:
    python pandas里面的一些函数及用法
    Python enumerate() 函数
    论文笔记:EPTD模型/ Efficient and Privacy-Preserving Truth Discovery in Mobile Crowd Sensing Systems
    论文笔记:Adversarial Attacks and Defenses in Deep Learning 对抗训练部分
    一周入门Linux 基础篇 虚拟机快照
    一周入门Linux 基础篇 虚拟机克隆
    一周入门Linux 基础篇 网络连接的三种方式
    一周入门Linux 基础篇 安装vm和Centos
    B站考研网课推荐
    关于我
  • 原文地址:https://www.cnblogs.com/zhangchaocoming/p/14734527.html
Copyright © 2020-2023  润新知