I would like to have an application, database and redis service running in a dev container where I’d be able to access my database and redis inside the container, application and on Windows, this is what currently works just as I wanted for my application and database:
.devcontainer.json
:
{
"name": "Node.js, TypeScript, PostgreSQL & Redis",
"dockerComposeFile": "docker-compose.yml",
"service": "akira",
"workspaceFolder": "/workspace",
"settings": {
"typescript.tsdk": "node_modules/typescript/lib",
"sqltools.connections": [
{
"name": "Container database",
"driver": "PostgreSQL",
"previewLimit": 50,
"server": "database",
"port": 5432,
"database": "akira",
"username": "ailuropoda",
"password": "melanoleuca"
}
],
"editor.formatOnSave": true,
"editor.codeActionsOnSave": {
"source.fixAll": true
}
},
"extensions": [
"aaron-bond.better-comments",
"dbaeumer.vscode-eslint",
"esbenp.prettier-vscode",
"mtxr.sqltools",
"mtxr.sqltools-driver-pg",
"redhat.vscode-yaml"
],
"forwardPorts": [5432],
"postCreateCommand": "npm install",
"remoteUser": "node"
}
docker-compose.yml
:
version: "3.8"
services:
akira:
build:
context: .
dockerfile: Dockerfile
command: sleep infinity
env_file: .env
volumes:
- ..:/workspace:cached
database:
image: postgres:latest
restart: unless-stopped
environment:
POSTGRES_USER: ailuropoda
POSTGRES_DB: akira
POSTGRES_PASSWORD: melanoleuca
ports:
- 5432:5432
volumes:
- pgdata:/var/lib/postgresql/data
redis:
image: redis:alpine
tty: true
ports:
- 6379:6379
volumes:
pgdata:
Dockerfile
:
ARG VARIANT="16-bullseye"
FROM mcr.microsoft.com/vscode/devcontainers/typescript-node:0-${VARIANT}
As you can see I already tried to achieve what I wanted to using networks
but without success, my question is: How can I add Redis to my services while still being able to connect redis and database inside the application and on Windows?
3
Answers
Delete all of the
network_mode:
settings. Compose will use the defaultnetwork_mode: bridge
. You’ll be able to communicate between containers using their Compose service names as host names, as described in Networking in Compose in the Docker documentation.In SO questions I frequently see trying to use
network_mode:
to make other things appear aslocalhost
. That host name is incredibly context-sensitive; if you asked my laptop, one of the Stack Overflow HTTP servers, your application container, or your database container wholocalhost
is, they’d each independently say "well I am of course" but referring to a different network context.network_mode: service:...
sounds like you’re trying to make the other container belocalhost
; in practice it’s extremely unusual to use this.You may need to change your application code to make settings like the database location configurable, depending on where they’re running, and environment variables are an easy way to set this in Docker. For this particular example I’ve used the
$PGHOST
variable the standard PostgreSQL client libraries use; in a Typescript/Node context you may need to change your code to refer toprocess.env.SOME_HOSTNAME
instead of'localhost'
.If you’re using Docker on WSL, I found that I can often not connect when the process is listening on ::1, but when explicitly binding the port to 127.0.0.1 makes the service accessible through Windows.
So something like
might work
Switch all non-dev containers to network_mode: service:akira
It seems this was the original configuration :
https://github.com/microsoft/vscode-dev-containers/pull/523
But it was reverted back because if you rebuild the dev container while others servies are running, the port forwarding will break :
https://github.com/microsoft/vscode-dev-containers/issues/537