Files
vpd-permission-poc/docs/runbooks/547-vm-https-operations.md

110 lines
4.3 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# Redmine #547 - 외부 VM HTTPS 운영 런북
## 운영 구조
- 공개 endpoint: `https://<소유 FQDN>` 또는 `https://<고정 public IPv4>`
- Caddy: VM의 80/443에서 TLS termination, HTTP redirect, HSTS, 인증서 자동 발급·갱신
- Spring Boot: `127.0.0.1:8082`에서만 수신
- 외부 `8082/tcp`: OCI NSG와 VM firewalld 모두 deny
FQDN을 쓰면 A 레코드는 VM public IP를 가리켜야 한다. DNS가 없는 고정 public IPv4는 Lets Encrypt `shortlived` profile 기반 약 6일 인증서를 사용하며 Caddy 자동 갱신이 정상인지 반드시 모니터링한다. 임시 공개 DNS 서비스와 Caddy 로컬 CA 인증서는 운영 endpoint로 사용하지 않는다.
## 최초 준비
아래 작업은 시스템 패키지와 방화벽을 바꾸므로 개별 승인을 받은 뒤 수행한다.
1. 소유 FQDN의 A 레코드를 VM public IP로 설정하거나 고정 public IPv4 사용을 확정한다.
2. OCI NSG와 VM firewalld에서 80/443 ingress를 허용한다.
3. 기존 8082 ingress를 OCI NSG와 firewalld에서 제거한다.
4. Oracle Linux/RHEL 계열 VM에 공식 Caddy 패키지를 설치한다.
```bash
sudo dnf install -y dnf-plugins-core
sudo dnf copr enable -y @caddy/caddy
sudo dnf install -y caddy
```
공식 패키지는 `caddy.service``/etc/caddy/Caddyfile`을 제공한다. 설정 스크립트가 service enable/start를 처리한다.
## 적용
먼저 로컬 검증과 앱 배포를 수행한다.
```bash
mvn test
scripts/test-backoffice-https-config.sh
scripts/deploy-backoffice-vm.sh --host hermes
```
HTTPS 설정을 dry-run으로 확인한 다음 적용한다.
```bash
scripts/configure-backoffice-https-vm.sh \
--host hermes \
--public-host admin.example.com \
--tls-email ops@example.com \
--expected-address 130.162.134.59 \
--dry-run
scripts/configure-backoffice-https-vm.sh \
--host hermes \
--public-host admin.example.com \
--tls-email ops@example.com \
--expected-address 130.162.134.59
```
실제 endpoint, 이메일, 주소로 바꿔 실행한다. FQDN 대신 IP를 쓰는 현재 hermes 예시는 `--public-host 130.162.134.59 --expected-address 130.162.134.59`다. 스크립트는 DNS/IP 일치, Caddy/sudo, Caddyfile 문법, service 상태를 확인하고 기존 설정을 `~/apps/vpd-backoffice/caddy-backups`에 저장한다.
## 반복 검증
설정을 바꾸지 않고 외부 검증만 다시 수행할 수 있다.
```bash
scripts/configure-backoffice-https-vm.sh \
--host hermes \
--public-host admin.example.com \
--tls-email ops@example.com \
--expected-address 130.162.134.59 \
--verify-only
```
검증 항목:
- HTTP `/login`이 동일 host의 HTTPS로 전환됨
- HTTPS 인증서가 공개 신뢰됨
- HSTS 1년
- `JSESSIONID`의 Secure/HttpOnly/SameSite=Lax
- 외부 `:8082` 직접 연결 실패
## 인증서 갱신과 모니터링
Caddy는 공개 DNS 이름의 인증서를 자동 갱신하며, 공식 systemd service의 인증서 상태는 `/var/lib/caddy/.local/share/caddy`에 유지된다. 별도 cron이나 certbot hook을 추가하지 않는다.
```bash
ssh hermes 'systemctl is-active caddy && systemctl is-enabled caddy'
ssh hermes 'sudo journalctl -u caddy --since "24 hours ago" --no-pager'
ssh hermes 'sudo caddy validate --config /etc/caddy/Caddyfile --adapter caddyfile'
```
ACME 오류, 인증서 만료 경고, 반복 reload 실패를 알림 대상으로 삼는다. VM 백업에서 Caddy data directory와 앱의 Caddyfile backup을 함께 보존한다.
## 장애와 롤백
1. 앱이 살아 있는지 VM 내부에서 확인한다.
```bash
ssh hermes 'curl -sS -H "X-Forwarded-Proto: https" -H "X-Forwarded-Host: admin.example.com" -o /dev/null -w "%{http_code}\n" http://127.0.0.1:8082/login'
```
2. Caddy 로그와 설정을 확인한다.
3. 설정 변경 직후 장애라면 가장 최근 backup을 복원한다.
```bash
ssh hermes 'ls -1t ~/apps/vpd-backoffice/caddy-backups/Caddyfile.* | head -n 3'
ssh hermes 'sudo install -o root -g root -m 644 ~/apps/vpd-backoffice/caddy-backups/Caddyfile.<timestamp> /etc/caddy/Caddyfile && sudo systemctl reload caddy'
```
4. 앱 jar 롤백이 필요하면 직전 승인된 artifact를 배포하고 앱과 Caddy를 모두 재검증한다.
장애 우회를 위해 `8082`를 다시 공개하지 않는다. 서비스 중단이나 방화벽/NSG 롤백은 개별 승인을 받는다.