생활/개발일지

AWS에서 Python + Celery + Flower + venv 환경 설정하기

사당맥주 2024. 4. 11. 13:33
반응형

시스템 정의

AWS ec2 Instance

  • 1core
  • RAM 2GB
  • SSD 30GB
  • t2.small

OS 버전

Ubuntu 20.04 버전 기준입니다.

Application 버전

Python 3.8


시스템 설정

AWS ec2 인스턴스를 처음 생성하게 되면 기본적인 프로그램(vi, apt 등..)을 제외 하고, 인스턴스의 경량화를 위해 아무것도 설치 되어있지 않습니다.

아래 가이드는 Django Application을 인스턴스에 올리는 커멘드를 순서대로 작성하였으며, 다른 설정 필요없이 커멘드만 따라서 입력해주시면 서버 구성이 완료됩니다.

시스템 확인

아래와 버전이 같은지 확인해줍니다.

-- 우분투 버전 확인
$ lsb_release -a

-- 결과 
No LSB modules are available.
Distributor ID: Ubuntu
Description:    Ubuntu 20.04.6 LTS
Release:        20.04
Codename:       focal
ubuntu@ip-172-31-4-97:/

Linux 계정 생성

인스턴스 처음 생성시 계정 비밀번호를 지정해주세요. (비밀번호가 없으면, 일부 프로그램 설치시 비밀번호를 물어볼때 입력할 값이 없어 진행 할 수 없습니다.)

$ sudo passwd root -- root 계정 비밀번호 설정
$ sudo passwd ubuntu -- 사용자 계정 비밀번호 설정

파이썬 설치

매장 관리 시스템은 파이썬으로 만들어진 Django 프레임워크 프로젝트입니다. 파이썬을 사용하기 위해 시스템의 글로벌 영역에 파이썬을 설치 해줍니다.

APT 업데이트

Ubuntu는 apt(패키지 설치 매니저) 를 사용합니다. 최신 버전을 이용할 수 있도록 업데이트 해줍니다.

$ sudo apt update && sudo apt upgrade

오래된 파이썬 프로젝트 설치 밑작업

최신버전의 파이썬을 설치하면 좋겠지만, 관리하고 있는 매장관리시스템 은 파이썬 3.8으로 개발되어있으므로, SideEffect를 막기위해 버전을 맞춰줘야 합니다. 오래된 버전의 파이썬을 설치하려면 설치하기 전 몇가지 설정이 필요합니다.

$ sudo apt install software-properties-common
$ sudo add-apt-repository ppa:deadsnakes/ppa

파이썬 버전 선택

3.8 버전이 설치 될 수 있도록 정책 설정을 해줍니다.

$ sudo apt-cache policy python3.8

파이썬 설치

파이썬 3.8 을 설치합니다.

$ sudo apt install python3.8

OS의 기본으로 사용할 파이썬(버전)을 선택
파이썬 버전이 여러 개 일 경우 OS 입장에서 어떤 버전을 사용할지 우선 순위를 정해줍니다. (우리의 경우 하나만 설치 하기 때문에 큰 의미는 없습니다.)

$ ls /usr/bin/python*
$ sudo update-alternatives --install /usr/bin/python python /usr/bin/python3.8 3
-- Switch the default Python version
$ sudo update-alternatives --config python

버전 확인

마지막으로 아래 명령어로 파이썬 3.8 이 잘 설치 되었는지 확인해줍니다.

$ python -V

PIP 설치

사용자 디렉터리로 이동하여 PIP 설치 프로그램을 다운로드 받고, 설치하는 과정입니다.

$ cd ~
$ sudo curl https://bootstrap.pypa.io/get-pip.py -o get-pip.py
$ sudo python3 get-pip.py
--- PIP 설치 확인
$ pip3
-- PIP 업그레이드
$ sudo pip install --upgrade pip
-- python3-pip 설치
$ sudo apt install python3-pip

vevn 가상 환경 설치

가상 환경을 설치해줍니다. 파이썬 프로젝트는 버전에 예민하므로 인스턴스에 배포된 프로그램은 각 버전에 맞는 패키지들만 사용할 수 있도록 가상 환경을 설치해주어야 합니다.

$ sudo apt install python3-venv
--python3.8-venv 패키지 설치
$ sudo apt-get install python3.8-venv
--python3.8 가상환경 설정
$ sudo mkdir ~/venvs/
$ cd ~/venvs
$ python3.8 -m venv mysite
-- 가상환경 실행
$ source ~/venvs/mysite/bin/activate

