TIL - 20260609

juni·2026년 6월 9일

TIL

목록 보기
374/468

0609 AWS 운영 실무 기초 (2/N): EC2 서버 생성과 기본 운영


✅ 1. EC2란 무엇인가?

  • EC2(Elastic Compute Cloud)는 AWS에서 제공하는 가상 서버 서비스입니다.
  • 쉽게 말하면 AWS에서 빌려 쓰는 리눅스 또는 윈도우 서버입니다.
  • 웹 개발자는 EC2 위에 백엔드 서버, Nginx, PM2, Docker, 배포 스크립트 등을 설치해서 웹서비스를 운영할 수 있습니다.

➕ 1-1. EC2가 필요한 이유

  • 백엔드 서버 실행

    • NestJS, Express, Spring Boot 같은 API 서버를 실행할 수 있습니다.
  • 프론트엔드 정적 파일 제공

    • React/Vite 빌드 결과물을 Nginx로 제공할 수 있습니다.
  • Reverse Proxy 구성

    • Nginx를 앞단에 두고 API 서버로 요청을 전달할 수 있습니다.
  • 운영 환경 구성

    • 환경변수, 로그, 배포, SSL, 프로세스 관리 등을 직접 제어할 수 있습니다.

✅ 2. EC2 인스턴스 생성 시 선택 항목

  • EC2를 만들 때는 운영체제, 인스턴스 타입, 키 페어, 보안 그룹, 스토리지 등을 선택해야 합니다.

➕ 2-1. AMI

  • AMI(Amazon Machine Image)는 EC2 서버의 운영체제 이미지입니다.
  • 보통 웹 서버 운영에는 Ubuntu 또는 Amazon Linux를 많이 사용합니다.
추천 예시:
Ubuntu Server 22.04 LTS
Ubuntu Server 24.04 LTS
Amazon Linux 2023
  • 초보자나 Node.js/NestJS 운영 기준으로는 자료가 많은 Ubuntu LTS 계열이 무난합니다.

➕ 2-2. 인스턴스 타입

  • 인스턴스 타입은 서버의 CPU, 메모리 성능을 결정합니다.
타입용도
t3.micro테스트, 소규모 서비스
t3.small작은 운영 서비스
t3.medium트래픽이 조금 있는 운영 서비스
t3.large 이상부하가 있는 서비스
  • 처음부터 큰 서버를 쓰기보다 작은 타입으로 시작하고, CPU/메모리 사용량을 보면서 올리는 것이 좋습니다.

➕ 2-3. 스토리지

  • EC2의 기본 디스크는 EBS 볼륨입니다.
  • 로그, 빌드 파일, 업로드 파일, Docker 이미지가 쌓이면 디스크가 부족할 수 있습니다.
초기 추천:
20GB ~ 30GB

서비스 운영:
30GB 이상 검토
  • 업로드 파일은 가능하면 EC2 디스크가 아니라 S3에 저장하는 것이 좋습니다.

✅ 3. 키 페어와 SSH 접속

  • EC2에 접속하려면 보통 키 페어(Key Pair)를 사용합니다.
  • 키 페어는 서버에 접속할 수 있는 열쇠이므로 절대 유출되면 안 됩니다.

➕ 3-1. SSH 접속 예시

ssh -i my-key.pem ubuntu@서버IP
  • Ubuntu AMI를 사용하면 기본 사용자는 보통 ubuntu입니다.
  • Amazon Linux는 기본 사용자가 보통 ec2-user입니다.
# Ubuntu
ssh -i my-key.pem ubuntu@서버IP

# Amazon Linux
ssh -i my-key.pem ec2-user@서버IP

➕ 3-2. 키 파일 권한 설정

  • 키 파일 권한이 너무 열려 있으면 SSH 접속이 거부될 수 있습니다.
chmod 400 my-key.pem
  • 키 파일은 GitHub, Notion, Slack, 카카오톡 등에 올리면 안 됩니다.
  • 분실하면 서버 접속이 매우 번거로워질 수 있으므로 안전한 위치에 백업해야 합니다.

✅ 4. 보안 그룹

  • 보안 그룹(Security Group)은 EC2의 방화벽 역할을 합니다.
  • 어떤 포트로, 어떤 IP가 접근할 수 있는지 설정합니다.

➕ 4-1. 자주 사용하는 포트

