| 항목 | 내용 |
|---|---|
| 프로젝트 | Ceph |
| 관련 릴리스 | v20.2.0 Tentacle (2025-11-18) |
| 최초 구현 | ceph/ceph#57535 — Adding support for ceph mgmt-gateway (029b4ea1, 2024-07-10 머지) |
| HA 보완 | ceph/ceph#59982 — Adding HA support for mgmt-gateway and oauth2-proxy services (bd0160de, 2024-10-24 머지) |
| 발견 출처 | Tentacle v20.2.0 Release Notes의 Cephadm mgmt-gateway 항목 |
| 검증 근거 | PR #57535/#59982 설명과 실제 diff(services/mgmt_gateway.py, NGINX templates, monitoring service 연동, mgmt-gateway.rst) |
| 소스 라이선스 | 코드 기본값 LGPL-2.1 또는 LGPL-3.0, doc/*는 CC BY-SA 3.0 (COPYING 기준) |
Ceph Tentacle은 Dashboard, Prometheus, Grafana, Alertmanager처럼 서로 다른 host/port에 흩어진 관리 서비스를 NGINX 기반 mgmt-gateway 뒤로 모았다. 사용자는 TLS가 종료되는 단일 endpoint로 접속하고, 내부 Ceph 서비스도 특정 monitoring daemon을 직접 가리키는 대신 gateway의 내부 endpoint를 사용한다. 여기에 여러 gateway의 active/standby virtual IP와 여러 stateless oauth2-proxy 인스턴스를 결합해, 단일 진입점이 새 단일 장애점이 되지 않도록 했다.
Cephadm은 placement spec에 따라 Prometheus, Grafana, Alertmanager 같은 daemon을 여러 host에 배치할 수 있다. 그러나 producer가 여러 인스턴스를 실행하는 것과 consumer가 자동 failover하는 것은 별개다. 기존 Dashboard 설정은 dashboard set-prometheus-api-host 같은 명령으로 monitoring endpoint 하나를 저장했다. PR #57535의 문제 설명에 따르면 여러 daemon이 있어도 마지막에 구성된 하나를 선택했고, 그 daemon이 내려가면 다른 정상 인스턴스로 자동 전환하지 못했다.
사용자도 각 서비스가 어느 host/port에 배치됐는지 알아야 했다. Dashboard와 monitoring UI는 서로 다른 URL과 TLS 설정을 가질 수 있고, SSO를 적용하려면 서비스마다 인증 경계를 맞춰야 한다. cephadm이 daemon을 재배치하거나 active mgr가 바뀔 때 endpoint 설정을 다시 계산하고 관련 daemon을 재시작하는 연쇄도 생긴다.
NGINX의 upstream은 같은 역할을 하는 backend 여러 개를 한 논리 그룹으로 묶는다. client는 proxy 주소만 알면 되고, proxy가 정상 backend를 골라 요청을 전달한다. 외부 사용자용 server와 cluster 내부 service용 server를 분리하면, 둘에 다른 인증·인증서·경로 정책을 적용하면서 backend 목록은 공유할 수 있다.
단, proxy 하나만 두면 backend 장애는 숨겨도 proxy 자체가 single point of failure가 된다. 그래서 "backend HA"와 "gateway HA"를 따로 설계해야 한다.
[변경 전]
사용자 ─────────────▶ Dashboard host:port
사용자 ─────────────▶ Grafana host:port
Dashboard
├─ 저장된 Prometheus endpoint ─────▶ Prometheus #2 (한 인스턴스)
└─ 저장된 Alertmanager endpoint ───▶ Alertmanager #1
Prometheus #1, #3가 정상이어도 #2가 실패하면
Dashboard가 자동으로 다른 인스턴스를 선택하지 못한다.
daemon 재배치 / mgr failover
→ endpoint 재설정
→ monitoring daemon 재구성·재시작 가능
PR #57535는 cephadm service registry에 MgmtGatewayService를 추가하고, daemon cache에서 Dashboard·Prometheus·Grafana·Alertmanager endpoint 전체를 수집해 NGINX template에 넘긴다. main template은 서비스별 upstream 그룹을 만들고 외부/내부 server 설정을 include한다.
- 외부 server는 기본적으로 TLS를 종료하고
/,/grafana,/prometheus,/alertmanager를 각 upstream으로 proxy한다. Dashboard 경로에는proxy_next_upstream조건도 설정해 timeout과 5xx 응답에서 다른 backend를 시도한다. - 내부 server는 별도 port와 내부 인증서를 사용하고
/internal/prometheus같은 경로를 제공한다. Dashboard가 monitoring daemon을 직접 가리키지 않고 이 내부 endpoint를 사용하도록 설정 경로도 바뀌었다.
외부 사용자 경계에는 나중에 인증·인가 같은 처리를 넣을 수 있고, 내부 서비스 통신에는 별도 TLS 정책을 적용할 수 있다. 실제로 Tentacle에서는 oauth2-proxy와 결합해 OIDC/OAuth 2.0 기반 중앙 인증과 SSO를 적용할 수 있다.
최초 PR은 NGINX upstream으로 Dashboard/monitoring backend의 장애를 숨겼지만, NGINX와 oauth2-proxy 자체는 한 인스턴스라 여전히 단일 장애점이었다. PR #59982는 이 경계를 다음처럼 보완했다.
mgmt-gateway여러 개를 active/standby로 배치하고,ingressservice의keepalive_only모드와 동일한virtual_ip를 사용해 활성 gateway를 전환한다.oauth2-proxy는 상태를 gateway에 두지 않는 여러 인스턴스로 배치하고, NGINX가 upstream에서 round-robin으로 분산한다.- gateway 인증서의 IP 목록에 daemon 주소뿐 아니라 virtual IP도 포함해 failover 뒤에도 같은 TLS endpoint를 사용할 수 있게 한다.
- 내부 서비스는 개별 gateway daemon 주소가 아니라 virtual IP의 internal endpoint를 사용하므로 gateway 전환을 알 필요가 없다.
기존에는 active mgr가 바뀌면 Prometheus 등이 service discovery 주소 변경을 반영하려고 다시 구성되거나 재시작될 수 있었다. HA 보완은 모든 mgr의 service discovery endpoint를 NGINX upstream으로 만들고, monitoring service가 gateway의 안정적인 내부 주소를 보게 한다. active endpoint 변경을 consumer 재설정 문제에서 proxy의 backend 선택 문제로 바꾼 것이다.
MgmtGatewayService.get_dependencies()도 Prometheus·Alertmanager·Grafana·oauth2-proxy daemon과 port, mgr 목록을 dependency로 계산한다. backend topology가 실제로 변할 때 gateway 설정을 다시 생성하되, consumer 쪽 endpoint는 유지하는 경계가 생겼다.
Dashboard와 각 monitoring component가 서로의 replica 탐색·health check·failover를 구현하게 하면 조합마다 로직이 중복된다. NGINX upstream에 이 책임을 모으면 cephadm은 backend 목록만 생성하면 되고, 사용자와 내부 client는 안정적인 URL 하나만 사용한다. 대신 모든 관리 트래픽에 proxy hop이 하나 늘고, NGINX 설정 오류의 영향 범위가 Dashboard와 monitoring stack 전체로 넓어진다.
단일 gateway는 접근성과 보안을 단순화하지만 장애 도메인을 집중시킨다. Ceph는 gateway 자체는 keepalived 기반 active/standby virtual IP로, 인증 proxy는 여러 stateless 인스턴스와 NGINX round-robin으로 풀었다. 두 component의 상태 특성이 다르기 때문에 같은 복제 전략을 억지로 쓰지 않은 것이다. 대가로 mgmt-gateway spec과 ingress spec의 virtual IP·placement를 일관되게 관리해야 한다.
외부 listener는 사용자 TLS와 인증/SSO를 담당하고, 내부 listener는 Dashboard·Prometheus 같은 component 사이 통신을 담당한다. 하나의 listener와 URL namespace로 합치면 설정은 짧아지지만, 사용자 인증 실패와 내부 service 통신 실패가 같은 경로에 묶이고 인증 정책을 예외 처리하기 어렵다. 두 server를 둔 설계는 설정 파일과 인증서 관리가 늘어나는 대신 외부 identity boundary와 cluster-internal routing boundary를 명확히 한다.
[변경 후]
virtual IP
사용자 / API client ─────────┬───────────────┐
▼ │ failover
mgmt-gateway A mgmt-gateway B
(ACTIVE, NGINX) (STANDBY)
│ external TLS
├─ / ───────────────▶ Dashboard upstream
├─ /grafana ────────▶ Grafana upstream
├─ /prometheus ─────▶ Prometheus upstream
└─ oauth2 auth ─────▶ oauth2-proxy replicas
Dashboard / Prometheus 등 내부 consumer
│ 동일 virtual IP의 internal listener
▼
/internal/prometheus, /internal/service-discovery
│
├─ backend daemon 장애 → NGINX가 다른 upstream 선택
└─ active mgr 변경 → consumer URL 유지, upstream만 변경
- active/standby gateway 전환과 장시간 Dashboard session 또는 OAuth callback 사이에는 어떤 사용자 체감 경계가 남을까?
- service discovery 외에 mgr failover 때 consumer 재시작을 유발하는 endpoint 의존성을 같은 내부 proxy 패턴으로 더 줄일 수 있을까?
- gateway가 관리 plane 전체의 공통 경계가 된 만큼, 설정 검증과 canary reload를 어떤 수준까지 cephadm이 자동화해야 할까?
- Ceph v20.2.0 Tentacle Release Notes — mgmt-gateway, monitoring HA, oauth2-proxy, certmgr 릴리스 설명
- ceph/ceph#57535 — Adding support for ceph mgmt-gateway — 기존 endpoint failover 문제, 외부/내부 NGINX server 설계와 최초 구현 diff
- ceph/ceph#59982 — Adding HA support for mgmt-gateway and oauth2-proxy — virtual IP, keepalived, oauth2-proxy replica, service discovery proxy 보완
- Ceph mgmt-gateway 문서 — 현재 배치 spec과 HA 구성
- Ceph COPYING — 코드와 문서의 파일별 라이선스 범위
본문 참고 자료로 충분했다.