배포할 때 개인적으로 가장 무서운 에러 502.. 스푼피드 개발의 배포를 맡았는데 어김없이 502를 만나고야 말았다 😣 잊어버리기 전에 어떻게 해결했는지 과정을 되새겨보기로 했다. 그래야 다음 502 때는 덜 무서울 것 같다

🐳 도커 컨테이너 확인

ssh 접속 후 워킹 디렉토리로 진입한다. sudo docker ps -a 명령어를 입력하면 현재 빌드된 컨테이너들을 확인할 수 있는데, 필자의 경우 502 에러가 처음 났을 때 nginx는 정상 up, app은 exit 상태였다.

♻️ 에러 로그 확인 후 app 컨테이너 재시작

nginx는 잘 띄워졌는데 app과 연결이 안된 것 같아 sudo docker logs app으로 에러 로그를 확인했다.

이렇게 뜨길래 npm install 이 제대로 안되었다는 걸 알게 되었고, 수동으로 npm install 을 해준 뒤 sudo docker restart app 으로 재시작해주었다. Dockerfile 에서 npm install 과정을 넣어주었기 때문에 자동으로 되었을 줄 알았는데 왜 누락이 된 것인지, 어느 부분을 놓치고 있는지 아직 발견하지 못했다. 그래서 아직 깃헙액션 후 ssh 에 접속해 npm install -> restart 과정을 수동으로 반복 중인데 빠른 시일 내에 해결하고 기록하고 싶다.

이렇게 app 도 up 상태로 만들어주었는데,, 502가 없어지지 않았다. 그래서 이제 진짜 nginx 설정을 만져봐야겠다 싶었고 우선 파일을 확인하기로 했다.

⚙️ 적용되고 있는 nginx 설정 파일 확인

sudo docker exec -it (nginx컨테이너id) ls /etc/nginx/conf.d 를 해보면 conf.d 폴더 안에 있는 conf 파일이 확인 가능하다. 설정 파일을 커스텀하지 않았다면 기본 nginx 설정 파일은 다음과 비슷한 형태일 것이고 sudo docker exec -it (nginx컨테이너id) vi /etc/nginx/conf.d/default.conf 로 확인할 수 있을 것이다.

user       www www;  ## Default: nobody
worker_processes  5;  ## Default: 1
error_log  logs/error.log;
pid        logs/nginx.pid;
worker_rlimit_nofile 8192;

events {
  worker_connections  4096;  ## Default: 1024
}

http {
  include    conf/mime.types;
  include    /etc/nginx/proxy.conf;
  ... 중략

  server { # simple load balancing
    listen          80;
    server_name     big.server.com;
    access_log      logs/big.server.access.log main;

    location / {
      proxy_pass      http://big_server_com;
    }
  }
}

필자는 커스텀 설정 파일을 만들어둔 상태였는데, 바보같이 위와 같은 default conf 파일을 삭제하지 않았었다.
결론적으로 nginx 기본 설정이 적용되어 app과 연결이 안된 것이었다.

🛠 커스텀 nginx.conf 파일을 적용하기 위한 Dockerfile 연결

아래처럼 nginx용 Dockerfile 도 만들어주었다 (default 설정을 지우고 커스텀 설정으로 덮는 코드). 이렇게 해야 커스텀 nginx.conf에서 app:3000 을 했던 내용이 먹힐 것이다.

FROM nginx:1.20.2-alpine

RUN rm /etc/nginx/conf.d/default.conf
COPY nginx.conf /etc/nginx/conf.d

잊지 않고 루트의 docker-compose.yml에도 다음 내용을 추가해준다.

nginx:
    build: ./proxy  # proxy는 필자의 nginx Dockerfile이 있는 디렉토리 이름

이후 다시 마스터에 푸시해서 배포하고(깃헙액션), ssh 접속 후 sudo docker exec -it (nginx컨테이너id) vi /etc/nginx/conf.d/nginx.conf 를 해보면 자신이 작성한 커스텀 설정 파일 내용이 보인다!!

🔑 IP 확인

여기까지 확인했는데 사라지지 않는 502..?!
그렇다면 가장 기본적인 부분을 놓치고 있진 않았는지 확인해보자,,

netstat -nlptsudo docker ps -a 을 해서 포트 확인을 했는데 포트 연결 방향이 다 맞는 것 같다면 (아래 예시는 Ip 문제 해결 후 사진이지만 해결 전에는 127.0.0.1:80->80/tcp 이런 형식이었음)

ip 설정을 까먹은건 아닌지 체크해볼 필요가 있다.
처음에 로컬로 개발하면서 localhost ip인 127.0.0.1로 설정되어있었을 것인데, 이를 0.0.0.0으로 바꿔주어야 한다.
둘의 차이는 여기 나와있다.

아래의 코드처럼 app.listen 부분에서 ip를 특정적으로 추가해주었더니 성공 💫

import app from './app';
import dotenv from 'dotenv';
import { connectDB } from './config/index';

dotenv.config();

const runServer = async () => {
    await connectDB();
    /* Run server */
    console.log('Set application...');
    // app.listen(process.env.PORT, () => console.log(`server Run with port: ${process.env.PORT}`));
    app.listen(3000, '0.0.0.0', () => console.log(`server Run with port: ${process.env.PORT}`));
};

runServer();

➕ 언더스코어(_) 관련 문제 해결 방법

추가적으로 배포 성공 후 언더스코어 관련 이슈가 있어 적어보자면,
프론트에서 요청을 보낼 때 header 값에 'access_token' 처럼 언더스코어가 포함되어있을 경우 nginx에서 디폴트로 언더바를 지우게끔 되어있어서 발생하는 문제가 있었다.
이는 nginx.conf 에 underscores_in_headers on; 코드를 추가해줌으로써 해결했다.

그리고 도커 컨테이너에 변경을 가했다면 항상 restart 로 최신상태를 유지하자 @~@

profile
Move Forward

0개의 댓글

관련 채용 정보

Powered by GraphCDN, the GraphQL CDN