Search code examples
dockerdocker-composeport

Connecting multiple container replicas to a single container without port conflicts


I currently have two types of Docker containers: a redis server, and a Node.js app. With just one of each, I can get them to interact just fine. The redis server listens for connections on the default port 6379. The Node.js app connects using

const redis_client = redis.createClient({
  socket: {
    host: 'redis-server', # name of the redis container in my docker-compose.yml
    port: 6379,
  }
});

and in its docker-compose.yml definition has

node-app:
  # ...other configs...
  ports:
    - "6379:6379"

This works, all is well and good.

I'm now trying to scale this up to allow for several Node.js app container instances to interact with one redis container instance. I originally tried adding

deploy:
  replicas: 2

to my node-app definition, but on $ docker compose up -d this throws Error response from daemon: Ports are not available: exposing port TCP 0.0.0.0:6379 -> 0.0.0.0:0: listen tcp 0.0.0.0:6379: bind: Only one usage of each socket address (protocol/network address/port) is normally permitted.

How can I attach multiple containers to one container in a way that's scalable (i.e. not just hardcoding two node-app instances)?


Solution

  • In order to create multiple replicas of the same service running on different ports but exposing the same one, specify a range of port numbers like in the following docker-compose.yml example:

    services:
      node-app:
    ...
        ports:
          - 6379-6381:5432
        deploy:
          replicas: 3
    ...