• 中间件之Nginx的反向代理


    一、引言:代理服务器的简介

    本节介绍代理服务器的基本配置。 学习如何通过不同协议将 NGINX 请求传递给代理的服务器,修改发送到代理服务器的客户端请求标头,以及配置来自代理服务器的响应缓冲。

    代理通常用于在多个服务器之间分配负载,无缝地显示来自不同网站的内容,或者通过 HTTP以外的协议将请求传递给应用服务器
    在这里插入图片描述

    二、将请求传递给代理的服务器

    当 NGINX 代理请求时,它将请求发送到指定的代理服务器,获取响应,并将其发送回客户端。 可以使用指定的协议将请求代理到 HTTP 服务器(另一个 NGINX 服务器或任何其他服务器)或非 HTTP 服务器(可以运行使用特定框架开发的应用程序,如 PHP 或 Python)。

    要将请求传递给 HTTP 代理服务器,则在一个 location 块内指定 proxy_pass 指令。 例如:

    worker_processes 4;
    
    events {
    	worker_connections 1024;
    }
    
    http {
    	server {
    		listen 8888;
    		location / {
    			proxy_pass http://192.168.7.146:8889;
    		}
    	}
    	server {
                    listen 8889;
            }
    	server {
                    listen 8890;
            }
    	server {
                    listen 8891;
            }
    }
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24

    此 示 例 配 置 将 在 此 location 处 理 的 所 有 请 求 传 递 到 指 定 地 址(www.example.com/link/)处的代理服务器。该地址可以指定为域名或 IP 地址。 该地址还可能包括一个端口。

    三、代理多个服务器

    在一个 location 块内指定 proxy_pass 指令可以代理一个服务器,也可以使用upstream指令代理多个服务器。示例:

    worker_processes 4;
    
    events {
    	worker_connections 1024;
    }
    
    http {
    
    	upstream backend {
    		server 192.168.7.146:8889;
    		server 192.168.7.147:8890;
    	}
    
    	server {
    		listen 8888;
    		location / {
    			proxy_pass http://backend;
    		}
    	}
    	server {
                    listen 8889;
            }
    	server {
                    listen 8890;
            }
    	server {
                    listen 8891;
            }
    }
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30

    backend 是模块名,里面就可以写上多个需要代理的服务器。
    不能使用多个proxy_pass来代理,需要使用upstream来实现代理多个服务器。

    四、代理多个服务器的负载均衡

    可以使用weight来调整权重,实现负载均衡(注意weight和等号之间不能出现空格)。
    不仅仅可以代理其他的服务器,也可以代理本机的。

    worker_processes 4;
    
    events {
    	worker_connections 1024;
    }
    
    http {
    
    	upstream backend {
    		server 192.168.7.146:8889 weigth=2;
    		server 192.168.7.147:8890 weigth=3;
    		erver 192.168.7.148 weigth=1;
    	}
    
    	server {
    		listen 8888;
    		location / {
    			proxy_pass http://backend;
    		}
    	}
    	server {
                    listen 8889;
            }
    	server {
                    listen 8890;
            }
    	server {
                    listen 8891;
            }
    }
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31

    五、restful介绍

    首先来看看常见的资源访问地址模式:

    https://blog.csdn.net/Long_xu?type=blog&&name=xxx
    
    • 1

    如果没有使用restful,那么Nginx的配置文件需要这样配置:

    http {
    	server {
    		listen 8888;
    		location /type=blog&&name=xxx {
    			proxy_pass http://192.168.7.146:8889;
    		}
    	}
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8

    显得有些复杂和固化。

    如果使用restful,就可以这样配置:

    http {
    	server {
    		listen 8888;
    		location /FLY/blog {
    			
    		}
    		location /FLY {
    			
    		}
    	}
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11

    如果conf的内容过长,还可以进行模块化配置,使用include引用:

    比如把下面的:

    # test.conf
    worker_processes 4;
    
    events {
    	worker_connections 1024;
    }
    
    http {
    
    	upstream backend {
    		server 192.168.7.146:8889 weigth=2;
    		server 192.168.7.147:8890 weigth=3;
    		erver 192.168.7.148 weigth=1;
    	}
    
    	server {
    		listen 8888;
    		location / {
    			proxy_pass http://backend;
    		}
    		location /FLY/blog {
    			
    		}
    		location /FLY {
    			
    		}
    	}
    	server {
                    listen 8889;
            }
    	server {
                    listen 8890;
            }
    	server {
                    listen 8891;
            }
    }
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38

    改为:

    # test.conf
    worker_processes 4;
    
    events {
    	worker_connections 1024;
    }
    
    http {
    
    	upstream backend {
    		server 192.168.7.146:8889 weigth=2;
    		server 192.168.7.147:8890 weigth=3;
    		erver 192.168.7.148 weigth=1;
    	}
    	include ./dir/*.conf
    }
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    # server8888.conf
    server {
    	listen 8888;
    	location / {
    		proxy_pass http://backend;
    	}
    	location /FLY/blog {
    		
    	}
    	location /FLY {
    		
    	}
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    # server8889.conf
    server {
    	listen 8889;
    }
    
    • 1
    • 2
    • 3
    • 4
    # server8890.conf
    server {
    	listen 8890;
    }
    
    • 1
    • 2
    • 3
    • 4
    # server8891.conf
    server {
    	listen 8891;
    }
    
    • 1
    • 2
    • 3
    • 4

    把一个拆分为多个,每个server可以独立。

    六、Nginx conf中http与server的关系

    在conf文件中,是http协议包含server还是server 包含协议呢?它们是N对N还是1对N?

    在计算机中,有很多N对N的场景,但是代码实现过程中,会将其转换为1对N的关系。因为N对N是一个很复杂的流程,不好处理。

    也就是http与server的关系是N对N的关系;只是代码实现会细化变为1对N的逻辑。

    七、进阶:Nginx 基础组件使用

    这是一个前导,主要了解如何将Nginx源码里提供的基础组件拆分出来使用,比如ngx_str、list,queue、hash、array等等。后面会有专门章节介绍Nginx 基础组件使用。

    这里先对ngx_str进行一个简单的使用。

    #include 
    
    #include "ngx_config.h"
    #include "ngx_conf_file.h"
    #include "nginx.h"
    #include "ngx_core.h"
    #include "ngx_string.h"
    //#include "ngx_palloc.h"
    //#include "ngx_array.h"
    //#include "ngx_hash.h"
    
    int main()
    {
    	ngx_str_t str = ngx_string("Hello World!");
    
    	printf("string length: %ld\n", str.len);
    	printf("string: %s\n", str.data);
    
    	return 0;
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20

    编译:

    gcc -o ngx_code ngx_code.c -I /home/fly/workspace/nginx-1.13.7/src/core/ -I /home/fly/workspace/nginx-1.13.7/src/event/ -I /home/fly/workspace/nginx-1.13.7/src/os/unix/ -I /home/fly/workspace/nginx-1.13.7/objs/ -I /home/fly/workspace/pcre-8.41/ -I /home/fly/workspace/openssl-1.1.0g/include/
    
    
    • 1
    • 2

    注意,库的路径要换成自己的。

    执行结果:

    # ./ngx_code
    string length: 12
    string: Hello World!
    
    
    • 1
    • 2
    • 3
    • 4

    把编译过程做成makefile:

    # 方便起见一般都会先定义编译器链接器
    CC = gcc
    LD = gcc
    # 正则表达式表示目录下所有.c文件
    SRCS = $(wildcard *.c)
    # OBJS表示SRCS中把列表中的.c全部替换为.o
    OBJS = $(patsubst %c, %o, $(SRCS))
    # -I指定头文件目录
    INCLUDE = -I /home/fly/workspace/nginx-1.13.7/src/core/ -I /home/fly/workspace/nginx-1.13.7/src/event/ -I /home/fly/workspace/nginx-1.13.7/src/os/unix/ -I /home/fly/workspace/nginx-1.13.7/objs/ -I /home/fly/workspace/pcre-8.41/ -I /home/fly/workspace/openssl-1.1.0g/include/
    # -L指定库文件目录,-l指定静态库名字(去掉文件名中的lib前缀和.a后缀)
    # LIB = -L./libs -ltomcrypt
    # 开启编译warning和设置优化等级
    # CFLAGS = -Wall -O2
    # 可执行文件的名字
    TARGET = ngx_code
    # .PHONE伪目标
    .PHONY:all clean
    # 要生成的目标文件
    all: $(TARGET)
    # 链接时候指定库文件目录及库文件名
    $(TARGET): $(OBJS)
    	$(LD) -o $@ $^ $(LIB)
     
    # 编译时候指定头文件目录
    %.o:%.c
    	$(CC) -c $^ $(INCLUDE) $(CFLAGS) 
    
    clean:
    	rm -f $(OBJS) $(TARGET)
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29

    总结

    1. 学会Nginx反向代理的conf文件配置。
    2. 了解nginx基础组件的源码组件:ngx_str、list、queue、hash、array、log、原子操作、共享内存、线程池、内存池、红黑树、http协议等等。
    3. nginx module开发:filter,handler,upstream。

    在这里插入图片描述

  • 相关阅读:
    2022英伟达显卡排名天梯图
    使用OpenPCDet实现VoxelNext进行训练和测试:实现NuScence数据集的全局感知结果可视化
    【数组】【快慢指针】Leetcode 27 移除元素
    Kylin ext3/4 xfs手动扩容根分区
    Nginx - 虚拟主机与域名解析
    自己实现 SpringMVC 底层机制 系列之-实现任务阶段 8- 完成返回 JSON 格式数据-@ResponseBody
    s19.基于 Kubernetes v1.25.0(kubeadm) 和 Docker 部署高可用集群(一)
    以antd为例 React+Typescript 引入第三方UI库
    卡车上的最大单元数
    Rmarkdown教程
  • 原文地址:https://blog.csdn.net/Long_xu/article/details/127887144