Skip to content

fix: 1GB 인스턴스(프리티어)에서 배포·기동이 가능하도록 - #131

Merged
RosieOh merged 1 commit into
mainfrom
feat/free-tier-deploy
Sep 26, 2026
Merged

RosieOh merged 1 commit into
mainfrom
feat/free-tier-deploy

Conversation

@RosieOh

@RosieOh RosieOh commented Sep 26, 2026

Copy link
Copy Markdown
Contributor

Closes #130

측정 (같은 이미지·같은 DB)

조건 결과
제한 없음 (기존) 858MB — 호스트 전체의 75%를 힙으로 계산
--memory=512m + 기존 기본값 OOM 종료 (exit 137)
--memory=512m + 새 기본값 기동 성공 464MB (91%)
--memory=640m + 새 기본값 기동 성공 520MB → 부하 후 575MB (90%)

1GB 배분: 앱 520575 + MariaDB 96 + Redis 9 + OS/Docker 150200 = 약 800MB. 여유 200MB 라 스왑 2GB 필수(문서에 명령 포함).

변경

내용
배포 예비 컨테이너 검증 → 교체 후 실패 시 롤백. JVM 2개(≈1.3GB)는 1GB 에서 불가능하다. 순단 20~40초를 받아들이고, 되돌릴 대상은 태그가 아니라 이미지 ID (같은 태그가 덮여도 정확히 이전 버전)
JVM MaxRAMPercentage 75→55, MaxMetaspaceSize=192m, G1→SerialGC. 힙 밖이 150MB 가까워 70%면 한도를 넘긴다. vCPU 1~2개에서 G1 백그라운드 스레드는 부담
이미지 1.25GB → 686MB. JDK→JRE, chown -R 의 156MB JAR 중복 복사 제거, 스프링 부트 레이어 분리(재배포 시 애플리케이션 레이어 수 MB 만 pull)
DB 풀 운영 20/10 → 8/2. 커넥션마다 DB 가 버퍼를 잡아 앱 몫을 가져간다
compose 같은 한도를 로컬에도 적용. 제한이 없으면 개발 PC 에서만 잘 뜨고 운영에서만 죽는다
MariaDB/Redis 버퍼풀 96M·performance_schema off / maxmemory 48mb·noeviction(리프레시 토큰이 들어 있어 내보내면 로그아웃이 깨진다)
문서 프리티어 절 신설 — 측정 표, 스왑 명령, MariaDB·Redis 준비 명령(기존 문서에 없었다), CPU 크레딧·디스크 주의

JDK 를 뺀 것에 대해

원래 JDK 베이스는 운영 중 jcmd·jstack 을 위한 의도된 선택이었다. 그건 버리지 않고 같은 PID 공간에 JDK 컨테이너를 붙이는 방법으로 대체하고 문서에 명령을 적었다.

docker run --rm --pid=container:carecode eclipse-temurin:17-jdk-jammy jcmd 1 VM.native_memory

확인

  • 새 이미지로 --memory=512m/640m 기동 + /facilities·/policies·공개 통계 200, 동시 요청 120건 후에도 안정
  • compose 전체 기동 확인(앱 520MB/640m, MariaDB 96MB/320m, Redis 9MB/64m)
  • 전체 584 tests, 실패 0, skip 0

남는 제약 (프리티어에서도 동일)

업로드 파일이 로컬 디스크, 실시간 알림 연결이 인스턴스 메모리 — 한 대 전제다 (#49).

실측으로 확인한 문제 세 가지를 고친다. 모두 같은 이미지·같은 DB 로 측정했다.

  제한 없음(현재 설정)      858MB 사용  ← 호스트 전체의 75%를 힙으로 계산한다
  --memory=512m + 예전 설정  OOM 종료(137)
  --memory=512m + 새 설정    464MB 기동 성공
  --memory=640m + 새 설정    520MB → 부하 후 575MB

1) 배포 중 JVM 두 개
   예비 컨테이너로 먼저 검증한 뒤 교체하던 방식은 1GB 에서 불가능하다(JVM 2개 ≈ 1.3GB).
   "교체 → 실패 시 이전 이미지로 롤백" 으로 바꿨다. 되돌릴 대상은 태그가 아니라 이미지 ID 라,
   같은 태그가 새 이미지로 덮여도 정확히 이전 버전으로 돌아간다. 순단 20~40초를 받아들인다.

2) JVM 기본값
   MaxRAMPercentage 75 → 55, MaxMetaspaceSize 192m, G1 → SerialGC.
   힙 밖(메타스페이스·스레드·코드캐시)이 150MB 가까이 되므로 70%면 한도를 넘겨 죽는다.
   vCPU 1~2개에서는 G1 의 백그라운드 스레드가 부담이다. 배포 시 --memory 를 함께 건다(기본 640m,
   서버 .env 의 APP_MEMORY 로 조정).

3) 이미지 1.25GB → 686MB
   JDK → JRE, chown -R 이 156MB JAR 을 레이어에 한 번 더 복사하던 것 제거,
   스프링 부트 레이어 분리(재배포 때 애플리케이션 레이어 수 MB 만 받는다).
   JDK 를 뒀던 이유(jcmd·jstack)는 JDK 컨테이너를 같은 PID 공간에 붙이는 방법으로 대체하고 문서에 적었다.

그 외
- 운영 DB 풀 20/10 → 8/2. 커넥션마다 DB 가 버퍼를 잡아 앱 몫을 가져간다.
- compose 에도 같은 한도를 건다. 제한이 없으면 개발 PC 에서만 잘 뜨고 운영에서만 죽는다.
- MariaDB 96M 버퍼풀·performance_schema off, Redis 48mb·noeviction(토큰이 들어 있어 내보내면 안 된다).
- 운영 문서: 측정 표, 스왑 2GB, MariaDB·Redis 준비 명령(문서에 아예 없었다), CPU 크레딧·디스크 주의.
@RosieOh
RosieOh merged commit fcf4499 into main Sep 26, 2026
7 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[ 인프라 ] 1GB 인스턴스에서는 지금 설정으로 배포가 불가능하다

1 participant