파이썬 스크립트 도커라이징(Dockerizing)의 필요성
로컬 PC에서 파이썬(Python)으로 웹 크롤러나 텔레그램 알림 봇을 완성하고 나면, 이를 24시간 내내 구동하기 위한 배포(Deployment) 단계를 고민하게 됩니다. 윈도우 환경의 작업 스케줄러를 활용하거나 항상 PC를 켜두는 방식은 전력 소모와 시스템 불안정성 측면에서 매우 비효율적입니다.
가장 이상적인 대안은 작성한 파이썬 스크립트를 도커(Docker) 컨테이너로 감싸서(Image Build), 시놀로지 NAS나 AWS, 클라우드 가상 서버(VPS)에 올려 무중단으로 구동하는 것입니다. 도커를 활용하면 개발을 진행했던 로컬 PC의 운영체제나 파이썬 버전, 설치된 패키지 환경을 100% 동일하게 복제하여 서버에 이식할 수 있습니다.
이를 흔히 ‘도커라이징(Dockerizing)’이라고 부릅니다. 하지만 코드 자체에는 문제가 없음에도 불구하고, 이를 도커 이미지로 빌드하고 컨테이너로 실행하는 과정에서 컨테이너 특유의 격리된 환경으로 인해 다양한 예외 상황이 발생합니다. 본 글에서는 파이썬 코드를 도커 환경에 배포하며 겪었던 주요 오류들과 그 해결 과정을 상세히 기록합니다.
Dockerfile 작성 및 배포 중 겪는 치명적 오류
파이썬 스크립트를 도커 이미지로 만들기 위해서는 설계도 역할을 하는 ‘Dockerfile’을 작성해야 합니다. 이 텍스트 파일 하나에 어떤 베이스 운영체제를 쓸 것인지, 어떤 패키지를 설치할 것인지 명시하게 되는데, 이 과정에서 초보자들이 흔히 겪는 세 가지 장애물이 있습니다.
1. 패키지 의존성 누락 및 ModuleNotFoundError
로컬 환경에서는 정상 작동하던 스크립트가 도커 컨테이너로 실행되자마자 ‘ModuleNotFoundError: No module named requests’와 같은 에러를 내뿜으며 즉시 종료되는 현상입니다. 도커 컨테이너는 완전히 백지상태의 격리된 리눅스 환경이므로, 로컬 PC에 설치해 두었던 파이썬 라이브러리들은 컨테이너 내부에 존재하지 않습니다.
이 문제를 해결하기 위해서는 로컬 PC의 프로젝트 폴더에서 터미널을 열고 ‘pip freeze > requirements.txt’ 명령어를 실행하여 현재 스크립트 구동에 필요한 라이브러리 목록과 버전을 텍스트 파일로 추출해야 합니다. 이후 Dockerfile 내부에 ‘COPY requirements.txt ./’ 그리고 ‘RUN pip install -r requirements.txt’ 구문을 추가하여, 컨테이너가 빌드될 때 빈 공간에 필요한 모듈들을 스스로 다운로드하여 설치하도록 자동화 로직을 구성해야 합니다.
2. 표준 출력(Stdout) 버퍼링으로 인한 실시간 로그 실종 현상
두 번째로 당황스러운 오류는 스크립트가 죽지 않고 백그라운드에서 정상적으로 실행되고 있음에도 불구하고, 도커 컨테이너의 터미널(Log) 창에 print() 함수로 작성해 둔 결과물이 전혀 나타나지 않는 현상입니다. 이는 파이썬이 리눅스 백그라운드 환경에서 동작할 때 성능 최적화를 위해 표준 출력(Stdout) 데이터를 즉시 화면에 뿌리지 않고, 내부 메모리(버퍼)에 일정량 모아두었다가 한 번에 출력하려는 특성 때문입니다.
에러가 발생했을 때 즉각적인 원인 파악이 불가능해지므로 모니터링에 치명적입니다. 이를 해결하는 가장 깔끔한 방법은 Dockerfile 최상단에 ‘ENV PYTHONUNBUFFERED=1’ 이라는 환경 변수를 강제로 주입하는 것입니다. 이 한 줄의 코드를 추가하면 파이썬의 출력 버퍼링 기능이 비활성화되어, print() 함수가 호출되는 즉시 도커 로그 창에 텍스트가 실시간으로 스트리밍됩니다.
3. 컨테이너 내부 타임존(Timezone) 동기화 실패
세 번째 문제는 스케줄러(예: schedule 패키지)를 활용하여 ‘매일 아침 9시에 실행’되도록 파이썬 코드를 작성했을 때 발생합니다. 도커 컨테이너에 코드를 올리면 아침 9시가 아닌 오후 6시에 뜬금없이 스크립트가 동작합니다. 이는 모든 도커 컨테이너의 기본 시스템 시간이 협정 세계시(UTC)로 고정되어 있어, 한국 시간(KST)과 정확히 9시간의 시차가 발생하기 때문입니다.
컨테이너 내부의 시간을 물리적인 호스트 서버와 동기화하기 위해서는 Dockerfile 내부에 시스템 시간대 변경 명령어를 넣어야 합니다. Ubuntu나 Debian 기반의 파이썬 이미지를 사용 중이라면 ‘ENV TZ=Asia/Seoul’ 환경 변수를 추가하고, ‘RUN ln -snf /usr/share/zoneinfo/$TZ /etc/localtime && echo $TZ > /etc/timezone’ 구문을 삽입하여 컨테이너가 생성되는 시점에 리눅스의 시스템 시계를 강제로 한국 표준시로 맞춰주는 필수 작업이 선행되어야 합니다.
안정적인 무중단 배포 및 인프라의 완성
위의 세 가지 치명적인 예외 상황을 모두 방어하는 Dockerfile을 작성했다면, 이제 ‘docker build -t my_python_bot .’ 명령어를 통해 이미지를 생성할 수 있습니다. 이렇게 생성된 이미지는 시놀로지 NAS의 Container Manager 등을 통해 언제든 동일한 환경으로 재현할 수 있습니다.
특히 컨테이너 실행 설정에서 ‘자동 재시작(Restart Always)’ 옵션을 부여하면, 파이썬 코드 내부의 일시적인 통신 장애나 시스템 메모리 부족 등으로 프로세스가 강제 종료(Crash)되더라도 도커 데몬이 이를 즉각 감지하여 스크립트를 처음부터 다시 구동시킵니다.
결론적으로 도커를 활용한 파이썬 스크립트 배포는 초기 Dockerfile 문법 학습과 리눅스 환경 변수에 대한 이해를 요구하지만, 한 번 구축해 두면 OS 환경의 제약 없이 어디서든 24시간 돌아가는 완벽한 무인 자동화 서버를 소유하게 됨을 의미합니다. 이는 단순한 코더를 넘어 전체 인프라 아키텍처를 이해하는 개발자로 도약하는 가장 중요한 마일스톤이 될 것입니다.
