使用psycopg2连接Postgres容器时出现连接拒绝错误
问题:Python容器无法连接PostgreSQL容器,NestJS容器连接正常
部署环境
- postgres:10.4容器
- NestJS容器(服务名
alyanetworkapi) - 集成psycopg2的python:3.9.14-alpine3.16容器
所有容器通过docker-compose.yml编排,NestJS可正常连接PostgreSQL,但Python容器连接失败。
docker-compose.yml 配置
version: "3" services: alyanetworkapi: container_name: alyanetworkapi image: alyanetworkapi:1.0.0 build: context: ./docker/alyanetworkapi args: DATABASE_USERNAME: ${DATABASE_USERNAME} DATABASE_DATABASE: ${DATABASE_DATABASE} DATABASE_HOST: ${DATABASE_HOST} DATABASE_PASSWORD: ${DATABASE_PASSWORD} ports: - "6002:8000" networks: - alyattes-backend - internal extra_hosts: - "host.docker.internal:host-gateway" depends_on: - postgres restart: unless-stopped postgres: image: postgres:10.4 ports: - "5432:5432" environment: POSTGRES_USER: ${DATABASE_USERNAME} POSTGRES_PASSWORD: ${DATABASE_PASSWORD} POSTGRES_DB: ${DATABASE_DATABASE} user: postgres volumes: - ./database:/var/lib/postgresql/data networks: - alyattes-backend - internal networks: alyattes-backend: driver: bridge internal:
Python容器Dockerfile
FROM python:3.9.14-alpine3.16 WORKDIR /app RUN apk update RUN apk add git RUN apk add --update alpine-sdk RUN apk add libpq-dev RUN apk update \ && apk add --virtual build-deps gcc python3-dev musl-dev \ && apk add postgresql-dev gcc python3-dev musl-dev \ && apk del build-deps \ && apk --no-cache add musl-dev linux-headers g++ bash ARG DATABASE_USERNAME ARG DATABASE_DATABASE ARG DATABASE_HOST ARG DATABASE_PASSWORD ENV DATABASE_USERNAME=${DATABASE_USERNAME} ENV DATABASE_DATABASE=${DATABASE_DATABASE} ENV DATABASE_HOST=${DATABASE_HOST} ENV DATABASE_PASSWORD=${DATABASE_PASSWORD} RUN git clone https://${GITHUB_PAT}@github.com/owner/reponame.git RUN chmod 775 -R /app WORKDIR /app/alya-network-api RUN pip3 install . CMD [ "python3", "main.py"]
错误信息
psycopg2.OperationalError: connection to server at "postgres" (192.168.112.2), port 5432 failed: Connection refused Is the server running on that host and accepting TCP/IP connections?
排查与解决方法
1. 给Python容器添加docker-compose服务配置
当前docker-compose.yml未定义Python服务,需将其加入services列表,并配置与PostgreSQL相同的网络,否则容器间无法互通。示例配置:
python-app: build: context: ./path/to/python/dockerfile # 替换为Python Dockerfile所在目录 args: DATABASE_USERNAME: ${DATABASE_USERNAME} DATABASE_DATABASE: ${DATABASE_DATABASE} DATABASE_HOST: postgres # 直接用PostgreSQL服务名作为主机名 DATABASE_PASSWORD: ${DATABASE_PASSWORD} GITHUB_PAT: ${GITHUB_PAT} networks: - alyattes-backend - internal depends_on: - postgres restart: unless-stopped
2. 确保PostgreSQL服务完全就绪
depends_on仅保证容器启动顺序,不保证PostgreSQL服务可用。添加健康检查,确保数据库就绪后再启动Python容器:
修改PostgreSQL服务配置:
postgres: # ...其他原有配置 healthcheck: test: ["CMD-SHELL", "pg_isready -U ${DATABASE_USERNAME} -d ${DATABASE_DATABASE}"] interval: 5s timeout: 5s retries: 5
同时更新Python服务的depends_on:
python-app: # ...其他配置 depends_on: postgres: condition: service_healthy
3. 配置PostgreSQL监听所有网卡
PostgreSQL默认可能仅监听localhost,需修改配置允许容器网络连接,可通过启动命令设置:
postgres: # ...其他原有配置 command: postgres -c listen_addresses='*'
4. 验证环境变量正确性
进入Python容器检查DATABASE_HOST是否为postgres:
docker exec -it <python容器名> env | grep DATABASE_HOST
如果值不正确,可直接在Python服务的environment中强制设置:
python-app: # ...其他配置 environment: DATABASE_HOST: postgres
内容的提问来源于stack exchange,提问作者albert112
相关产品推荐
相关产品推荐

