본문 바로가기
Q&A2026년 6월 29일1분 읽기

Docker 컨테이너 안에서 localhost DB 접속이 안 됩니다 (ECONNREFUSED)

도
도커입문_민
조회 1060댓글 3

로컬에서 잘 되던 Node 앱을 도커로 띄웠더니 DB 접속이 안 됩니다.

Error: connect ECONNREFUSED 127.0.0.1:5432

DB 접속 설정은 host: 'localhost', port: 5432입니다. PostgreSQL은 제 노트북(호스트)에 설치돼서 돌고 있고요. 컨테이너 밖에서는 잘 붙는데 컨테이너 안에서만 안 돼요. 방화벽 문제인가요?

댓글 3

김김영삼4개월 전

방화벽이 아니라 "localhost"의 의미가 달라져서입니다. 컨테이너 안에서 localhost(127.0.0.1)는 호스트 노트북이 아니라 그 컨테이너 자기 자신을 가리켜요. 그래서 컨테이너 안에는 5432에서 듣는 게 없으니 거부당하는 겁니다.

해결 — 호스트를 가리키게

Docker Desktop(Mac/Windows)이면 특수 DNS 이름을 씁니다:

host: 'host.docker.internal'
port: 5432

리눅스에서는 이게 기본으로 안 되는 경우가 있어, 실행 시 추가하세요:

docker run --add-host=host.docker.internal:host-gateway ...
더 나은 방법 — DB도 컨테이너로

사실 개발환경이면 DB도 같이 컴포즈로 묶는 게 정석입니다. 그러면 서비스 이름으로 서로를 찾습니다.

# docker-compose.yml
services:
app:
build: .
environment:
DB_HOST: db # ← 서비스 이름
db:
image: postgres:18
environment:
POSTGRES_PASSWORD: secret

같은 컴포즈 네트워크 안에서는 db라는 이름이 자동으로 그 컨테이너 IP로 해석됩니다. localhost 쓸 일이 없어져요.

도도커입문_민(guest)4개월 전
컴포즈로 묶었는데 이번엔 app이 db에 붙으려다 getaddrinfo ENOTFOUND db가 납니다. 이름은 맞게 넣었는데요?
김김영삼4개월 전

거의 다 오셨어요. 두 가지 중 하나입니다.

  1. 기동 순서 문제 — app이 db보다 먼저 떠서, db가 아직 준비 안 됐을 때 붙으려다 실패하는 경우가 흔합니다. depends_on만으로는 "컨테이너 시작"만 보장하지 "DB 준비 완료"는 보장 안 해요. healthcheck를 걸어야 합니다.
    services:
    db:
    image: postgres:18
    healthcheck:
    test: ["CMD-SHELL", "pg_isready -U postgres"]
    interval: 3s
    retries: 10
    app:
    depends_on:
    db:
    condition: service_healthy
  2. 같은 네트워크가 아닌 경우 — 두 서비스를 서로 다른 컴포즈 파일/프로젝트로 띄우면 네트워크가 분리돼 이름 해석이 안 됩니다. 한 파일 안에 두거나 외부 네트워크를 공유시키세요.

대부분은 1번(기동 순서)입니다. healthcheck + condition: service_healthy 걸면 app이 db 준비될 때까지 기다렸다 뜹니다.

Ctrl+Enter로 등록