이것저것 적어보는 블로그

AWS에 Django 서비스 배포하기 2 - nginx 설정 및 uWSGI와 연결하기 본문

개발&코딩

AWS에 Django 서비스 배포하기 2 - nginx 설정 및 uWSGI와 연결하기

dona0408 2023. 7. 8. 10:43
반응형

uWSGI에 이어서 nginx를 연결할 차례다. ”Client ↔ Nginx ↔ uWSGI ↔ Django”의 구조가 된다.

AWS EC2 인스턴스에서 django의 runserver로 실행시켜서 배포하면 되는 거 아니냐?? 싶겠지만 (나도 그렇게 생각했었고)

runserver는 "개발 및 테스트"가 목적이라고 한다.

공식 도큐먼트를 봐도 보안이나 성능 테스트를 거치지 않았으므로 배포용으로 사용하지 말라고 되어있고

그래서 대부분 nginx + uwsgi + django 조합으로 구성을 한다.

 

우리가 사용할 nginx는 대표적인 웹 서버 애플리케이션(WAS)으로 사용자는 웹 브라우저를 통해 웹서버로 HTTP 요청을 하고 nginx나 Apache 같은 웹 서버가 정적페이지를 담당하게 된다.

nginx는 동적 페이지를 Django에게 요청해야 하는데, nginx는 Python이라는 언어를 모른다.

그래서 nginx는 이를 도와줄 중간다리인 uWSGI에게 요청을 하는 것으로 nginx + uwsgi + django라는 조합이 자주 등장하게 되는 것이다.

 

uwsgi + django만 써도 웹 프레임워크의 기능을 할 수 있는데 nginx를 쓰는 이유로는

wsgi는 SSL연결과 static파일을 지원하지 않는다. django까지 요청이 도착한 다음에 처리해야 해 성능저하가 발생할 수 있다. (uwsgi는 SSL과 정적 파일 지원. 하지만 다른 wsgi보다 메모리와 cpu를 더 많이 소비)

또한 DOS 공격과 같은 많은 요청을 nginx에서 처리 및 분산시킴으로써 서버의 안정성을 보장할 수 있다고 한다.

 

EC2에 nginx를 설치한다. 그리고 nginx.conf 파일을 열고 user를 ubuntu 로 변경한다.

sudo apt-get install nginx

sudo vi /etc/nginx/nginx.conf

 

이제 nginx 설정 파일을 만들 거다. 프로젝트 폴더/.config/nginx 폴더를 만들고 mysite.conf 파일을 만든다.

.config/nginx/mysite.conf

server {
    listen 80;
    server_name *.compute.amazonaws.com;
    charset utf-8;
    client_max_body_size 128M;

    location / {
        uwsgi_pass  unix:///tmp/mysite.sock;
        include     uwsgi_params;
    }
        location /static/ {
                alias [프로젝트 폴더 경로/collectstatic되는 경로]
        }
}
  • listen: 요청을 받을 포트 번호로 80 포트가 http 기본 포트
  • server_name: 요청을 받을 서버 주소로 compute.amazonaws.com 주소를 모두 포함하도록 한다.
  • location / { }: "server_name/" 식의 요청이 들어올 경우
  • location /static/ 은 "server_name/static/" 인 경우다. 이거 제대로 설정 안 해주면 css나 js 등 static 폴더 내의 모든 동작이 안된다.

나중에 static부분을 수정해도 되지만 또 열어서 수정하고 그러기엔 귀찮으니 한 번에 하면서 넘어가는 게 편할 거 같다.

settings.py를 열어 static 파일이 모이는 경로를 수정해 준다.

나의 경우 collected_statics라고 폴더명을 정해줬다. 폴더명은 다른 걸로 해줘도 된다.

python3 manage.py collectstatic 명령어를 입력하면 collected_statics폴더가 새로 생기며 기존 static 폴더의 내용이 복사된다.

이러면 nginx가 정적파일을 불러오도록 설정이 완료된다. 이제 nginx와 uWSGI를 연결할 차례다.

 

nginx와 uWSGI는 HTTP통신을 해도 되지만 둘 다 같은 서버에 있으므로 유닉스 소켓(unix socker) 통신을 하는 것이 오버헤드(overhead)가 적어 효율이 좋다고 한다.

따라서 .config/uwsgi/mysite.inihttp = : 8080 내용을 지우고 다음과 같이 수정한다.

socket = /tmp/mysite.sock
chmod-socket = 666
chown-socket = ubuntu:ubuntu

uWSGI와 nginx를 연결한다면 uWSGI는 항상 켜져있어야 해서 백그라운드에 uWSGI를 계속 실행하도록 설정 파일을 추가한다.

프로젝트 폴더/.config/uwsgi에 uwsgi.service 파일을 만들어 다음의 내용을 입력한다.

[Unit]
Description=uWSGI service
After=syslog.target

[Service]
ExecStart=[1편에서 저장한 uWSGI.ini 저장 경로]

Restart=always
KillSignal=SIGQUIT
Type=notify
StandardError=syslog
NotifyAccess=all

[Install]
WantedBy=multi-user.target

uwsgi.service 파일을 데몬(백그라운드에 실행)에 등록하고 데몬을 새로고침한다.

sudo ln -f [uwsgi.service 경로] /etc/systemd/system/uwsgi.service

sudo systemctl daemon-reload

 

이후 서비스를 사용 가능하게 하고 재시작해준다.

sudo systemctl enable uwsgi
sudo systemctl restart uwsgi

 

또한, Django 프로젝트 내의 nginx 설정 파일을 nginx 애플리케이션에 등록해야 한다.

sudo cp -f [nginx/mysite.conf 경로] /etc/nginx/sites-available/mysite.conf

sites-available에 복사된 설정 파일을 sites-enables폴더 안에서도 링크

sudo ln -sf /etc/nginx/sites-available/mysite.conf /etc/nginx/sites-enabled/mysite.conf

 

다시 데몬을 새로 고침 해주고 nginx와 uwsgi를 다시 실행해 준다.

sudo systemctl daemon-reload

sudo systemctl restart uwsgi nginx

 

 

퍼블릭 DNS 주소로 포트 번호 없이 접속했을 때 정상적으로 접속이 되면 설정이 정상적으로 된 것이다.

static 설정에 제대로 되었는지 쉽게 확인하는 방법으론 /admin 페이지에 들어갔을 때 잘 나오는지 보면 된다.

이렇게 하면 http로 동작하는 서비스를 배포하게 된 것이다.

이후 https 연결로 변경하거나, 도메인을 등록해서 서비스를 이용 및 배포하면 된다.

 

 

프로젝트 배포를 하면서 큰 도움을 받은 사이트

https://kodorricoding.tistory.com/23

https://nerogarret.tistory.com/48

 

Django 서비스 AWS로 배포하기 - [4] nginx 연결하기

Django 서비스 AWS로 배포하기 - [1] 프로젝트 준비와 AWS 서버 대여 Django 서비스 AWS로 배포하기 - [2] github과 프로젝트 업로드 Django 서비스 AWS로 배포하기 - [3] uWSGI 연결하기 사용자의 브라우저를 통

nerogarret.tistory.com

-> 서비스를 배포하면서 처음부터 끝까지 정말 큰 도움이 되었다. 덕분에 절대 안 까먹고 오래오래 기억할 수 있을듯하다..ㅎㅎ

반응형
Comments