포트용도
22SSH 접속
80HTTP
443HTTPS
3000Node.js/NestJS 내부 서버
5173Vite 개발 서버
5432PostgreSQL
3306MySQL

➕ 4-2. 기본 보안 그룹 예시

인바운드 규칙

SSH 22
- 내 IP만 허용

HTTP 80
- 0.0.0.0/0 허용

HTTPS 443
- 0.0.0.0/0 허용
  • 운영 서버에서 SSH 22번을 0.0.0.0/0으로 열어두는 것은 위험합니다.
  • 가능하면 본인 회사 IP 또는 내 IP만 허용해야 합니다.

➕ 4-3. 피해야 할 설정

위험한 설정:
22번 포트 전체 공개
5432 DB 포트 전체 공개
3306 DB 포트 전체 공개
관리자용 포트 전체 공개
테스트 서버 방치
  • DB는 가능하면 EC2 내부 또는 RDS 보안 그룹을 통해서만 접근하게 해야 합니다.
  • 외부에서 직접 DB에 접속해야 한다면 IP를 제한해야 합니다.

✅ 5. EC2 초기 세팅

  • 새 EC2를 만들면 기본 패키지를 업데이트하고 필요한 도구를 설치해야 합니다.

➕ 5-1. 패키지 업데이트

sudo apt update
sudo apt upgrade -y
  • 서버를 만들고 바로 하는 기본 작업입니다.
  • 보안 패치와 패키지 정보를 최신 상태로 맞춥니다.

➕ 5-2. 기본 도구 설치

sudo apt install -y git curl unzip build-essential
도구용도
git소스코드 가져오기
curl외부 요청 테스트
unzip압축 파일 해제
build-essential일부 Node 패키지 빌드에 필요

✅ 6. Node.js 설치

  • NestJS나 React 빌드 서버로 사용하려면 Node.js가 필요합니다.
  • 운영에서는 프로젝트와 맞는 Node.js 버전을 설치해야 합니다.

➕ 6-1. Node.js 버전 확인

node -v
npm -v

➕ 6-2. NVM 설치 방식

  • Node.js 버전을 쉽게 관리하려면 NVM을 사용할 수 있습니다.
curl -o- https://raw.githubusercontent.com/nvm-sh/nvm/v0.40.1/install.sh | bash
  • 설치 후 터미널을 다시 열거나 아래 명령어를 실행합니다.
source ~/.bashrc
nvm install 20
nvm use 20
node -v
  • 운영 서버에서는 로컬 개발 환경과 Node.js major 버전을 맞추는 것이 좋습니다.

✅ 7. 프로젝트 배포 폴더 구성

  • EC2 안에서는 프로젝트 위치를 명확히 정하는 것이 좋습니다.

➕ 7-1. 예시 폴더 구조

/home/ubuntu/apps/
  togethermall-api/
  togethermall-admin/
  togethermall-front/

/var/www/
  frontend/
  admin/
  • 백엔드 소스코드는 /home/ubuntu/apps 아래에 두고,
  • 프론트엔드 빌드 결과물은 /var/www 아래에 두는 식으로 구분할 수 있습니다.

➕ 7-2. 소스코드 가져오기

mkdir -p /home/ubuntu/apps
cd /home/ubuntu/apps

git clone git@github.com:organization/project-api.git
  • private repository라면 서버에 GitHub 접근 권한을 설정해야 합니다.
  • SSH Deploy Key 또는 GitHub Actions 배포 방식을 사용할 수 있습니다.

✅ 8. PM2 설치와 백엔드 실행

  • Node.js 백엔드 서버는 터미널에서 직접 npm run start:prod로 실행하면 터미널을 닫을 때 종료될 수 있습니다.
  • 운영에서는 PM2 같은 프로세스 매니저를 사용합니다.

➕ 8-1. PM2 설치

npm install -g pm2

➕ 8-2. NestJS 빌드와 실행

cd /home/ubuntu/apps/togethermall-api

npm install
npm run build

pm2 start dist/main.js --name togethermall-api

➕ 8-3. PM2 상태 확인

pm2 list
pm2 logs togethermall-api
pm2 monit

➕ 8-4. 서버 재부팅 후 자동 실행

pm2 startup
pm2 save
  • pm2 startup 실행 후 출력되는 명령어를 한 번 더 실행해야 할 수 있습니다.
  • pm2 save를 해야 현재 실행 중인 프로세스 목록이 저장됩니다.

