Securing Communication between Nginx and Backend in Docker with Caddy

1. The problem I’m having:

I have a docker container with caddy which redirects traffic to an nginx container. Then nginx serves the Angular frontend will interact with the backend.

My caddy redirects requests to HTTPS for my nginx. However, the requests between nginx and my backend are in HTTP so I get the error:

“Mixed Content: The page at ‘https://srvtest.local/rack’ was loaded over HTTPS, but requested an insecure XMLHttpRequest endpoint ‘http://srvtest.local:8000/api/oracle/ jumb/rack’.”

I would like queries made between Nginx and my backend to also be secure thanks to caddy. How to do ?

Second other small problem: caddy redirects the traffic to nginx but the https is crossed out in my browser and it tells me that the certificate is invalid. For what?

Sorry I’m starting to use caddy.

2. Error messages and/or full log output:

Mixed Content: The page at 'https://srvtest.local/rack' was loaded over HTTPS, but requested an insecure XMLHttpRequest endpoint 'http://srvtest.local:8000/api/oracle/jumb/rack'.

3. Caddy version:

caddy:2.7.6

4. How I installed and ran Caddy:

a. System environment:

Docker

b. Command:

docker-compose -f docker-compose.prod.yml up

c. Service/unit/compose file:

  springboot-backend_v4:
    container_name: springboot-backend_v4
    build:
      context: ./backend
      dockerfile: Dockerfile.dev.backend
    volumes:
      - ./backend:/app
      - maven_cache:/root/.m2
    ports:
      - "8000:8080"
    networks:
      - local
    depends_on:
      - mssql_archiving_v4

  angular-frontend_v4:
    container_name: angular-frontend_v4
    build:
      context: ./frontend
      dockerfile: Dockerfile.dev.angular
    networks:
      - local
    depends_on:
      - springboot-backend_v4
      - mssql_archiving_v4

  caddy_v4:
    container_name: caddy_v4
    build:
      dockerfile: Dockerfile.prod.caddy
    ports:
      - "80:80"
      - "443:443"
    restart: unless-stopped
    networks:
      - local

d. My complete Caddy config:

ba071srv.cbs01dom.local {
    route /* {
    	reverse_proxy angular-frontend_v4:8081
    }
}

ba071srv.cbs01dom.local:8000 {
    route /api/* {
        reverse_proxy springboot-backend_v4:8080
    }
}

Your help is greatly appreciated.

You don’t need this, it’s redundant.

This will set up HTTPS on port 8000. Is that what you want? If not then you should either remove the domain name here (so it’s just :8000) or prefix it with http://.

Why are you using two different ports? Can’t you serve both from the same site/port?

This means your app is serving links with http://. Caddy will pass through the X-Forwarded-Proto: https header which your app should read to know that it should build URLs with https://. Make sure Nginx passes that through correctly, and make sure your app actually does that.

If you use a .local domain, then it’s not valid for publicly trusted TLS. You’d need to use a real domain to be able to have it automatically trusted by browsers.

When using .local domains, Caddy issues the TLS cert using its internal CA, so you need to grab the root CA cert from Caddy’s storage and install it on whatever machines will be making requests to it. See Keep Caddy Running — Caddy Documentation

2 Likes

Thank you for your reply.

Ok, I updated my caddy file :

srv.local {
    reverse_proxy angular-frontend_v4:8081
    reverse_proxy /api/* springboot-backend_v4:8080
}

The problem is that I receive the error in my browser:

GET https://srv.local:8000/api/oracle/jumbos/rack net::ERR_SSL_PROTOCOL_ERROR

Do you know why ?

Caddy is bound to the host on ports 80 and 443. Don’t make a request with srv.local:8000 :thinking:

Did you follow the steps I linked to install Caddy’s root CA cert on your machine? You need to install it on each browser as well, they have their own trust stores separate from the system.

2 Likes

sorry for the beginner’s mistake :stuck_out_tongue:

everything works now thank you very much !

1 Like