Post

02 Nginx Advanced Settings

02 Nginx Advanced Settings

1. ( 1 Nginx * N domain )

1. default.conf

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
  #서버1
  server {
        listen 80;
        server_name jscode.p-e.kr; # 이 경로의 접근은 A localtion

        location / { # A location
                root /usr/share/nginx/nginx-frontend-react/dist;
                index index.html;
        }
  }
  #서버2
  server {
          listen 80;
          server_name admin.jscode.p-e.kr;  # 이 경로의 접근은 B localtion
  
          location / { # B location
                  root /usr/share/nginx/nginx-frontend-next/out;
                  index index.html;
          }
  }

2. Nginx 재반영

1
2
3
4
5
    # Nginx 설정 파일 중 문법 에러가 있는 지 체크
    $ sudo nginx -t
  
    # Nginx의 설정 파일이 바뀐 경우 아래 명령어를 입력해줘야 설정 파일이 반영된다.
    $ sudo nginx -s reload

2. HTTPS

1. HTTPS 인증서

  • HTTPS 인증서 = 서버의 신원을 증명하는 디지털 증명서
  • 사람으로 치면 “공인된 기관이 발급한 신분증”
  • 암호화와 신원확인을 하는 역할을 함.
  • 굳이 특정 인증서lib에 매몰될 필요는 없음.
  • 어디에서인가 발급하고 그걸 사용하기만 하면됨.

2. 인증서안에 있는 내용

  • 이 서버의 도메인(example.com)
  • 서버의 공개키(Public Key)
  • 발급자(CA: Certificate Authority)
  • 유효기간
  • 서명(Signature)

3. 인증서 생성 방법

발급 방식발급 주체 / 도구발급 절차 요약특징적합한 사용처
Let’s Encrypt (무료)Let’s Encrypt + Certbot
(acme.sh, lego 등)
도메인 소유 검증 → 자동 발급무료 / 90일 / 자동 갱신
사실상 표준
일반 웹서비스
직접 서버 운영
클라우드 매니지드 인증서AWS ACM
GCP Managed Cert
Azure Managed Cert
콘솔에서 생성 → LB/CDN 연결서버에 인증서 파일 없음
갱신 완전 자동
클라우드 기반 서비스
로드밸런서 구조
유료 CA 인증서DigiCert
GlobalSign
Sectigo
CSR 생성 → 구매 → 서버 설치비용 발생
OV/EV 가능
신뢰 정책 엄격
금융, 공공
외부 감사 대상
사내 CA 인증서회사 내부 CA내부 CA 발급 → 사내 PC에 루트 CA 배포외부 브라우저 신뢰 ❌
내부 신뢰 ⭕
사내망 시스템
내부 API
Self-signed 인증서자체 생성개인키 생성 → 자체 서명무료 / 즉시 사용
브라우저 경고 발생
로컬 개발
테스트 전용

4. 인증서의 검증

1. CA(Certificate Authority) - 인증서를 발급하는 주체

  • 특정 도메인의 인증서 발급만 함.

2. 사용자의 클라이언트

  • 신뢰 가능한 CA인가
    • 인증서를 서명한 CA가
    • 브라우저(또는 OS)에 내장된 신뢰 목록에 있는지
  • 인증서가 만료되지 않았는가
    • Not Before / Not After 기간 확인
  • 도메인이 일치하는가
    • 속한 도메인과 인증서의 CN / SAN 값이 일치하는지
  • 인증서 체인이 정상인가
    • 중간 인증서 누락 여부
    • 루트 CA까지 연결되는지
  • 서명이 위조되지 않았는가
    • CA 공개키로 서명 검증

3. 서버

  • 인증서 + 개인키를 제공
  • TLS 프로토콜 수행
  • 암호화된 통신 처리

5. Nginx + certBot 인증서 발급

1. certbot

  • 원래는 Nginx의 설정파일에 직접 인증키와 관련된 내용을 추가해야하지만,
  • certbot을 이용하면 자동으로 코드를 추가해줌. ( /etc/nginx/conf.d/default.conf )
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    
     server {
       listen 443 ssl;
       server_name example.com;
      
       # 이부분이 추가됨.
       ssl_certificate     /etc/letsencrypt/live/example.com/fullchain.pem;
       ssl_certificate_key /etc/letsencrypt/live/example.com/privkey.pem;
    
       location / {
           proxy_pass http://localhost:8080;
       }
     }
    

2. 방법

  • 라이브러리 설치
    1
    2
    
     $ sudo snap install --classic certbot
     $ sudo ln -s /snap/bin/certbot /usr/bin/certbot
    
  • 인증서 적용
    1
    2
    3
    4
    
     $ sudo certbot --nginx -d <도메인 주소>
     # 예시
     $ sudo certbot --nginx -d jscode.p-e.kr
     $ sudo certbot --nginx -d admin.jscode.p-e.kr
    

