简体   繁体   English

Nginx作为Nexus的反向代理服务器 - 无法在docker环境中连接

[英]Nginx as reverse proxy server for Nexus - can't connect in docker environment

I have environment builded upon docker containers (in boot2docker). 我在docker容器上建立了环境(在boot2docker中)。 I have following docker-compose.yml file to quickly setup nginx and nexus servers : 我有以下docker-compose.yml文件来快速设置nginx和nexus服务器:

version: '3.2'

services:
  nexus:
    image: stefanprodan/nexus
    container_name: nexus
    ports:
      - 8081:8081
      - 5000:5000

  nginx:
    image: nginx:latest
    container_name: nginx
    ports:
      - 5043:443
    volumes:
      - /opt/dm/nginx2/nginx.conf:/etc/nginx/nginx.conf:ro

Nginx has following configuration (nginx.conf) Nginx有以下配置(nginx.conf)

user  nginx;
worker_processes  1;

error_log  /var/log/nginx/error.log warn;
pid        /var/run/nginx.pid;

events {
    worker_connections  1024;
}

http {

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

    access_log  /var/log/nginx/access.log  main;

    proxy_send_timeout 120;
    proxy_read_timeout 300;
    proxy_buffering    off;
    keepalive_timeout  5 5;
    tcp_nodelay        on;

    server {
        listen         80;
        server_name    demo.com;

    return         301 https://$server_name$request_uri;
    }

    server {
        listen   443 ssl;
        server_name  demo.com;

        # allow large uploads of files - refer to nginx documentation
        client_max_body_size 1024m;

        # optimize downloading files larger than 1G - refer to nginx doc before adjusting
        #proxy_max_temp_file_size 2048m

        #ssl on;
        #ssl_certificate      /etc/nginx/ssl.crt;
        #ssl_certificate_key  /etc/nginx/ssl.key;

        location / {
            proxy_pass http://nexus:8081/;
            proxy_set_header Host $host;
            proxy_set_header X-Real-IP $remote_addr;
            proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header X-Forwarded-Proto "https";
        }
    }
}

Nexus seems to work very well. Nexus似乎运作良好。 I call sucessfully curl http://localhost:8081 on docker host machine. 我在docker主机上调用sucessfully curl http://localhost:8081 This return me html of nexus login site. 这返回我的nexus登录网站的html。 Now I want to try nginx server. 现在我想尝试nginx服务器。 It is configured to listen on 443 port, but SSL is right now disabled (I wanted to test it before diving into SSL configuration). 它配置为侦听443端口,但SSL现在已禁用(我想在深入SSL配置之前测试它)。 As you can notice, my ngix container maps port 443 to port 5043. Thus, I try to use following curl command : curl -v http://localhost:5043/ . 您可以注意到,我的ngix容器将端口443映射到端口5043.因此,我尝试使用以下curl命令: curl -v http://localhost:5043/ Now I expect that my http request is going to be send to nginx and proxied to proxy_pass http://nexus:8081/; 现在我希望我的http请求将被发送到nginx并代理到proxy_pass http://nexus:8081/; nexus. 关系。 Nexus hostname is visible within docker container network and is accesible from nginx container. Nexus主机名在docker容器网络中可见,可从nginx容器访问。 Unfortunately in reponse I receive : 不幸的是,我收到了回复:

*   Trying 127.0.0.1...
* Connected to localhost (127.0.0.1) port 5043 (#0)
> GET / HTTP/1.1
> Host: localhost:5043
> User-Agent: curl/7.49.1
> Accept: */*
>
* Empty reply from server
* Connection #0 to host localhost left intact
curl: (52) Empty reply from server

I was checking nginx logs, error, access but these logs are empty. 我正在检查nginx日志,错误,访问但这些日志是空的。 Can somebody help me solving this problem ? 有人可以帮我解决这个问题吗? It should be just a simple example of proxying requests, but maybe I misunderstand some concept ? 它应该只是一个代理请求的简单例子,但也许我误解了一些概念?

Do you have an upstream directive in your nginx conf (placed within the http directive)? 你的nginx conf有一个upstream指令(放在http指令中)吗?

upstream nexus {
    server <Nexus_IP>:<Nexus_Port>;
}

Only then nginx can correctly resolve it. 只有这样nginx才能正确解析它。 The docker-compose service name nexus is not injected to the nginx container on runtime. docker-compose服务名称nexus不会在运行时注入nginx容器。

You can try links in docker-compose: 您可以尝试使用docker-compose中的links

https://docs.docker.com/compose/compose-file/#links https://docs.docker.com/compose/compose-file/#links

This gives you an alias for the linked container in your /etc/hosts . 这为您提供了/etc/hosts链接容器的alias But you still need an upstream directive . 但是你仍然需要一个upstream directive Update : If resolvable, you can as well use the names directly in nginx directives like location . 更新 :如果可解析,您也可以直接在nginx directives使用名称,例如location

https://serverfault.com/questions/577370/how-can-i-use-environment-variables-in-nginx-conf https://serverfault.com/questions/577370/how-can-i-use-environment-variables-in-nginx-conf

As @arnold's answer you are missing the upstream configuration in your nginx. 正如@ arnold的回答,你错过了nginx中的上游配置。 I saw you are using the stefanprodan nexus image, see his blog for the full configuration. 我看到你正在使用stefanprodan nexus图片,请参阅他的博客了解完整配置。 Below you can find mine (remember to open ports 8081 and 5000 of nexus even the entrance point is the 443). 下面你可以找到我的(记得打开端口8081和5000的nexus甚至入口点是443)。 Besides you need to include the certificate because docker client requires ssl working: 此外,您需要包含证书,因为docker客户端需要ssl工作:

worker_processes 2;

events {
    worker_connections 1024;
}

http {
    error_log /var/log/nginx/error.log warn;
    access_log  /dev/null;
    proxy_intercept_errors off;
    proxy_send_timeout 120;
    proxy_read_timeout 300;

    upstream nexus {
        server nexus:8081;
    }

    upstream registry {
        server nexus:5000;
    }

    server {
        listen 80;
        listen 443 ssl default_server;
        server_name <yourdomain>;

        add_header Strict-Transport-Security "max-age=31536000; includeSubDomains" always;

        ssl_certificate /etc/letsencrypt/live/<yourdomain>/fullchain.pem;
        ssl_certificate_key /etc/letsencrypt/live/<yourdomain>/privkey.pem;
        ssl_session_cache shared:SSL:10m;
        ssl_session_timeout 5m;
        ssl_protocols TLSv1 TLSv1.1 TLSv1.2;
        ssl_prefer_server_ciphers on;
        ssl_dhparam /etc/ssl/certs/dhparam.pem;
        ssl_ciphers "EECDH+AESGCM:EDH+AESGCM:ECDHE-RSA-AES128-GCM-SHA256:AES256+EECDH:DHE-RSA-AES128-GCM-SHA256:AES256+EDH:ECDHE-RSA-AES256-GCM-SHA384:DHE-RSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-SHA384:ECDHE-RSA-AES128-SHA256:ECDHE-RSA-AES256-SHA:ECDHE-RSA-AES128-SHA:DHE-RSA-AES256-SHA256:DHE-RSA-AES128-SHA256:DHE-RSA-AES256-SHA:DHE-RSA-AES128-SHA:ECDHE-RSA-DES-CBC3-SHA:EDH-RSA-DES-CBC3-SHA:AES256-GCM-SHA384:AES128-GCM-SHA256:AES256-SHA256:AES128-SHA256:AES256-SHA:AES128-SHA:DES-CBC3-SHA:HIGH:!aNULL:!eNULL:!EXPORT:!DES:!MD5:!PSK:!RC4";

        keepalive_timeout  5 5;
        proxy_buffering    off;

        # allow large uploads
        client_max_body_size 1G;

        location / {
            # redirect to docker registry
            if ($http_user_agent ~ docker ) {
                    proxy_pass http://registry;
            }
            proxy_pass http://nexus;
            proxy_set_header Host $host;
            proxy_set_header X-Real-IP $remote_addr;
            proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
            proxy_set_header X-Forwarded-Proto "https";
        }
    }
}

The certificates are generated using letsencrypt or certbot. 证书使用letsencrypt或certbot生成。 The rest of the configuration is to have an A+ in ssllabs analysis as it is explained here 该构造的其余部分是具有在A + ssllabs分析 ,因为它是解释这里

Your docker-compose of 5000 port is an dynamic port(Because it hadn't been exposed ) , so you cannot connect the 5000 port because the 您的docker-compose是5000端口是一个动态端口(因为它没有被暴露),所以你无法连接5000端口,因为

ports:
      - 8081:8081
      - 5000:5000

are not efficient . 效率不高。

you can use like this: 你可以像这样使用:

  1. Build a new Dockerfile and expose 5000 port (Mine name is ) 构建一个新的Dockerfile并公开5000端口(我的名字是)

     FROM sonatype/nexus3:3.16.2 EXPOSE 5000``` 
  2. Use new image to start the container and publish the port . 使用新映像启动容器并发布端口。

version: "3.7"
    services:
      nexus:
        image: 'feibor/nexus:3.16.2-1'
        deploy:
          placement:
            constraints:
              - node.hostname == node1
          restart_policy:
            condition: on-failure
        ports:
          - 8081:8081/tcp
          - 5000:5000/tcp
        volumes:
          - /mnt/home/opt/nexus/nexus-data:/nexus-data:z

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM