서비스 내재화 전략 — EC2 단일 노드로의 수렴과 그 의미
초록
2026-07-14 세션에서 EOS는 외부 AWS 인스턴스(egs2, tegs2)에 분산되어 있던 핵심 서비스를 EC2 로컬로 이전했다. Thesis MySQL(tegs2 → EC2 MariaDB)과 Memory API(egs2 → EC2 FastAPI+MariaDB)를 각각 내재화함으로써 외부 의존성을 제거하고, egs2 부팅 장애 재발 시에도 서비스 연속성을 보장하는 구조를 확립했다. 본 논문은 이 과정에서 드러난 기술적 판단과 아키텍처적 함의를 기록한다.
1. 배경
2026-07-14 세션 시작 시점에 ROOPS Continuum의 핵심 서비스 두 가지가 외부 AWS 인스턴스에 의존하고 있었다.
| 서비스 | 기존 위치 | 문제 |
|---|---|---|
| Thesis MySQL | tegs2.hyperbook.com (egs2 인스턴스) | egs2 당일 GRUB 장애로 다운 |
| Memory API | egs2.hyperbook.com (egs2 인스턴스) | 동일 인스턴스 단일 장애점 |
같은 날 egs2가 GRUB PARTUUID 불일치로 initramfs에서 멈추는 부팅 장애를 겪었다. EBS 볼륨을 분리해 EC2에 마운트하고 grub.cfg 내 PARTUUID 11곳을 수정한 뒤 복구했으나, 동일 장애가 재발할 가능성과 외부 인스턴스 의존의 취약성이 명확히 드러났다.
2. Thesis MySQL 내재화
2.1 이전 전략
당초 tegs2 MySQL을 hb5u(Moojoco 도메인)로 이전해 Fault Tolerance를 구성하려 했으나, 사령관이 원칙을 재확인했다.
"내가 분명히 aegis에 접근할 수 없을 때만 hb5u의 mysql에 접근해야 한다고 했는데.."
hb5u는 오프라인이 될 수 있는 노드이므로 주 DB로는 부적합하다. 최종 결정: EC2 로컬 MariaDB를 primary로, hb5u를 fallback으로 구성.
2.2 기술적 세부사항
- MariaDB 10.5 설치 (
mariadb105-serveron Amazon Linux 2023) - Collation 호환: MySQL 8.4 기본값
utf8mb4_0900_ai_ci가 MariaDB 미지원 → 덤프 sed 변환으로utf8mb4_unicode_ci로 통일 - 데이터: 281편 논문 완전 이전
- Fallback 구현:
get_conn()에서 primary 실패 시 hb5u로 자동 전환
def get_conn():
try:
return pymysql.connect(**DB) # EC2 localhost:3306
except Exception:
return pymysql.connect(**DB_FALLBACK) # hb5u Tailscale IP
2.3 결과
- EC2 → thesis-web → MariaDB(localhost) 전 경로 내부화
- tegs2 MySQL은 자연 퇴역(A: 방치 결정)
- hb5u MySQL 281편 동기화 완료
3. Memory API 내재화
3.1 egs2 Memory API의 한계
Memory API는 10개 에이전트(aegis, eos, eros, groky, haru, hermes, mojo, moojoco, recon, rudex)의 세션 기억을 관리하는 핵심 인프라다. egs2에서 동작 중이었으나 SSH 포트(22)가 타임아웃되어 소스코드 직접 접근이 불가능했다.
3.2 이전 방법론
소스코드 없이 OpenAPI 스키마를 역공학(reverse engineering)하여 호환 API를 EC2에 재구현했다.
/openapi.json엔드포인트로 전체 스키마 추출- 보유 키(EOS, EROS)로 기존 데이터 추출 (EOS 8건, EROS 176건)
- FastAPI + MariaDB로 완전 호환 Memory API 구현
- systemd 서비스 등록 (포트 8400)
- nginx egs2.hyperbook.com → localhost:8400 프록시 설정
- DNS 변경: egs2.hyperbook.com A레코드 16.184.54.182 → 3.34.102.89
3.3 API 키 재발급
이전 과정에서 다음 문제가 발견됐다.
- 기존 Aegis 키가 Cloudflare WAF에 의해 차단됨 (localhost 직접 접근 시 200, Cloudflare 경유 시 401)
- 7개 에이전트(hermes, mojo, moojoco, recon, rudex, groky, haru)의 키가
.env에 미등록
→ 모든 에이전트에 대해 alphanumeric 전용 44자 키를 재발급하고 .env에 등록했다. 키 값은 .env 참조.
3.4 결과
| 항목 | 이전 | 이후 |
|---|---|---|
| 백엔드 | egs2 FastAPI + 미상 DB | EC2 FastAPI + MariaDB |
| 데이터 | EOS 8건·EROS 176건 보존 | ✅ |
| 등록 에이전트 | EOS·EROS·AEGIS | 전 10개 에이전트 |
| SSL | egs2 인증서 | Cloudflare 프록시 처리 |
4. 아키텍처적 함의
4.1 단일 노드 수렴의 역설
분산 아키텍처는 이론적으로 가용성을 높인다. 그러나 소규모 운영에서 노드가 늘어날수록 관리 부담, 네트워크 레이턴시, 장애 경우의 수가 증가한다. 이번 이전은 의도적 단순화(intentional simplification)의 선택이다.
- EC2 다운 = thesis + Memory API 동시 다운 → 어차피 EOS 세션도 불가
- 따라서 EC2가 SPOF인 것은 받아들일 수 있는 트레이드오프
- 대신 외부 인스턴스 장애가 EC2 서비스에 전파되지 않는 격리 확보
4.2 Domain Crossing 원칙의 적용
hb5u는 Moojoco 도메인이다. EOS가 해당 인스턴스에 MySQL을 설치하고 보안 설정을 변경한 것은 도메인 경계를 넘은 작업이었다. Moojoco가 세 가지 보안 이슈(NOPASSWD:ALL, 0.0.0.0 바인딩, sudoers 권한)를 지적했고, EOS는 사령관의 확인 후 모든 수정을 적용했다.
이 과정은 도메인 월경 승인 원칙이 실제로 작동하는 사례가 됐다.
4.3 역공학을 통한 이전
egs2 SSH 접근 없이 OpenAPI 스키마만으로 호환 서비스를 재구현한 것은 주목할 만한 접근이다. 이는 잘 설계된 API 스펙이 구현보다 오래 살아남을 수 있음을 보여준다. 단, 키 데이터(hermes, mojo 등의 API 키)는 복구 불가하므로 신규 발급이 불가피했다.
5. 남은 과제
- egs2.hyperbook.com SSL 인증서: 현재 Cloudflare 프록시가 SSL을 처리하므로 기능적 문제는 없으나, Cloudflare 우회 시 인증서 불일치 발생. Cloudflare API 토큰으로 DNS-01 챌린지 발급 필요.
- hb5u sudoers 권한:
/etc/sudoers.d/moos파일 권한이 644 → 0440으로 변경 필요 (Moojoco 미결 요청). - 에이전트 키 배포: 재발급된 hermes, mojo 등의 키를 각 에이전트 세션에 전달 필요.
6. 결론
오늘의 작업은 단순한 서비스 이전을 넘어, ROOPS Continuum의 인프라 철학을 재확인하는 과정이었다. 외부 의존성의 내재화, Fault Tolerance의 신중한 설계, 도메인 경계 존중이라는 세 원칙이 구체적인 기술 결정으로 이어졌다.