✅ 9. Nginx 설치와 Reverse Proxy

  • 운영에서는 사용자가 직접 http://서버IP:3000으로 접근하게 하지 않습니다.
  • 보통 Nginx가 80/443 포트로 요청을 받고, 내부의 NestJS 서버로 전달합니다.

➕ 9-1. Nginx 설치

sudo apt install -y nginx

➕ 9-2. Nginx 상태 확인

sudo systemctl status nginx
sudo systemctl start nginx
sudo systemctl enable nginx

➕ 9-3. API Reverse Proxy 설정 예시

server {
  listen 80;
  server_name api.example.com;

  location / {
    proxy_pass http://localhost:3000;
    proxy_set_header Host $host;
    proxy_set_header X-Real-IP $remote_addr;
    proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
    proxy_set_header X-Forwarded-Proto $scheme;
  }
}

➕ 9-4. 설정 적용

sudo nginx -t
sudo systemctl reload nginx
  • sudo nginx -t는 Nginx 설정 문법 검사입니다.
  • 문법 검사를 통과한 뒤 reload해야 합니다.

✅ 10. React 정적 파일 배포

  • React/Vite 프로젝트는 빌드 후 정적 파일을 Nginx로 제공할 수 있습니다.

➕ 10-1. 프론트엔드 빌드

npm install
npm run build
  • Vite는 보통 dist 폴더가 생성됩니다.
dist/
  index.html
  assets/

➕ 10-2. 정적 파일 위치로 복사

