负载均衡 + Nginx的基本使用

一、了解什么是负载均衡

负载均衡(Server Load Balancer) 是一种将网络流量、计算任务或数据请求分布式到多个服务器或资源 的技术,旨在优化资源使用、最大化吞吐量、减少响应时间,并避免单个节点过载,从而提高系统的可用性 (也就是提高系统的性能,降低单个服务器的压力)、可靠性 (避免单点故障导致的系统崩溃)和扩展性(根据流量动态增减服务器适应业务需求)。

1、负载均衡的分类

根据OSI七层模型(物理,数据链路,网络,传输,会话,表示,应用)分类:

  • 四层负载均衡(基于IP和端口转发,速度快单无法识别应用层内容);
  • 七层负载均衡(解析HTTP/HTTPS等协议,基于URL/Cookie等路由,功能灵活)

根据实现方法划分:

  • 硬件负载均衡:专用设备(如F5、A10),性能高但成本昂贵。
  • 软件负载均衡:通过软件实现(如Nginx(七层)、HAProxy(四层/七层)、LVS(四层)、Envoy),灵活且成本低。
  • 云服务负载均衡:云平台提供的托管服务(如AWS ALB、阿里云SLB)。

根据调度算法划分:

  • 静态算法:轮询(一次分配请求);加权轮询(根据服务器性能分配权重);IP哈希(同一用户IP固定访问某服务器,保持会话粘性)
  • 动态算法:最少连接(优先分配给当前连接数最少的服务器);响应时间优先(选择响应最快的节点)

2、关键技术机制

  1. 健康检查(Health Check):定义检查后端服务器状态(传输层是否能够建立TCP连接,应用层返回的状态码和响应体内容是否正确),自动剔除故障节点。
  2. 会话保持(Session Persistence):确保同一用户的请求在一定时间内分配到同一服务器,常用方式:
    1. Cookie注入:负载均衡器在响应中插入唯一标识,通过该标识分配到指定的服务器。
    2. 源IP绑定:通过哈希算法关联用户IP与服务器,通过IP和哈希算出固定的值,通过这个值找到指定的服务器。
  3. 弹性伸缩(Auto Scaling):结合监控系统,在流量高峰时自动增加服务器实例,低谷时减少
  4. 全局负载均衡(GSLB):跨地域分配流量,实现灾难恢复和就近访问(DNS轮询+地理定位)

3、正向代理和反向代理

正向代理:正向代理是站在客户端以便,为客户端服务,其目的是为了对外部隐藏客户端,客户知道自己在用代理。如下图:员工电脑通过代理访问外部互联网,员工指导自己在使用代理,但是互联网并不知道员工电脑的位置,仅仅指导代理的IP地址。

反向代理:站在服务器一边,为服务器服务,客户端并不知道有代理以为是直达服务器。

二、使用Nginx

Nginx实现负载均衡的核心是通过其反向代理(为了隐藏服务器)功能,结合多种调度算法和健康检查机制,将客户端请求分发到一组后端服务器(Upstream Servers)。

Nginx配置的层级关系为:用户请求 → Nginx实例(一个进程) → server块(虚拟主机) → location块 → upstream组 → 真实后端服务器

Nginx通过ngx_http_proxy_module模块作为反向代理,将请求转发到后端服务器集群。

负载均衡配置主要在 upstream 块中定义,通过proxy_pass指令引用。

python 复制代码
http {
    # 1. 定义后端服务器组(负载均衡池)
    upstream backend_servers {
        server 192.168.1.10:80 weight=3;  # 权重为3
        server 192.168.1.11:80 weight=2;
        server 192.168.1.12:80;
        server backup.example.com:8080 backup;  # 备份服务器(仅在其它服务器故障时启用)
    }

    # 2. 虚拟主机配置,通过Nginx的一个端口80,可以将请求转发到服务器组内的不同后端服务器。
    server {
        listen 80;
        
        location / {
            proxy_pass http://backend_servers;  # 将请求转发到upstream组
            proxy_set_header Host $host;
            proxy_set_header X-Real-IP $remote_addr;
        }
    }
}

1、Nginx中upstream模块的不同算法

无状态算法:每次分配服务器都是独立的选择。

  • 轮询:默认算法,按照顺序分配请求
  • 加权轮询:根据服务器性能分配权重,权重越高分配的请求就越多
  • 最少连接:将请求分配给当前活跃连接数最少的服务器。
  • 响应时间优先:基于服务器响应时间动态分配请求

有状态的算法:既能分配服务器又能保持会话,因为它们基于请求特征进行一致性映射。

  • IP哈希:同一客户端IP的请求始终分配给同一台服务器(用于会话保持)
  • url哈希:基于url哈希,但是负载均衡可能不均匀。
  • 一致性哈希:通过哈希环实现,适用于缓存服务器场景(如Redis集群),减少节点变动对缓存命中率的影响
