글에 앞서 서린이는 (서버어린이) 힘든 과정이었다.
프론트앤드쪽이 https로 ssl 적용하기는 요새 호스팅업체에서 알아서 잘 해주기 때문에 (파이어베이스도 그렇고..) 어렵지 않지만
문제는 프론트가 서버통신할때 서버도 https여야 오류가 안난다는 사실...
현재 도메인만 적용시켜놓고 뒤에 포트번호를 붙여서 쓰던 서버를 이제는 https를 적용해야했다.. (ex : abcdefg:shop/8000)
참고로 서버는 AWS LightSail의 인스턴스 (우분투 24)를 사용중
여러가지 방법이 있겠다만 letsencrypt를 사용하면.. 편하게 할 수 있었다.
그전에 이상한 자료를 봐서 너무 돌아갔었지만...
일단 도메인을 구매했다는 가정하에 작성하겠다.
나의 경우는 가비아에서 500원주고 샀었다.
AWS LightSail에서 일단 도메인을 등록해야한다.
가비아에서는
A타입과 CNAME타입을 사용한다.
A 타입의 www는 잘못썼던것 같은데. 일단 도메인을 등록하는건 많은 자료가 있으니 해보도록 하자..
일단 이렇게 되면 abcdefg.shop:8000 포트로 fastapi가 실행될 수 있어야한다.. 우리의 목표는 https를 적용함과 동시에 8000포트번호를 없에버리는것....!
참고로 처음 가비아에서 DNS 세팅을 하게되면 적용되기까지 시간이 좀 오래 걸린다..
확인하고 싶으면
nslookup 도메인명
을 치면
Server: 8.8.8.8
Address: 8.8.8.8#53
Non-authoritative answer:
Name: naver.com
Address: 1.2.3.4
머 이런식으로 나와야 정상적으로 되었다는거다
일단 되었다고 치고 ssh로 접속하자.
참고로 ssl을 적용하려면 80포트가 열려있고 서버가 실행되고있지 않아야한다..일단 docker compose down으로 멈춰두자
LightSail은 편하게도 22 80 포트는 기본적으로 열려있다. 443과 fastapi를 위해 열었던 8000번을 추가해두었었다 나는..
일단 우리는 nginx와 Lets Encrypt를 사용한다.
sudo apt update
sudo apt install certbot
sudo certbot certonly --standalone -d 도메인주소
이제 docker-compose.yaml을 수정한다.
docker-compose.yaml
services:
interior-app:
image: ddurdocker/interiorserver:latest
ports:
- 8000:8000
environment:
- MYSQL_HOST=db
- MYSQL_DATABASE=demo
- MYSQL_USER=root
- MYSQL_PASSWORD=password
depends_on:
- db
networks:
- app-network
restart: always
nginx:
image: nginx:latest
container_name: nginx
restart: always
ports:
- "80:80"
- "443:443"
volumes:
- ./nginx.conf:/etc/nginx/nginx.conf:ro
- /etc/letsencrypt/archive/도메인명/fullchain1.pem:/etc/nginx/ssl/fullchain.pem:ro
- /etc/letsencrypt/archive/도메인명/privkey1.pem:/etc/nginx/ssl/privkey.pem:ro
depends_on:
- interior-app
networks:
- app-network
db:
image: mysql:8.0
platform: linux/x86_64
environment:
MYSQL_DATABASE: 'demo'
MYSQL_ROOT_PASSWORD: 'password'
MYSQL_PASSWORD: 'password'
TZ: 'Asia/Seoul'
volumes:
- mysql_data:/var/lib/mysql
ports:
- 33306:3306
networks:
- app-network
restart: always
networks:
app-network:
driver: bridge
volumes:
mysql_data:
driver: local
여기서 중요한 점은 networks가 같아야한다는점이고 (nginx와 fastapi 프로젝트가..)
이다음에는 nginx.config를 작성한다.
위치는 docker-compose.yaml이 있는 폴더에 작성한다.
nano nginx.conf
events {}
http {
server {
listen 80;
server_name 도메인명;
return 301 https://$host$request_uri;
}
server {
listen 443 ssl;
server_name 도메인명;
ssl_certificate /etc/nginx/ssl/fullchain.pem;
ssl_certificate_key /etc/nginx/ssl/privkey.pem;
location / {
proxy_pass http://interior-app:8000;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
}
}
}
location에서 proxy_pass의 경우 나는 interior-app이지만 docker-compose.yaml에서 fastapi의 이름을 적어주면된다.
도메인명은 예를들면 naver.com이라면 그것으로 된다.
이제 인증서를 만들자
인증서 명령어
sudo certbot certonly --standalone -d 도메인 -d 서브도메인 (안써도무방)
물론 위의 명령어는.. 가비아에서 DNS세팅이 되어야 한다...
세팅해두고 다음날 편하게 하는것을 추천
확인하는 방법은
ls -l /etc/letsencrypt/live/도메인명/
이렇게 했을 때
이렇게 4개가 있다면 성공
그리고 우리는 privkey fullchain을 chmod로 접근가능하게 해줘야한다.
sudo chmod 644 /etc/letsencrypt/live/도메인명/fullchain.pem
sudo chmod 644 /etc/letsencrypt/live/도메인명/privkey.pem
심볼릭링크라서 안될수있는데..
그렇다면 직접 아카이브로 가서 풀어주자
확인경로는
sudo ls -l /etc/letsencrypt/archive/도메인명/fullchain1.pem
sudo chmod 644 /etc/letsencrypt/archive/도메인명/fullchain1.pem
sudo chmod 644 /etc/letsencrypt/archive/도메인명/privkey1.pem
자 이러고 나서 docker compose up을 해주면 아주 잘되는것을 알 수 있다.
쓰고보니 별거 아닌것처럼 쓰긴했는데
하도 인터넷에 이상한정보들이 많아서 -_- 며칠 고생했다.
키포인트는
가비아의 DNS 세팅하기 (A 와 CNAME)
가 아닐까...?
'프로그래밍 > Backend' 카테고리의 다른 글
[AWS] CloudFront, S3 이미지 pdf 다운로드 캐싱에러 log (0) | 2025.02.10 |
---|---|
[FastAPI] docker compose로 fastapi & mysql aws LightSail에 배포하기 (0) | 2025.01.23 |
[FastAPI] MySQL 한글이 깨져 보일 때 (feat: 파워쉘, cmd등) (0) | 2025.01.16 |
[FastAPI] pydantic v2 - orm_mode를 마이그레이션.. (0) | 2025.01.12 |