sudo mkdir -p /var/www/frontend
sudo cp -r dist/* /var/www/frontend

➕ 10-3. Nginx 설정 예시

server {
  listen 80;
  server_name www.example.com;

  root /var/www/frontend;
  index index.html;

  location / {
    try_files $uri /index.html;
  }
}
  • React Router를 사용하는 SPA에서는 try_files $uri /index.html; 설정이 중요합니다.
  • 이 설정이 없으면 /event/galaxy 같은 경로로 직접 접속했을 때 404가 발생할 수 있습니다.

✅ 11. 환경변수 설정

  • EC2 운영 서버에서는 .env 파일 또는 서버 환경변수로 설정값을 관리해야 합니다.

➕ 11-1. 백엔드 .env 예시

NODE_ENV=production
PORT=3000

DATABASE_URL=postgresql://USER:PASSWORD@DB_HOST:5432/DB_NAME

JWT_SECRET=production-secret
CORS_ORIGIN=https://www.example.com
  • 운영 .env 파일은 Git에 올리면 안 됩니다.
  • 파일 권한도 제한하는 것이 좋습니다.
chmod 600 .env

➕ 11-2. 환경변수 수정 후 재시작

pm2 reload togethermall-api
  • .env를 수정해도 실행 중인 서버에 바로 반영되지 않습니다.
  • 대부분 서버 프로세스를 재시작해야 합니다.

✅ 12. 도메인 연결

  • EC2 서버를 실제 서비스로 운영하려면 도메인을 연결해야 합니다.
  • 도메인 DNS에서 EC2의 Public IP 또는 Elastic IP를 바라보게 설정합니다.

➕ 12-1. Elastic IP

  • EC2의 Public IP는 인스턴스를 중지하고 다시 시작하면 바뀔 수 있습니다.
  • 운영 서버에서는 고정 IP인 Elastic IP를 사용하는 것이 좋습니다.
api.example.com → Elastic IP
www.example.com → Elastic IP 또는 CloudFront

➕ 12-2. DNS A 레코드 예시

Type: A
Name: api
Value: EC2 Elastic IP
  • 설정 후 DNS 전파 시간이 걸릴 수 있습니다.
  • 바로 안 된다고 서버 문제로 단정하면 안 됩니다.

✅ 13. SSL과 HTTPS 적용

  • 운영 서비스는 HTTPS 적용이 필수입니다.
  • 로그인, 관리자 페이지, 개인정보 입력, 상담 신청이 있는 사이트는 반드시 HTTPS를 사용해야 합니다.

➕ 13-1. Certbot 설치

sudo apt install -y certbot python3-certbot-nginx

➕ 13-2. SSL 인증서 발급

sudo certbot --nginx -d api.example.com
  • 프론트엔드와 API 도메인을 함께 발급할 수도 있습니다.
sudo certbot --nginx -d www.example.com -d api.example.com

➕ 13-3. 자동 갱신 테스트

sudo certbot renew --dry-run
  • Let's Encrypt 인증서는 만료 기간이 있으므로 자동 갱신이 정상인지 확인해야 합니다.

✅ 14. EC2 로그 확인

  • 운영 서버에서 문제가 발생하면 로그를 확인해야 합니다.
  • EC2에서는 애플리케이션 로그, PM2 로그, Nginx 로그, 시스템 로그를 함께 봐야 합니다.

➕ 14-1. PM2 로그

pm2 logs togethermall-api

➕ 14-2. Nginx 로그

sudo tail -f /var/log/nginx/access.log
sudo tail -f /var/log/nginx/error.log

➕ 14-3. 시스템 상태 확인

df -h
free -h
top
명령어용도
df -h디스크 사용량 확인
free -h메모리 사용량 확인
topCPU/프로세스 확인

✅ 15. EC2에서 자주 발생하는 문제

➕ 15-1. SSH 접속 실패

  • 가능한 원인:

    • 키 파일 권한 문제
    • 잘못된 사용자명
    • 보안 그룹에서 22번 포트 미허용
    • 접속 IP가 바뀌었는데 보안 그룹 미수정
    • 잘못된 키 페어 사용
chmod 400 my-key.pem

➕ 15-2. 502 Bad Gateway

  • 가능한 원인:

    • NestJS 서버가 죽어 있음
    • PM2 프로세스 오류
    • Nginx proxy_pass 포트가 틀림
    • 백엔드가 3000 포트에서 실행되지 않음
    • 환경변수 누락으로 앱 실행 실패
pm2 list
pm2 logs togethermall-api
sudo tail -f /var/log/nginx/error.log

➕ 15-3. 사이트 접속 안 됨

  • 가능한 원인:

    • EC2 인스턴스 중지
    • 보안 그룹 80/443 미허용
    • Nginx 미실행
    • DNS 설정 오류
    • SSL 인증서 문제
sudo systemctl status nginx
sudo nginx -t

➕ 15-4. 디스크 용량 부족

  • 가능한 원인:

    • 로그 파일 누적
    • Docker 이미지 누적
    • 업로드 파일 누적
    • 빌드 파일 중복 보관
    • 백업 파일 방치
df -h
du -sh /var/log/*
du -sh /home/ubuntu/apps/*
  • 디스크가 꽉 차면 로그 저장, 빌드, DB, 배포가 실패할 수 있습니다.

✅ 16. EC2 운영 보안

➕ 16-1. SSH 보안

  1. 22번 포트는 내 IP만 허용
  2. 키 파일 권한 제한
  3. 키 파일 Git 업로드 금지
  4. 사용하지 않는 계정 제거
  5. 필요 시 SSH 포트 변경 검토
  6. root 직접 로그인 제한

➕ 16-2. 서버 내부 보안

  1. .env 파일 권한 제한
  2. 운영 DB 비밀번호 노출 금지
  3. 불필요한 포트 닫기
  4. 패키지 보안 업데이트
  5. 로그에 토큰/비밀번호 출력 금지
  6. 관리자 페이지 접근 제한 검토

➕ 16-3. 보안 그룹 보안

좋은 예시:
22번 포트 → 내 IP만 허용
80/443 → 전체 허용
5432 → 외부 공개 안 함

나쁜 예시:
22번 포트 → 0.0.0.0/0
5432 포트 → 0.0.0.0/0
3000 포트 → 0.0.0.0/0

✅ 17. EC2 비용 관리

  • EC2는 실행 중인 시간만큼 비용이 발생합니다.
  • 인스턴스 타입, 스토리지, 데이터 전송량, Elastic IP 사용 방식에 따라 비용이 달라집니다.

➕ 17-1. 비용 관리 포인트

  1. 사용하지 않는 인스턴스 중지
  2. 불필요한 EBS 볼륨 삭제
  3. 사용하지 않는 Elastic IP 확인
  4. 로그와 빌드 파일 정리
  5. 인스턴스 타입 과도하게 크게 잡지 않기
  6. 비용 알림 설정
  7. 테스트 서버 방치하지 않기

➕ 17-2. 주의할 점

  • EC2를 중지해도 EBS 스토리지 비용은 계속 발생할 수 있습니다.
  • Elastic IP도 연결 상태에 따라 비용이 발생할 수 있습니다.
  • 테스트용 서버를 만들고 잊어버리면 불필요한 과금이 생길 수 있습니다.

✅ 18. 실무 체크리스트

➕ 18-1. EC2 생성 체크리스트

  1. Ubuntu LTS 같은 안정적인 AMI를 선택했는가?
  2. 인스턴스 타입이 서비스 규모에 맞는가?
  3. 키 페어를 안전하게 보관했는가?
  4. 스토리지 용량이 충분한가?
  5. 보안 그룹에서 22번 포트를 내 IP로 제한했는가?
  6. 80, 443 포트를 열었는가?
  7. Elastic IP를 연결했는가?

➕ 18-2. 서버 초기 세팅 체크리스트

  1. 패키지 업데이트를 했는가?
  2. Git, curl, unzip 등을 설치했는가?
  3. Node.js 버전을 맞췄는가?
  4. PM2를 설치했는가?
  5. Nginx를 설치했는가?
  6. 프로젝트 폴더 구조를 정리했는가?
  7. 운영 .env 파일을 생성했는가?

➕ 18-3. 배포 후 체크리스트

  1. PM2 프로세스가 online 상태인가?
  2. Nginx 설정 테스트를 통과했는가?
  3. API health check가 정상인가?
  4. 프론트엔드 직접 URL 접속이 정상인가?
  5. HTTPS 인증서가 정상인가?
  6. Nginx error log에 오류가 없는가?
  7. PM2 logs에 앱 오류가 없는가?
  8. 디스크, 메모리 사용량이 정상인가?

✅ 19. AI를 활용해 EC2 문제를 해결할 때 질문법

  • EC2 문제는 서버 상태, 보안 그룹, Nginx, PM2, 도메인, 로그가 모두 연결됩니다.
  • AI에게 질문할 때는 “어떤 주소로 접속했고, 어떤 에러가 나며, 서버 내부 상태가 어떤지”를 함께 알려줘야 합니다.

➕ 19-1. 좋은 질문 예시

AWS EC2 Ubuntu 서버에 NestJS API를 배포했는데 api.example.com 접속 시 502 Bad Gateway가 발생해.

환경:
1. EC2 Ubuntu 22.04
2. NestJS는 PM2로 실행
3. Nginx reverse proxy 사용
4. NestJS 내부 포트는 3000
5. 도메인은 api.example.com
6. 보안 그룹은 80, 443, 22 허용
7. pm2 list에서는 api가 errored 상태
8. pm2 logs에는 DATABASE_URL 누락 에러가 있음

이 상황에서 확인 순서와 수정 방법을 알려줘.
명령어별로 무슨 의미인지 설명해줘.

➕ 19-2. AI 답변 검증 기준

  1. PM2 로그를 먼저 확인하게 하는가?
  2. Nginx 로그와 앱 로그를 구분하는가?
  3. 보안 그룹, 포트, 프로세스 상태를 함께 확인하는가?
  4. 무작정 서버 재부팅부터 시키지 않는가?
  5. 위험한 rm -rf, reset --hard 같은 명령어를 함부로 권하지 않는가?
  6. 환경변수 수정 후 PM2 reload를 안내하는가?
  7. 운영 DB 정보나 Secret 값을 그대로 보내라고 하지 않는가?

📌 요약

  • EC2는 AWS에서 제공하는 가상 서버이며, 백엔드 API, Nginx, PM2, Docker, 배포 스크립트 등을 운영할 수 있습니다.
  • EC2 생성 시 AMI, 인스턴스 타입, 키 페어, 보안 그룹, 스토리지를 신중하게 선택해야 합니다.
  • SSH 접속에는 키 페어가 필요하며, 키 파일 권한은 chmod 400으로 제한해야 합니다.
  • 보안 그룹에서는 22번 포트는 내 IP만 허용하고, 80/443은 웹 접속을 위해 열어두는 것이 일반적입니다.
  • Node.js 백엔드는 PM2로 운영하고, Nginx를 Reverse Proxy로 사용하면 안정적인 운영 구조를 만들 수 있습니다.
  • React 정적 파일은 Nginx로 제공할 수 있으며, SPA에서는 try_files $uri /index.html; 설정이 중요합니다.
  • 운영에서는 도메인, Elastic IP, HTTPS, 환경변수, 로그 확인까지 함께 관리해야 합니다.
  • EC2 장애 대응의 핵심은 PM2 로그, Nginx 로그, 보안 그룹, 포트, 환경변수를 순서대로 확인하는 것입니다.

0개의 댓글