Java, Spring

[트러블 슈팅] docker-compose로 브릿지 네트워크 구성

green_dev 2024. 8. 26. 17:11

 

동일한 테스트 환경을 구성하기 위해서 도커로 서버를 띄우려고 했다.

근데... Redis, Rabbitmq, Mysql 모두 도커로 사용하다 보니 이들을 docker-compose.yml을 이용해서 브릿지 네트워크를 구성해줘야 했다.

 

version: '3.8'

services:
  app:
    build: .
    container_name: blackfriday
    ports:
      - "8080:8080"
    depends_on:
      - mysql
      - redis-cache
      - redis-session
      - rabbitmq
    environment:
      SPRING_DATASOURCE_URL: jdbc:mysql://localhost:3306/blackfriday?characterEncoding=UTF-8&serverTimezone=UTC
    networks:
      - app-network

  mysql:
    image: mysql:8.0.36
    container_name: mysql
    environment:
      MYSQL_ROOT_PASSWORD: 1234
      MYSQL_DATABASE: blackfriday
    ports:
      - "3306:3306"
    networks:
      - app-network

  redis-session:
    image: redis:latest
    container_name: redis-session
    ports:
      - "6379:6379"
    networks:
      - app-network

  redis-cache:
    image: redis:latest
    container_name: redis-cache
    ports:
      - "6380:6379"
    networks:
      - app-network

  rabbitmq:
    image: rabbitmq:management
    container_name: rabbitmq
    ports:
      - "5672:5672"
      - "15672:15672"
    networks:
      - app-network

networks:
  app-network:
    name: app-network
    driver: bridge

 

그래서 위와 같이 app-network로 브릿지 네트워크를 구성해 주었고, docker를 실행해 보았더니?

 

Mysql 오류

DB connection 에러

Mysql에 접속을 하지 못하여 커넥션 에러가 났다. 곧, DB URL이 잘못됐다는 것을 깨달았다.

SPRING_DATASOURCE_URL: jdbc:mysql://localhost:3306/blackfriday?characterEncoding=UTF-8&serverTimezone=UTC

 

위에서 환경변수localhost로 구성해주었는데, docker network inspect로 확인해 보면 스프링 컨테이너와 Mysql 컨테이너의 IP주소가 다르다. localhost로 접속하면 안되고 컨테이너 이름으로 지정해주면 접속할 수 있다.

 

SPRING_DATASOURCE_URL: jdbc:mysql://mysql:3306/blackfriday?characterEncoding=UTF-8&serverTimezone=UTC

 

위와 같이 수정하고 다시 도커 컨테이너를 실행했지만 실패했다 ㅋㅋㅋ

왜냐하면 Redis랑 RabbitMQ 둘다 application.yml 파일에서 host가 localhost 였기 때문!
그래서 docker-compose.yml에 environment로 둘 다 container 이름으로 호스트 변경

(docker-compose.yml에서 지정한 환경변수가 application.yml을 덮어 씀)

 

Redis 오류

 

모두 수정 후 실행하니 도커 컨테이너가 정상적으로 작동했다!

하지만 Redis 접근이 안되는 것이 아닌가? (이걸로 진짜 하루 삽질함)

 

  redis-session:
    image: redis:latest
    container_name: redis-session
    ports:
      - "6379:6379"
    networks:
      - app-network

  redis-cache:
    image: redis:latest
    container_name: redis-cache
    ports:
      - "6380:6379"
    networks:
      - app-network

 

레디스 설정 코드를 보면 session 서버는 6379포트를, cache 서버는 6380포트로 구성해주었는데, 도대체 세션 서버만 접근이 가능하고, 캐시 서버를 호출할 때마다 Connection refused를 하는 것이 아닌가?

 

스프링 컨테이너에 접속해서 redis 캐시 서버를 호출해본 결과

 

docker ps를 통해 실행중인지도 확인해봤는데 실행도 잘되고 있고, 포트도 잘 바인딩 되어 있는 것을 볼 수 있다.

docker ps

 

redis inspect

실제 redis 캐시 서버 inspect에서도 호스트 포트가 6380으로 잘 매핑되어 있는 것을 확인할 수 있다.

해결

브릿지 네트워크로 구성 시 내부 컨테이너를 호출할 때는 호스트 Port를 사용하지 않기 때문에 6380포트로 redis cache 서버를 호출했을 때 응답을 받을 수 없던 것이다...

 

그래서 명시적으로 포트를 바인딩 하기 위해서 아래와 같이 command 옵션을 추가해주었다. (굳이 6380포트로 바꿔 줄 필요 없이 6379포트를 사용해도 된다.)

  redis-session:
    image: redis:latest
    container_name: redis-session
    command: [ "redis-server", "--bind", "redis-session", "--port", "6379" ]
    networks:
      - app-network

  redis-cache:
    image: redis:latest
    container_name: redis-cache
    command: [ "redis-server", "--bind", "redis-cache", "--port", "6380" ]
    networks:
      - app-network

 

그 후 도커 컨테이너를 모두 재실행해주고나서 잘 접속되는 것을 확인했다!

드디어 테스트 환경 구축 완료 ㅠㅠ....