dunglas / vulcain

Fast and idiomatic client-driven REST APIs.
https://vulcain.rocks
GNU Affero General Public License v3.0
3.5k stars 104 forks source link

Gateway Server Setup with Docker-Compose #38

Open jessequinn opened 4 years ago

jessequinn commented 4 years ago

Hi,

Just a quick question. I am struggling to get my nginx+ssl configuration working with vulcain. With the current setup i have, see below, i receive the following vulcain error: (site_url represents my real url)

time="2019-12-04T12:09:47Z" level=error msg="http: proxy error: x509: certificate is valid for site_url, not api"

I have the following Docker-compose.yml:

version: '3.7'

services:
  php:
    container_name: mcapi_php
    build:
      context: ./api
      target: api_platform_php
      dockerfile: prod.Dockerfile
      args:
        PHP_VERSION: 7.3
        APCU_VERSION: 5.1.18
        VARNISH_VERSION: 6.3
    healthcheck:
      interval: 10s
      timeout: 3s
      retries: 3
      start_period: 30s
    volumes:
      - "./api:/var/www/html"
    restart: unless-stopped

  api:
    container_name: mcapi_nginx
    image: nginx:1.17-alpine
    depends_on:
      - php
#    ports:
#      - target: 80
#        published: 80
#        protocol: tcp
#      - target: 443
#        published: 443
#        protocol: tcp
    volumes:
      - "./api:/var/www/html"
      - "./api/docker/nginx/conf.d/default.prod.conf:/etc/nginx/conf.d/default.conf"
      - "./api/docker/nginx/nginx.conf:/etc/nginx/nginx.conf"
      - "./api/docker/nginx/nginxconfig.io:/etc/nginx/nginxconfig.io"
      - "./api/docker/data/certbot/conf:/etc/letsencrypt"
      - "./api/docker/data/certbot/www:/var/www/certbot"
    restart: unless-stopped
    command: "/bin/sh -c 'while :; do sleep 6h & wait $${!}; nginx -s reload; done & nginx -g \"daemon off;\"'"

  certbot:
    container_name: mcapi_cerbot
    image: certbot/certbot
    volumes:
      - "./api/docker/data/certbot/conf:/etc/letsencrypt"
      - "./api/docker/data/certbot/www:/var/www/certbot"
    entrypoint: "/bin/sh -c 'trap exit TERM; while :; do certbot renew; sleep 12h & wait $${!}; done;'"

  vulcain:
    container_name: mcapi_vulcain
    image: dunglas/vulcain
    environment:
#      - UPSTREAM=http://cache-proxy
      - UPSTREAM=https://api
      - CERT_FILE=/etc/letsencrypt/live/rsite_url/fullchain.pem
      - KEY_FILE=/etc/letsencrypt/live/site_url/privkey.pem
    depends_on:
#      - cache-proxy
      - api
    volumes:
      - "./api/docker/data/certbot/conf:/etc/letsencrypt"
    ports:
      - target: 443
        published: 443
        protocol: tcp
    restart: unless-stopped

#  cache-proxy:
#    container_name: mcapi_varnish
#    build:
#      context: ./api
#      target: api_platform_varnish
#      dockerfile: prod.Dockerfile
#      args:
#        PHP_VERSION: 7.3
#        APCU_VERSION: 5.1.18
#        VARNISH_VERSION: 6.3
#    depends_on:
#      - api
#    tmpfs:
#      - /usr/local/var/varnish:exec
#    restart: unless-stopped

My guess here, Vulcain requires that nginx be using http only? However, i would prefer to use my nginx ssl setup. Any information would be greatly appreciated.

teohhanhui commented 4 years ago

The Vulcain gateway server is connecting using Host: api, which does not match the Subject Alternate Name (SAN) of the certificate. Is it not possible to just connect using the public domain name?

jessequinn commented 4 years ago

that is correct. I also tried that. using http: site_url and https: site_url and vulcain complained about certificates being unauthorized or something. i can try to get the exact error message after lunch.

teohhanhui commented 4 years ago

Seems like https://github.com/golang/go/issues/28168

We need to override req.Host explicitly?

jessequinn commented 4 years ago

no idea. ill wait for a response. thanks.

the error when using https: site_url

vulcain_1      | time="2019-12-04T20:25:33Z" level=error msg="http: proxy error: x509: certificate signed by unknown authority"
vulcain_1      | 177.74.217.145 - - [04/Dec/2019:20:25:32 +0000] "POST /authenticate HTTP/1.1" 502 23 "" "PostmanRuntime/7.20.1"
vulcain_1      | 2019/12/04 20:25:33 http: TLS handshake error from 3.232.5.187:37056: remote error: tls: bad certificate
Neirda24 commented 4 years ago

If using mkcert you need to mount the $(mkcert -CAROOT)/rootCA.pem into the vulcain container (path = /etc/ssl/certs/ca-certificates.crt) so vulcain will see the certificate as correctly signed.

Regarding the use of the real host instead of the service name a good trick is to use the network config.

networks:
    vulcain:
        name: 'vulcain'

services:
    vulcain:
        networks:
            default: {}
            vulcain: {}
    app:
        networks:
            default: {}
            vulcain:
                aliases:
                    - 'site_url'