I have a Postgres database running in a Docker container and a Python application running in another Docker container. When I try to connect to the Postgres database from the Python app using SQLAlchemy, I get the following error:
sqlalchemy.exc.OperationalError: (psycopg2.OperationalError) could not connect to server: Connection refused Is the server running on host "localhost" (127.0.0.1) and accepting TCP/IP connections on port 5432?
I have checked that the Postgres container is running and I can connect to it from my host machine using DBeaver. However, when I try to connect from the Python app container, I get the above error.
this is the Postgres set up in docker compose
version: "3.7"
services:
postgresql_database:
container_name: postgresql_database
image: postgres:13.8
environment:
POSTGRES_HOST: localhost
POSTGRES_PASSWORD: MyPassword
POSTGRES_USER: MyUsername
POSTGRES_DB: "MyDatabase"
volumes:
- source: ../configs/postgresql
target: /docker-entrypoint-initdb.d/
type: bind
networks:
- default
- app_network
healthcheck:
test:
[
"CMD",
"pg_isready",
"-q",
"-U",
"MyUsername",
"-d",
"MyDatabase"
]
interval: 5s
timeout: 1s
retries: 2
restart: unless-stopped
the ../configs/postgresql directory has all database sql scripts
This is the python setup
version: "3.7"
services:
flask_app:
image: https://not_allowed_to_share/flask_app:latest
container_name: flask_app
volumes:
- source: ../configs/flask_app/config.yaml
target: /config/config.yaml
type: bind
environment:
CONTENT_CONNECTIONSTRING: DRIVER={PostgreSQL Unicode};SERVER=localhost;Port=5432;UID=MyUsername;PWD=MyPassword;Connect Timeout=5;DATABASE=MyDatabase;
CONTENT_DBTYPE: postgresql_odbc
networks:
- app_network
depends_on:
- "postgresql_database"
restart: "no"
The ../configs/flask_app/config.yaml contains configuration such as the connection string, is debug mode, etc
This is the connection string
DRIVER={PostgreSQL Unicode};SERVER=localhost;Port=5432;UID=MyUsername;PWD=MyPassword;Connect Timeout=5;DATABASE=MyDatabase;
I have also tried replacing ‘localhost’ with the name of the Postgres service but still get the same error.
How can I fix this issue and connect to the Postgres database from my Python app running in a Docker container?
2
Answers
The "localhost" of your python container, and the "localhost" of the postgres container are not the same.
Ways to fix this:
When you start two Docker compose deployments, both of them will have a different network, even if you name it
app_network
in each of them, like in your example.Start both deployments and then check your networks with
docker network list
. You should see two different networks.I’d suggest to put both services inside the same
docker-compose.yml
, as database and app belong together. This will start them together and they will be on the same network.In the
flask_app
service you can then set the name of the database service instead oflocalhost
.localhost
would be theflask_app
Docker container itself, but the database runs in a different container.So in
CONTENT_CONNECTIONSTRING
you should use host namepostgresql_database
instead oflocalhost
.If you really want to use two different Docker compose files, you need to mark networks as
external
. This way it will not create two different networks but use an existing one.Create the network with
docker network create app_network
.Then in both Docker compose files, set the network as you already did:
And at the end of the Docker compose files, define
app_network
as external network: