How to deploy multiple instances of a stack listening on the same port to Docker Swarm (behind a reverse proxy)?

Viewed 605

I have a multi-container web application which is defined in a docker-compose.yml file. In our test environment, I wish to run multiple instances of this stack on the same Docker Swarm host. The stacks will be identical save for some minor configuration details (e.g. each stack may use different databases and/or container image tags).

Specifically, I would like it to work as follows:

  • https://awesomeco.com/dev-app/ will point to the dev stack
  • https://awesomeco.com/test-app/ will point to the test stack
  • https://awesomeco.com/qa-app/ will point to the QA stack

All 3 stacks will use the same docker-compose.yml file.

I intend to use a uniquely-named Docker network for each stack to prevent naming collisions when containers communicate within a stack. However, it is not clear to me how I can put an Nginx reverse proxy in front of all of the stacks to route traffic to the correct stack, as each stack will have the same set of service names.

For example, if each stack will has a service named web-app, and my nginx reverse proxy is connected to all the stack networks, how do I route traffic to the "right" instance of the web-app service?

Does anyone know how best to achieve this? And, if it is not possible and each stack must have uniquely named services, won't communication between stack containers suddenly become much harder? For example, the service names are currently hard-coded in individual services' source code e.g. web-app may communicate with the database via http://database-server. Would these names all need to become dynamic too?

1 Answers

This can be achieved using network aliases. These can be used to resolve the container by another name in the network being connected to.

In a docker compose file they would be defined as follows:

services:
  some-service:
    networks:
      some-network:
        aliases:
          - alias1
          - alias3
      other-network:
        aliases:
          - alias2

Accordingly, in my particular use case, each instance of the web-app service would need to have a unique alias in the network it shares with the reverse proxy. This will permit the reverse proxy to differentiate between the different instances of the web-app service.

Further links:

Related