当前位置: 首页 > article >正文

什么,NGINX无法正向代理HTTPS?

需求

内网的机器无法访问互联网,但是有些业务服务必须要上网,这个时候就需要一个正向代理,将正向代理部署在一台可以上网的机器,业务应用通过正向代理去访问互联网,同时使用正向代理控制上网策略和权限。

什么是正向代理?

正向代理就是客户端client知道服务器server的地址,也知道proxy的地址,但是client通过proxy,并且告诉proxy,我要访问server的地址,proxy将请求直接转发到server。正向代理最常见的应用是VPN,用来突破client到server的网络限制。

与之对应的就是反向代理,反向代理是client不知道server的地址,但知道proxy的地址,client请求proxy,proxy根据配置的规则转发给server,这里client是不知道具体server的地址,都是通过proxy里的规则进行转发。反向代理最常见的工具就是Nginx。

我现在需要在linux服务器上做正向代理,查了下可以用的工具Squid,Nginx。作为研发来说,Squid比较陌生,nginx那是经常打交道,那就用nginx来搭建了。(nginx是反向代理的代表,其实也可以用来做正向代理)

nginx搭建正向代理

简单介绍下nginx做正向代理的原理,在nginx的配置中加上 resolver 8.8.8.8,其他配置通用,就可以做正向代理了,而这个配置的作用是:指定固定的DNS服务器,而8.8.8.8是Google提供的全球DNS服务器。这样就可以把请求直接转到Google的DNS服务器,然后DNS直接转发出去。完整配置如下:

worker_processes  3;

events {
    worker_connections  1024;
}

http {
    include       mime.types;
    default_type  application/octet-stream;

    log_format  main  '$remote_addr - $remote_user [$time_local] "$request" '
                              '$status $body_bytes_sent $request_body "$http_referer" '
                              '"$http_user_agent" "$http_x_forwarded_for" "$request_time"';

    access_log  /etc/nginx/logs/access.log  main;


    sendfile        on;

    server {
      listen 10080; # 代理监听的端口
      proxy_connect;
      server_name *.com;
      proxy_max_temp_file_size 0; 
      resolver 8.8.8.8; # DNS 解析器,使用 Google 的公共 DNS

      # 处理所有 HTTP 请求
      location / {
        proxy_pass http://$http_host;
        proxy_set_header Host $http_host;
        proxy_ssl_server_name on;
        proxy_ssl_session_reuse off;
        proxy_next_upstream error timeout invalid_header http_502;
        proxy_buffer_size 4k; # 调整缓冲区大小
        proxy_buffers 4 8k;
        proxy_busy_buffers_size 16k;
        }   
     }
}

将nginx运行起来之后,可以直接用curl进行测试代理是否正常,脚本如下:

curl --proxy "http://xx.xx.xx.xx:xx" 'http://www.baidu.com'

如无意外的情况下,可以得到正常返回了。但是我把http改成https之后,立马就返回400 bad request了。这时候可能以为是配置出问题了,其实是nginx代理并不支持https的正向代理转发,搞了半天,不支持https,有点扎心,那么nginx能否支持https的正向代理呢?答案是可以的。

github上有个大神,写了个ngx_http_proxy_connect_module(https://github.com/chobits/ngx_http_proxy_connect_module),用来解决nginx代理无法转发https的问题。可以参照文档内容将模块编译到nginx中。当然如果你觉得这样比较麻烦的话,有更简单的方法。我现在运维部署一些开源软件时,基本都是用docker去部署的,使用docker部署的好处我就不在这里赘述了。那现在我就介绍一下使用docker部署nginx的方式。

首先我们就是找一个已经编译了ngx_http_proxy_connect_module的nginx打包好的镜像,我用的是这个:https://github.com/reiz/nginx_proxy。部署就简单了,docker-compose文件如下

version: '2'
services:
  nginx:
    image: reiz/nginx_proxy:0.0.5
    container_name: proxy_nginx
    restart: always
    ports:
      - '10080:10080'
    environment:
      - TZ=Asia/Shanghai
    volumes:
      - ./nginx.conf:/usr/local/nginx/conf/nginx.conf
      - ./logs:/etc/nginx/logs

接下来是nginx.conf:

daemon off;
worker_processes  auto;

events {
    worker_connections  1024;
}


http {
    server_names_hash_bucket_size 128;

    log_format  main  '$remote_addr - $remote_user [$time_local] "$request" '
                              '$status $body_bytes_sent $request_body "$http_referer" '
                              '"$http_user_agent" "$http_x_forwarded_for" "$request_time"';


    access_log  /etc/nginx/logs/access.log;
    error_log   /etc/nginx/logs/error.log;
    sendfile        on;
    keepalive_timeout 65;

    server {
        listen       10080;
        #server_name  *.com;

        proxy_connect;
        resolver 8.8.8.8 ipv6=off;
        location / {
           proxy_pass http://$http_host;
           proxy_set_header Host $http_host;
        }
      }
}

nginx.conf可以配置访问的地址和禁止访问的地址,及其他的配置,可以看作者的使用文档。

问题

Cannot assign requested address

在连续请求的时候,有一半的请求会报无法分配地址,这个问题还挺棘手,最后发现是ipv6的问题,要关闭ipv6才行,resolver 8.8.8.8 ipv6=off; 关闭了之后就没有出现这个问题。


http://www.kler.cn/a/370493.html

相关文章:

  • 实践深度学习:构建一个简单的图像分类器
  • 51c嵌入式~单片机~合集6
  • 【多线程】线程池
  • 数据结构入门
  • 微信消息群发(定时群发)-UI自动化产品(基于.Net平台+C#)
  • 浙江安吉成新照明电器:Acrel-1000DP 分布式光伏监控系统应用探索
  • fastGpt
  • 计算机网络——开放系统互连参考模型
  • selenium的环境搭建
  • 记录element-ui改造select显示为table,并支持多查询条件
  • 【MATLAB源码-第193期】基于matlab的网络覆盖率NOA优化算法仿真对比VFINOA,VFPSO,VFNGO,VFWOA等算法。
  • JavaEE 多线程第三节 (lambda方法实现多线程/Thread属性和方法/前台线程后台线程)
  • 面试经典 150 题.P88. 合并两个有序数组(001)
  • UE4_Niagara基础实例—10、位置事件
  • 算法的学习笔记—滑动窗口的最大值(牛客JZ59)
  • Unity SpriteEditor 中的图集处理功能
  • 内核上项目【让ntoskrnl.exe保护程序】
  • Vue脚手架
  • 学校NTP电子钟结合教学系统,辅助教学管理
  • Jvm中的堆和栈
  • 微信小程序实现录音,播放录音功能
  • 面试域——岗位职责以及工作流程
  • React如何实现Vue的keepAlive功能
  • 深入了解 kotlinx-datetime:配置与使用指南
  • C++编写台达ME300变频器串口通讯实例
  • 语音提示器-WT3000A离在线TTS方案-打破语种限制/AI对话多功能支持