티스토리 뷰

개발계발/Python

python supervisord 사용기

개발계발 주인장 2024. 3. 21. 09:38

API 서버를 prod 환경에서 띄울 때 어떻게 하는 것이 가장 좋을까?

 

기본적으로 애플리케이션을 실행 시키는 방법은 다음과 같다.

 ( 아래는 fastapi 앱을 실행시키는 명령어이다. )

gunicorn main:app --workers 4 -k uvicorn.workers.UvicornWorker --bind unix:/tmp/gunicorn.sock

이렇게 하면 애플리케이션을 띄우고 트래픽을 받을 수 있다. 이대로 마쳐도 되지만 앱이 crash등의 이유로 죽는 상황에 대해 한 번 더 생각해 볼 수도 있다.

우리 서비스는 ECS fargate로 띄워서 서버가 죽는다면 ECS 에서 자동으로 오토스케일링되어 새로 띄운다. 하지만 죽은 서버를 띄우는데 상대적으로 시간이 걸려 딜레이가 발생한다. 요 부분을 좀 더 빠르게 안정적으로 해결해 볼 수 있는 방법 중 하나가 supervisor이다.

http://supervisord.org/

supervisor

Supervisor는 사용자가 UNIX와 유사한 운영 체제에서 여러 프로세스를 제어할 수 있도록 하는 클라이언트/서버 시스템

왜 필요할까?

  • 가장 큰 이유는 프로그램 다운 시 자동으로 재시작이 가능하다.
    • 기본 실행은 프로그램 다운시 재실행할 방법이 없다.
    • supervisord는 프로세스를 하위 프로세스로 시작하여 충돌 시 자동으로 다시 시작하도록 구성할 수 있다.
    • 고가용성을 제공한다.
    • 서버를 새로 오토스케일하기보다 프로세스를 새로 띄우는게 훨씬 유리하다.
  • 프로세스의 상태를 확인할 수 있다.
  • 프로세스에 우선순위 할당이 가능하다.

특징

  • 단순하다. ini 파일을 통해 구성한다.
  • 중앙 집중식이다. 프로세스를 시작, 중지 및 모니터링할 수 있는 한 곳을 제공한다.
  • 효율적이다. 포크/실행을 통해 하위 프로세스를 시작하며, 하위 프로세스는 데몬화되지 않는다.
    • 주기적인 폴링을 사용해 실패한 프로세스를 다시 시작하는 방식과 달리 프로세스가 종료되면 즉시 supervisord에게 시그널을 보낸다.

구성 요소

  • supervisord
    • supervisor의 서버 영역에 해당한다.
    • 서버 프로세스는 ini파일을 사용해 구성한다.
    • 프로세스 이벤트 생성 및 처리 담당
  • supervisorctl
    • supervisor의 CLI에 해당한다.
    • CLI를 사용해 프로세스 상태를 확인하고, 중지 및 시작한다.
  • web server
    • 서버를 띄워 브라우저에서 프로세스 상태를 확인할 수도 있다.

설치

pip install supervisor

or

poetry add supervisor

실행

$BINDIR/supervisord -c [supervisord.conf path]
-c 옵션을 붙이지 않으면 supervisord.conf를 찾아다니기 때문에, 원치 않는 설정파일이 로드될 수 있으므로 경고 메시지를 보여준다.

supervisord.conf 작성

conf 파일에서 사용한 기능들을 설명하겠다.

[unix_http_server]
-> http 서버 통신을 위해 필요한 섹션
file: http 요청을 수신받을 unix 소켓 경로

[supervisord]
-> supervisord 설정 섹션
nodaemon: daemon으로 실행시킬지 여부. false로 실행 시 도커 죽음.

[rpcinterface:supervisor]
-> supervisor 확장 설정 섹션
supervisor.rpcinterface_factory: 표준 설정을 위해 설정 유지해야 함.

[supervisorctl]
-> shell 프로그램 관련 섹션

[program:fastapi]
-> 하위 프로세스로 실행시킬 program 설정 섹션. 여러개 설정할 수 있다.
command: program 실행 명령어
priority: 프로그램 우선순위로 숫자가 높을수록 마지막에 시작하고 먼저 종료된다.
autostart: supervisor가 실행될 때 자동으로 실행할지 여부
startsecs: program 상태가 success임을 확인하기 위해 계속 실행되어야 하는 시간.
startretries: process를 포기하기 전까지 시행하는 연속 시도 횟수.
autorestart: 자동재시작 여부

트러블슈팅

  • program이 실행되지 않는 이슈
    • program은 포그라운드로 실행시켜야 한다. 백그라운드로 실행 시 동작하지 않는다.
  • CRIT Server 'unix_http_server' running without any HTTP authentication checking 문구 해결
    • unix는 멀티유저시스템이라 접근관리를 위해 username과 password를 추가하라는 경고메시지를 보낸다.
    • unix_http_server 섹션에 username과 password를 추가하면 된다.
    • 참고: https://github.com/Supervisor/supervisor/issues/717
  • python app의 실행 로그가 남지 않는 이슈가 생겼다.
    • 구글링해본 PYTHONUNBUFFERED 환경 변수 세팅이나 sys.stdout.flush()으로 변경 실패
    • python logging 기본 stream은 stderr이다.
    • stderr을 stdout으로 redirect해주는 옵션추가해서 해결한다.

'개발계발 > Python' 카테고리의 다른 글

pydantic 살펴보기  (0) 2023.10.03
[Python] asyncio를 사용하여 코루틴 구현해 보기  (0) 2023.07.19
공지사항
최근에 올라온 글
최근에 달린 댓글
Total
Today
Yesterday
링크
«   2025/04   »
1 2 3 4 5
6 7 8 9 10 11 12
13 14 15 16 17 18 19
20 21 22 23 24 25 26
27 28 29 30
글 보관함