python 复制代码
# 轮询
upstream backend {
    server backend1.example.com;
    server backend2.example.com;
}
# 加权轮询
upstream backend {
    server backend1.example.com weight=5;  # 50%的流量(权重比例5/(5+3+2))
    server backend2.example.com weight=3;  # 30%
    server backend3.example.com weight=2;  # 20%
}
# IP哈希
upstream backend {
    ip_hash;  # 基于客户端IP的哈希值分配
    server backend1.example.com;
    server backend2.example.com;
}
# 最少连接
upstream backend {
    least_conn;
    server backend1.example.com;
    server backend2.example.com;
}
# 一致性哈希
upstream backend {
    hash $request_uri consistent;  # 根据请求URI哈希,consistent参数启用一致性哈希
    server backend1.example.com;
    server backend2.example.com;
}
# 响应时间优先
upstream backend {
    fair;  # 仅Nginx Plus支持
    server backend1.example.com;
    server backend2.example.com;
}

2、健康检查机制

  • 被动健康检查(默认):通过max_failsfail_timeout参数判断服务器是否健康。
  • 主动健康检查(Nginx plus):定期主动向后端服务器发送探测请求
  • 开源的替代方案:使用ngx_http_upstream_modulemax_fails机制,结合第三方模块如nginx_upstream_check_module,通过外部脚本监控并动态更新Nginx配置
python 复制代码
# 被动检查
upstream backend {
    server backend1.example.com max_fails=3 fail_timeout=30s;  # 30秒内失败3次则标记为不可用
    server backend2.example.com;
}
# 主动检查
upstream backend {
    zone backend_pool 64k;  # 共享内存区域
    server backend1.example.com;
    server backend2.example.com;
    
    health_check interval=5s fails=3 passes=2;  # 每5秒检查一次,失败3次标记为不健康,成功2次恢复
}

3、会话保持

  • IP哈希:同一客户端IP的请求始终分配给同一台服务器(用于会话保持)
  • 基于URL哈希:取模哈希,影响所有映射,可能不均匀。
  • URL一致性哈希,通过哈希环+虚拟节点实现,适用于缓存服务器场景(如Redis集群),减少节点变动对缓存命中率的影响
  • Cookie插入:cookie是服务器发送给客户端,并保存在客户端浏览器小型文本文件;cookie插入是指代理服务器主动设置或修改cookie的内容的行为。
python 复制代码
# Ip哈希
upstream backend {
    ip_hash;
    server backend1.example.com;
    server backend2.example.com;
}
# Nginx Plus可以插入路由Cookie
upstream backend {
    sticky cookie srv_id expires=1h domain=.example.com path=/;
    server backend1.example.com;
    server backend2.example.com;
}
# 基于URL哈希,适用于特定资源固定到同一服务器
upstream backend {
    hash $request_uri;
    server backend1.example.com;
    server backend2.example.com;
}
# 基于URL的一致性哈希,适用于特定资源固定到同一服务器
upstream backend {
    hash $request_uri consistent;
    server backend1.example.com;
    server backend2.example.com;
}

4、其他配置

(1)服务器状态控制

python 复制代码
upstream backend {
    server backend1.example.com down;    # 手动标记为下线(维护时使用)
    server backend2.example.com backup;  # 备份服务器,仅当主服务器全故障时启用
    server backend3.example.com slow_start=30s;  # 慢启动,故障恢复后权重逐渐恢复(Nginx Plus)
}

(2)长链接保持

python 复制代码
upstream backend {
    server backend1.example.com;
    server backend2.example.com;
    
    keepalive 32;                   # 每个worker进程保持的最大空闲连接数
    keepalive_timeout 60s;          # 空闲连接的超时时间
    keepalive_requests 100;         # 单个连接最大请求数
    keepalive_disable msie6;        # 禁用特定浏览器的长连接
}

(3)动态上游配置

python 复制代码
upstream backend {
    zone backend_pool 64k;                    # 启用共享内存
    state /var/lib/nginx/state/backend.conf;  # 持久化状态
}
相关推荐
菜鸟‍2 小时前
【课程学习】
学习·信息与通信
暗然而日章2 小时前
C++基础:Stanford CS106L学习笔记 11 Lambdas表达式
c++·笔记·学习
lxh01132 小时前
2025/12/19学习记录
学习
辞旧 lekkk2 小时前
【c++】c++11(上)
开发语言·c++·学习·萌新
走在路上的菜鸟2 小时前
Android学Dart学习笔记第二十一节 类-点的简写
android·笔记·学习·flutter
黑客思维者2 小时前
机器学习009:监督学习【回归算法】(岭回归)-- 给模型一个“清醒”的约束
学习·机器学习·回归·监督学习·岭回归
深蓝海拓2 小时前
PySide6从0开始学习的笔记(十一) QSS 属性选择器
笔记·python·qt·学习·pyqt
代码游侠3 小时前
学习笔记——Linux进程间通信(IPC)
linux·运维·笔记·学习·算法
xyx-3v3 小时前
RK3506G移植APM飞控的可行性
单片机·学习