## 주의 ## 
venvs 디렉터리(하위 모두 포함) 소유자는 사용자 것이어야 합니다! 사용자가 아닌 경우 파이썬 패키지 설치 시 가상 환경에 설치되지 않고 OS 자체에 설치됩니다..

--사용자 확인
whoami

--소유자 변경
sudo chown -R [사용자]:[사용자]~/venvs

가상 환경이 성공적으로 설정되었다면 아래와 같이 표시됩니다. (가상 환경 이름이 mysite 입니다.)

(mysite) ubuntu@ip-172-31-5-174:~$

!! 필수 !!
지금부터는 가상 환경(mysite)이 활성화 된 상태에서 작업해주셔야 합니다.


Celery 설치

Celery는 Django 프레임 워크 에서 사용하는 메시지 큐 입니다. 주로 배치 작업에 사용됩니다. Celery 와 함께 사용될 “redis“, “celery-beat“, “celery“ 를 설치합니다.

$ pip install "celery[redis]" redis
$ pip install django-celery-beat
$ pip install django-celery-results

init.d 구성

init.d 는 initial deamon 의 약어로, OS 실행 시 자동으로 실행되는 프로그램을 칭합니다.

init.d 는 /etc/init.d 아래에 정의되어 있고, 우리는 Celery 를 실행 시 자동으로 실행되는 프로그램으로 설정하고자 합니다.

Celery 데몬 생성

Celery 프로그램 코드: https://github.com/celery/celery/blob/main/extra/generic-init.d/celeryd

위 링크로 들어가서 보여지는 코드를 아래 파일에 입력 후 저장 합니다.

$ sudo vim /etc/init.d/celeryd

vim 간단 사용법
편집 모드 : ESC + i
저장: [편집 모드에서] :wq 입력

Celery 설정 파일 생성

아래 파일을 편집 모드로 열어줍니다.

$ sudo vim /etc/default/celeryd

위 파일에 아래 코드를 그대로 복붙 해 줍니다.

# Names of nodes to start
#   most people will only start one node:
CELERYD_NODES="worker1"
#   but you can also start multiple and configure settings
#   for each in CELERYD_OPTS
#CELERYD_NODES="worker1 worker2 worker3"
#   alternatively, you can specify the number of nodes to start:
#CELERYD_NODES=10
# Absolute or relative path to the 'celery' command:
CELERY_BIN="/home/ubuntu/venvs/mysite/bin/celery"
# App instance to use
# comment out this line if you don't use an app
CELERY_APP="config"
# or fully qualified:
#CELERY_APP="app.tasks:app"
# Where to chdir at start.
CELERYD_CHDIR="/home/ubuntu/projects/mysite"
# Extra command-line arguments to the worker
CELERYD_OPTS="--time-limit=7200 --concurrency=4"
# Configure node-specific settings by appending node name to arguments:
#CELERYD_OPTS="--time-limit=300 -c 8 -c:worker2 4 -c:worker3 2 -Ofair:worker1"
# Set logging level to DEBUG
#CELERYD_LOG_LEVEL="INFO"
# %n will be replaced with the first part of the nodename.
CELERYD_LOG_FILE="/var/log/celery/%n%I.log"
CELERYD_PID_FILE="/var/run/celery/%n.pid"
# Workers should run as an unprivileged user.
#   You need to create this user manually (or you can choose
#   a user/group combination that already exists (e.g., nobody).
CELERYD_USER="ubuntu"
CELERYD_GROUP="ubuntu"
# If enabled pid and log directories will be created if missing,
# and owned by the userid/group configured.
CELERY_CREATE_DIRS=1

주요설정

복붙 을 했으면 몇 가지 설정이 필요 할 수 있으므로 아래 설명을 참고 해주세요.

  • CELERYD_CHDIR = Django 프로젝트 Path
  • CELERYD_USER = AWS 사용자 eg> ubunutu
  • CELERYD_GROUP = AWS 그룹 eg> ubunutu
  • CELERY_APP = Django 프로젝트 이름
  • CELERY_BIN = 가상환경에 설치된 셀러리가 디렉터리

권한설정

설정이 완료 되었으면, OS 시작 시 시스템이 root 권한으로 실행 시킬 수 있도록 root 권한으로 변경 합니다.