3. conf 파일 분리하기

1. conf 파일 분리

  • 관리하는 시스템이 많아질 경우에는 conf 파일이 굉장히 많아지고 두꺼워짐
  • 따라서 이 파일들을 분리해서 사용한다면,
  • 가독성이 좋아지고 특정 사이트를 디컴 할때 빠르게 처리가 가능해짐

    2. 구조

    1. 예시구조

    1
    2
    3
    
      /etc/nginx/conf.d/default.conf
      /etc/nginx/conf.d/websites/jscode.p-e.kr.conf;
      /etc/nginx/conf.d/websites/admin.jscode.p-e.kr.conf;
    

2. 신규 conf

1
2
3
4
5
6
7
8
9
   #기존에 server 파일
   server {
    listen 443 ssl;
    server_name example.com;

    location / {
        proxy_pass http://localhost:8080;
    }
  }

3. 기준 conf(/etc/nginx/conf.d/default.conf)

1
2
3
  #해당 파일들을 include 처리함.
  include conf.d/websites/jscode.p-e.kr.conf;
  include conf.d/websites/admin.jscode.p-e.kr.conf

4. 프록시

1. 프록시 서버

  • 중간에서 대신 통신해주는 대리인
  • 클라이언트와 서버가 직접 통신하지 않고, 그 사이에 끼어 요청과 응답을 중계
  • 요청을 대신 받아서 전달하고, 응답을 대신 받아서 돌려주는 중간 서버

2. 프록시의 역할

  • 보안 (외부 직접 접근 차단)
  • 트래픽 제어
  • 로드밸런싱
  • 캐싱
  • TLS 처리(HTTPS 종료)

3. 포워드프록시, 리버스 프록시

  • 포워드 프록시
    1
    
     클라이언트 ─▶ 프록시 ─▶ 인터넷(서버)
    
    • 프록시는 클라이언트 쪽 네트워크에 있음
    • 서버는 프록시 존재를 모를 수도 있음
    • 보내려고 하는 요청을 관리 또는 보안 처리
  • 리버스 프록시
    1
    
     인터넷(클라이언트) ─▶ 프록시 ─▶ 내부 서버
    
    • 프록시는 서버 앞단에 있음
    • 클라이언트는 실제 서버를 모름
    • 들어오는 요청을 관리 또는 보안 처리

4. 프록시 설정(nginx -> springBoot)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
    # https 제한은 certbot으로 동일하게 하는게 편함
    server {
      listen 80;
      server_name example.com;
  
      location / {
          proxy_pass http://localhost:8080;
  
          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;
      }
   }  

5. 리버스프록시로 Request 제한

1. 방법

  • /etc/nginx/conf.d/default.conf파일에 접근할 수 있는 IP제한을 설정함.
  • 이때 conf파일을 분리해서 사용하는 경우에는 그 해당 페이지만 제한이 가능함.

2. 제한

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
  # 서버블록 밖에서 작성 필요
  # limit_req_zone : 요청 수를 제한하기 위한 메모리 공간(zone)과 요청 속도(rate)를 정의
  # $binary_remote_addr : 요청 수를 제한하는 기준을 클라이언트의 IP로 설정
  # zone=mylimit:10m : 메모리 공간(zone)의 이름을 mylimit이라고 지정, 메모리 공간의 크기를 10MB 제한 (약 16만개의 IP 주소를 관리할 수 있음)
  # rate=3r/s : 1초에 최대 3개의 요청만 허용
  
  # 이위치에 해당내용은 선언이 필수.
  limit_req_zone $binary_remote_addr zone=mylimit:10m rate=3r/s;
  
  server {
          # limit_req_zone에서 정의한 mylimit이라는 조건을 이 server 블럭에 적용
          limit_req zone=mylimit;
          
          # 요청이 제한됐을 때 429(Too Many Requests) 상태 코드를 반환
          limit_req_status 429;
          
          server_name api.jscode.p-e.kr;
          
          location / {
                  proxy_pass http://localhost:8080;
          }
      listen 443 ssl; # managed by Certbot
      ssl_certificate /etc/letsencrypt/live/api.jscode.p-e.kr/fullchain.pem # managed by Certbot
      ssl_certificate_key /etc/letsencrypt/live/api.jscode.p-e.kr/privkey.pm; # managed by Certbot
      include /etc/letsencrypt/options-ssl-nginx.conf; # managed by Certbot
      ssl_dhparam /etc/letsencrypt/ssl-dhparams.pem; # managed by Certbot
  }
This post is licensed under CC BY 4.0 by the author.