• Nginx的负载均衡


    作者:健健
    链接:https://zhuanlan.zhihu.com/p/84824603
    来源:知乎
    著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。

    我们都知道,Nginx支持负载均衡,可以很方便的帮助我们进行水平扩容,然而它究竟是依据什么原则进行请求的分发,其中又有哪些负载均衡算法可供选择和配置,今天就让我们好好来了解一下。

    负载均衡的定义

    什么叫负载均衡,我们可以参考一下图片中的这种情况:

     

     

    1. 当客户端发送请求时,会先到Nginx,然后Nginx会将请求分发到后台不同的服务器上。
    2. 如果后台的服务器群中有一个宕机了,那么Nginx会自动忽略这台服务器,不会将请求再次分发到这台服务器上。
    3. 如果有新加入的服务器,Nginx也会将请求分发到这台服务器上。

    我所理解的负载均衡,就是:

    能够将客户端的请求均匀地分发到后台各个应用服务器上,从而缓解服务器压力。
    并且当服务器出现宕机或者扩容时,也能正常运行。

    负载均衡的方法

    上面了解了什么是负载均衡,那么Nginx是怎么实现这个功能的呢?

    upstream和server的使用

    Nginx中负责与上游交互的模块,统称为upstream模块。

    而指定上游服务地址是通过upstreamserver指令完成的,其关系为:

     

     

    指定上游服务器的address时,其地址可以是域名、IP地址或者unix socket地址。

    可以在域名或者IP地址后加端口,如果不加端口,那么默认使用80端口

    address后面可以添加一些参数,比如:

    backup:指定当前server为备份服务,仅当非备份server不可用时,请求才会转发到该server。

    down:标识某台服务已经下线,不再服务。

    举个例子:

    upstream upstream-service {
            server 127.0.0.1:17002;
            server 127.0.0.1:17000;
        }
    

    round-robin

    upstream这个模块中,它还提供了一个最基本的负载均衡算法round-robin

    其功能是:

    以加权轮询的方式访问server指令指定的上游服务。

    这个算法是默认集成在Nginx的框架中,无法移除,所以后面讲解的所有算法都是基于此,所有算法在某些特殊情况下最终都会变成round-robin

    涉及到的指令有:

    1. weight:服务访问的权重,默认是1。
    2. max_conns:server的最大并发连接数,仅作用于单worker进程。
    3. max_fails:在fail_timeout时间内,最大的失败次数。当达到最大失败时,会在fail_timeout时间内不允许再次被选择。
    4. fail_timeout:单位为秒,默认是10秒。指定一段时间内,最大的失败次数max_fails。到达max_fails后,该server不能访问的时间。

    简单的hash模块

    有的时候,正常的轮询算法并不能满足我们的需求,

    比如:带有cookie请求状态的连接,如果应用服务没有设置专门的管理cookie的服务器,那么我们就希望同一个用户能被分配到同一个服务器。

    再比如:我们后端应用需要针对请求当中的参数或者URL,将相同的请求放到相同的服务器上进行处理。

    针对第一种情况,就可以用upstream_ip_hash。针对第二种情况,可以使用upstream_hash

    upstream_ip_hash

    功能:

    以客户端的IP地址作为hash算法的关键字,映射到特定的上游服务器中。
    1. 对IPV4地址使用前3个字节作为关键字,对IPV6则使用完整地址。
    2. 可以使用round-robin算法的参数。
    3. 可以基于realip模块修改用于执行算法的IP地址。

     

    举个例子:

    upstream upstream-service {
            ip_hash;
            server 127.0.0.1:17002;
            server 127.0.0.1:17000;
        }
    

    upstream_hash

    功能:

    通过制定关键字作为hash key,基于hash算法映射到特定的上游服务器中。
    1. 关键字可以含有变量、字符串。
    2. 可以使用round-robin算法的参数。

     

    举个例子(以请求中的参数username作为hash key):

    upstream upstream-service {
            hash user_$arg_username;
            server 127.0.0.1:17002;
            server 127.0.0.1:17000;
        }
    

    一致性哈希算法

    hash算法在一定程度上已经可以满足了我们的业务需求,但如果这个时候遇到应用宕机或者应用扩容,那么hash的总数就会变化,这样很有可能带来大量请求原本请求的服务器会更换,路由会失效,这样对于我们的应用服务也会产生极大的影响,这时候就可以采用一致性hash算法。

    对于一致性哈希算法的理解,可以参考这篇文章:一致性哈希算法的理解与实践

    它的使用也十分简单,就是在之前说的upstream_hash模块的hash指令最后,添加参数consistent,这样Nginx就可以使用一致性哈希算法了。

    举个例子(仍以请求中的参数username作为hash key):

    upstream upstream-service {
            hash user_$arg_username consistent;
            server 127.0.0.1:17002;
            server 127.0.0.1:17000;
        }
    

    总结

    以上就是Nginx中比较常见的负载均衡方法了,还有一些比如最少连接算法等,都是在此之上的一些应用。如果大家有什么疑问,欢迎在下方留言。

  • 相关阅读:
    HDU2026 首字母变大写
    HDU2026 首字母变大写
    Recursive Bubble Sort(递归冒泡排序)
    Recursive Bubble Sort(递归冒泡排序)
    Topological Sorting(拓扑排序)
    Topological Sorting(拓扑排序)
    HDU1870 愚人节的礼物【堆栈+输入输出】
    HDU1870 愚人节的礼物【堆栈+输入输出】
    HDU1233 还是畅通工程
    HDU1233 还是畅通工程
  • 原文地址:https://www.cnblogs.com/fan-1994716/p/11923211.html
Copyright © 2020-2023  润新知