$ sudo chmod 755 /etc/init.d/celeryd
$ sudo chown root:root /etc/init.d/celeryd
실행 방법 (참고> 따라하지 않아도 됩니다)
시작 : /etc/init.d/celeryd start
중지 : /etc/init.d/celeryd stop
재시작 : /etc/init.d/celeryd restart
상태확인 : /etc/init.d/celeryd status

CeleryBeat 설치

CeleryBeat 데몬 생성
CeleryBeat 프로그램 코드: https://github.com/celery/celery/blob/main/extra/generic-init.d/celerybeat

위 링크로 들어가서 보여지는 코드를 아래 파일에 입력 후 저장 합니다.

$ sudo vim /etc/init.d/celerybeat


권한설정

설정이 완료 되었으면, OS 시작 시 시스템이 root 권한으로 실행 시킬 수 있도록 root 권한으로 변경 합니다.

$ sudo chmod 755 /etc/init.d/celerybeat
$ sudo chown root:root /etc/init.d/celerybeat

 

실행 방법(Celery 와 같습니다. 따라 하실 필요는 없습니다.)
시작 : /etc/init.d/celerybeat start
중지 : /etc/init.d/celerybeat stop
재시작 : /etc/init.d/celerybeat restart
상태확인 : /etc/init.d/celerybeat status

Flower 구성

Flower는 Celery의 모니터링 웹 Tool 입니다. Celery 는 메시지 큐로 Django 에서 설정한 Batch Job 을 스케줄에 맞춰 순차적으로 실행 시켜주는 프로그램으로 실시간 처리 현황이 중요한데, Flower 가 이를 제공해줍니다.

Flower 설치
pip 를 통해 Flower 를 설치합니다.

$ pip install flower


Systemctl 등록
Systemctl은 시스템에서 서비스 관리 유틸리티 입니다. “시작”, “재시작”, “종료” 등 systemctl로 간편하게 서비스를 관리 할 수 있습니다

systemctl 에 Flower 서비스를 등록

$ sudo vim /etc/systemd/system/flower.service


위 파일에 아래 코드를 복붙 하고 저장합니다.

[Unit]
Description=Flower Celery Service
[Service]
User=ubuntu
Group=ubuntu
WorkingDirectory=/home/ubuntu/projects/mysite
ExecStart=/home/ubuntu/venvs/mysite/bin/celery -A config flower
Restart=on-failure
Type=simple
[Install]
WantedBy=multi-user.target

Gunicorn 설치

Django 프레임워크로 개발된 Python프로젝트에서 작동하는 요청, 응답 방식은 웹 서버에서 그대로 이해 할 수 없습니다. 그래서 서로 이해 할 수 있도록 중간에 도와주어야 하는데 Gunicorn이 이 역할을 수행 해줍니다.

별도의 설정은 필요 없으므로 설치만 진행합니다. (Django 와 Nginx 에서 설정합니다.)

$ pip install gunicorn

Nginx 설치

nginx 는 유명한 웹 서버 중 하나 입니다. 웹 서버는 외부로부터 HTTP 요청을 받아 설정된 위치로 요청을 해주는 서버입니다.

설치

$ sudo apt-get install nginx


버전확인

$ nginx -v


시작

$ sudo systemctl start nginx


상태확인

$ sudo systemctl start nginx


Nginx 설정 파일

기본 라우팅 설정

$ sudo vim /etc/nginx/conf.d/default.conf


위 파일에 아래 코드를 복붙 합니다.

server {
    listen 80;
    server_name localhost;
    #access_log /var/log/nginx/host.access.log main;
    
    location / {
        root /usr/share/nginx/html;
        index index.html index.htm;
    }
    
    #error_page 404 /404.html;
    # redirect server error pages to the static page /50x.html
    #

	error_page 500 502 503 504 /50x.html;
    location = /50x.html {
        root /usr/share/nginx/html;
    }
    
    # proxy the PHP scripts to Apache listening on 127.0.0.1:80
    #
    #location ~ .php$ {
    # proxy_pass http://127.0.0.1;
    #}
    # pass the PHP scripts to FastCGI server listening on 127.0.0.1:9000
    #
    #location ~ .php$ {
    # root html;
    # fastcgi_pass 127.0.0.1:9000;
    # fastcgi_index index.php;
    # fastcgi_param SCRIPT_FILENAME /scripts$fastcgi_script_name;
    # include fastcgi_params;
    #}
    # deny access to .htaccess files, if Apache's document root
    # concurs with nginx's one
    #
    #location ~ /.ht {
    # deny all;
    #}
}

Nginx 설정

$ sudo vim /etc/nginx/nginx.conf


위 파일에 아래 코드를 복붙 합니다.

user www-data;
worker_processes auto;
pid /run/nginx.pid;
include /etc/nginx/modules-enabled/.conf;

events {
    worker_connections 768;
    # multi_accept on;
}

http {
    ##
    # Basic Settings
    ##
    sendfile on;
    tcp_nopush on;
    tcp_nodelay on;
    keepalive_timeout 120;
    types_hash_max_size 2048;
    # server_tokens off;
    server_names_hash_bucket_size 128;
    # server_name_in_redirect off;
    include /etc/nginx/mime.types;
    default_type application/octet-stream;
    
    ##
    # SSL Settings
    ##
    ssl_protocols TLSv1 TLSv1.1 TLSv1.2 TLSv1.3; # Dropping SSLv3, ref: POODLE
    ssl_prefer_server_ciphers on;
    
    ##
    # Logging Settings
    ##
    access_log /var/log/nginx/access.log;
    error_log /var/log/nginx/error.log;
    
    ##
    # Gzip Settings
    ##
    gzip on;
    # gzip_vary on;
    # gzip_proxied any;
    # gzip_comp_level 6;
    # gzip_buffers 16 8k;
    # gzip_http_version 1.1;
    # gzip_types text/plain text/css application/json application/javascript text/xml application/xml application/xml+rss text/javascript;
    
    ##
    # Virtual Host Configs
    ##
    include /etc/nginx/conf.d/.conf;
    include /etc/nginx/sites-enabled/*;
}
# mail {
#     # See sample authentication script at:
#     # http://wiki.nginx.org/ImapAuthenticateWithApachePhpScript
# 
#     # auth_http localhost/auth.php;
#     # pop3_capabilities "TOP" "USER";
#     # imap_capabilities "IMAP4rev1" "UIDPLUS";
# 
# server {
#     listen localhost:110;
#     protocol pop3;
#     proxy on;
# }
# 
# server {
#     listen localhost:143;
#     protocol imap;
#     proxy on;
# }
#}

변경사항

  • server_names_hash_bucket_size 128

위 설정은 아마존에서 제공하는 “공개 DNS“ 길이가 길어서 기본 값에서 128로 변경 했습니다.

사용자 라우팅 후보 설정

sites-available 안의 파일은 사용자가 설정한 라우팅 설정 후보들입니다.(실제 설정에 반영되지 않습니다)

$ sudo vim /etc/nginx/sites-available/mysite

위 파일에 아래 코드를 복붙 합니다.

server {
    server_name ec2-sample.ap-northeast-2.compute.amazonaws.com;
    server_tokens off;
    location = /favicon.ico { access_log off; log_not_found off; }
    proxy_set_header X-Forwarded-Proto $scheme;
    
    location /static {
   	 	alias /home/ubuntu/project/mysite/static;
    }
    
    location /media {
    	alias /home/ubuntu/project/mysite/media;
    }
    
# gunicorn app
    location / {
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header X-Url-Scheme $scheme;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header Host $http_host;
        proxy_redirect off;
        proxy_pass http://unix:/tmp/gunicorn.sock;
    }
    
    location /test {
    	return 200 "TEST PAGE";
    }
}

Server DNS 설정

위 설정을 복붙 했으면, server_name 값을 AWS ec2 인스턴스의 공개DNS 로 변경해야 합니다.

사용자 라우팅 설정 후보 등록

sites-enabled 디렉터리에는 sites-available 의 후보들 중 설정할 설정을 심볼릭 링크로 걸어주면 Nginx 재실행시 설정에 반영됩니다.

사용자 라우팅(mysite) 등록

$ sudo ln -s /etc/nginx/sites-available/mysite /etc/nginx/sites-enabled/mysite


기본 라우팅 삭제

우리가 등록한 설정만 쓸 예정이므로, 기본으로 제공된 설정은 삭제 해줍니다.

$ sudo rm -rf /etc/nginx/sites-enabled/default

프로그램 배포

프로그램 배포 위치: ~/projects/mysite
디렉터리 생성: mkdir ~/projects

 

선택 1) SFTP로 배포

  • Remote host: ec2 인스턴스 공개 DNS
  • Username: ec2 Username
  • 중간탭: Advanced Sftp settings
  • 체크박스: UTF-8 Charset, Use private key (ec2 인스턴스에 설정된 pem 파일)

선택 2) Git 으로 배포

프로젝트 배포 디렉터리 이동

$ cd ~/projects


Git clone

$ git clone <Repository-URL>
tar 압축 및 압축 해제

tar로 압축하기
$ tar -cvf [파일명.tar] [폴더명]

ex) abc라는 폴더를 aaa.tar로 압축하고자 한다면tar -cvf aaa.tar abc2. tar​


tar 압축 해제

$ tar -xvf [파일명.tar]
$ tar -xvf [파일명.tar]​

ex) aaa.tar라는 tar파일 압축을 풀고자 한다면tar -xvf aaa.tar


프로그램 실행 환경

프로그램을 실행하기 위해서는 JS 라이브러리와 Python 패키지를 가상 환경에 설치가 되어 있어야 합니다.

NPM설치

npm은 Node 패키지 매니저로 Django로 개발된프로젝트에서사용하는 JS 라이브러리를 설치 및 관리를 합니다.

$ sudo apt install nodejs npm

NPM 라이브러리 설치

$ npm install

리눅스 환경 설정

파이썬 라이브러리를 설치하기 전에 미리 설치해주세요.

$ sudo apt-get install gcc libpq-dev -y
$ sudo apt-get install python-dev python-pip -y
$ sudo apt-get install python3-dev python3-pip python3-venv python3-wheel -y
$ pip3 install wheel

파이썬 패키지 설치

$ pip install -r requirements.txt
참고
Local 에서 파이썬 패키지 목록을 Export 할 경우
pip freeze > requirements.txt로컬 에서 프로그램 실행 시

로컬 환경의 가상 환경에 설치된 파이썬으로 실행해야 합니다.

예시)
C:\0_sources\2_columbia\mysite\env38\Scripts\python.exe .\manage.py runserver

Systemctl 등록

Django 프로그램 또한 시스템에서 편리하게 실행 할 수 있도록 Systemctl 에 등록합니다.

Systemctl 파일 생성

$ sudo vim /etc/systemd/system/mysite.service

아래 코드를 위 파일에 복붙 합니다.

[Unit]
Description=gunicorn daemon
After=network.target
[Service]
User=ubuntu
Group=ubuntu
WorkingDirectory=/home/ubuntu/projects/mysite
EnvironmentFile=/home/ubuntu/venvs/mysite.env
ExecStart=/home/ubuntu/venvs/mysite/bin/gunicorn --workers 4 --bind unix:/tmp/gunicorn.sock config.wsgi:application
[Install]
WantedBy=multi-user.target

프로그램 환경 설정 파일 추가

$ sudo vim /home/ubuntu/venvs/mysite.env

아래 코드를 위 파일에 복붙 합니다.

DJANGO_SETTINGS_MODULE=config.settings.local
주의
설정 안에는 실행 프로파일 설정만 있습니다.지금은 개발/테스트 단계로 local 설정으로 하겠습니다.운영 시 반드시 prod 로 바꿔야 합니다.

시스템 전체 재 시작

  • sudo /etc/init.d/celeryd restart
  • sudo /etc/init.d/celerybeat restart
  • sudo systemctl restart flower.service
  • sudo systemctl restart nginx
  • sudo systemctl restart mysite.service

참고 사항

다른 DB 를 사용할 경우, 아래와 같이 진행해주세요.

예시> PostgreSQL 경우
대상 DB드라이버 설치. 예시> POSTGRE 드라이버 설치

$ pip install psycopg2-binary

Django 설정 일부분(DB Connection 정보 변경)

PostgreSQL

DATABASES = {
    'default': {
    'ENGINE': 'django.db.backends.postgresql_psycopg2',
    'NAME':'postgres',
    'USER':'db_user',
    'PASSWORD':'db_password',
    'HOST':'database-1-mydatabase.xxxxxxxxxxxx.eu-west-1.rds.amazonaws.com',
    'PORT':'5432'
	}
}

 

  1. Django에 정의 된 모델을 DB 테이블로 구성
  2. Django 모든 migrations 폴더 내부를 init.py 를 제외하고 모두 삭제

 

마이그레이션 준비

./venv/mysite/Lib/python manage.py makemigrations

마이그레이션 진행

./venv/mysite/Lib/python manage.py migrate

 

E.O.D.

반응형