Checkout은 지웠지만 배포는 남아 있었다
프런트엔드에서 houkago.posts와 생성 파일 의존성을 제거한 뒤에도 글을 push하면 Vercel Production
deployment가 만들어졌다. 두 GitHub Actions workflow가 과거 구조를 유지하고 있었기 때문이다.
Blog workflow는 두 repository를 checkout해 콘텐츠를 검증하고 Vercel CLI로 prebuilt artifact를 올렸다. Posts workflow도 공개 결과에 영향이 있다고 판단하면 같은 배포를 실행했다. 정적 구조에서는 글이 프런트엔드 빌드 결과물의 입력이었으므로 필요한 연결이었다. 하지만 API에서 데이터를 읽는 구조로 전환한 뒤에는 애플리케이션을 다시 빌드할 이유가 없었다.
Data dependency 제거 O
Build dependency 제거 O
Deployment trigger 분리 X변경 주체별 결과를 다시 정했다
| 변경 | 필요한 결과 |
|---|---|
houkago.posts | 콘텐츠 검증, DB와 자산 갱신, cache freshness |
houkago.blog | Preview 또는 Production 애플리케이션 배포 |
houkago.server | 백엔드 release lifecycle |
최종 trigger는 다음처럼 나눴다.
Posts main push
-> GitHub Actions 콘텐츠 검증
-> 별도로 Webhook과 Content Worker 실행
-> Vercel deployment 없음
Blog branch push
-> Vercel Git Integration
-> main은 Production, 나머지는 Preview콘텐츠 검증과 Webhook은 직렬 승인 절차가 아니다. 같은 push에서 독립적으로 시작한다. 운영 상태 변경 전에는 Worker의 전체 후보 사전 검사가 별도로 실패를 막는다.
기존 배포를 지우기 전에 Vercel 경로를 시험했다
Custom workflow부터 삭제하면 검증된 배포 경로가 사라질 수 있었다. Workflow trigger에 걸리지 않는 임시 branch로 native Vercel Preview를 시험했다.
첫 push에서는 custom Action도, Vercel Preview와 commit status도 모두 생성되지 않았다. 삭제를 멈추고 Project와 Git 저장소 연결, GitHub App 접근 권한, Production branch, 서버 측 환경 변수와 Project Git 설정을 점검했다.
Integration과 저장소 접근 권한을 복구한 뒤 새 점검 branch를 push하자 같은 commit SHA의 Preview가 READY가
됐고 실행 환경 점검도 통과했다. 빌드 로그에는 Posts checkout과 검증, POSTS_REPO_PATH, 생성 파일이
없었다. 최초 실패 당시 설정 화면은 증거로 남지 않아 특정 checkbox 하나를 원인으로 단정하지 않았다.
Blog 배포 owner를 하나로 만들었다
Preview를 확인한 뒤 210줄의 .github/workflows/deploy-with-posts.yml을 삭제했다. 이 workflow가 맡던 dual
checkout과 Posts tooling, Vercel CLI build와 main·dev 분기는 더 이상 독립된 Blog CI 책임이 아니었다.
삭제 commit의 main push에서는 source=git, target=production, READY인 Vercel 배포가 정확히 한 건
생겼다. Commit SHA도 일치했고 custom GitHub Action은 0건이었다. Production에서 목록과 분류, 상세, 검색,
Sitemap, 자산, unknown 상세 404와 revalidation 인증 실패 계약을 확인했다.
Posts에는 검증만 남겼다
Blog native path를 확정한 뒤 Posts repository에서 다음을 제거했다.
- 135줄의
deploy-blog.yml - Public-impact detector와 전용 test
- Blog checkout과 Vercel CLI 경로
Commit 전체로는 476줄을 지우고 README와 package script 5줄을 바꿨다. 반면
content-validation.yml은 유지했다. Ubuntu와 macOS, Windows에서 npm ci와 npm run check를 실행해 원본
형식과 tooling을 검증한다.
Actions 검증은 저장소 품질 신호이고 Worker 사전 검사는 운영 상태 변경 경계다. 배포 제거가 원본 검증 제거를 뜻하지 않는다.
실제 Posts push로 분리를 확인했다
Workflow 삭제 commit을 main에 push했을 때 콘텐츠 경로는 계속 동작했다.
Webhook 202
-> checkout FF-only 갱신
-> 자산 stage와 DB sync
-> 자산 활성화와 API smoke
-> cache 무효화 200
Vercel Preview 0
Vercel Production 0당시 333개 자산, 8,087,458바이트의 generation이 활성화됐다. 동기화 결과는 CREATED=0, UPDATED=0,
TOUCHED=277, DELETED=0이었다. TOUCHED=277은 공개 글 수가 아니라 후보가 이미 같은 상태였다는 뜻이다.
App과 MySQL restart count도 늘지 않았다.
이 commit은 글 본문 변경이 아니므로 새 글 발행 evidence로 사용하지 않았다. 콘텐츠 경로는 실행되면서 프런트엔드 artifact는 만들지 않았다는 trigger separation만 확인했다.
Revalidation과 deployment는 다른 동작이다
Deployment는 새 프런트엔드 code로 application artifact를 만들고, revalidation은 이미 배포된 application의 백엔드 기반 cache를 비운다. Local consumer가 모두 사라졌기 때문에 콘텐츠 변경에는 후자만 필요했다.
Cache 무효화가 실패해도 DB와 자산 publication을 되돌리지 않는다. Manual retry와 300초 TTL이 별도 복구 경계로 남는다. 이 구조를 모든 Next.js application에 일반화할 수는 없다. 콘텐츠가 build 입력이라면 여전히 deployment가 필요하다.
분리 뒤에도 Vercel Integration과 Content Worker를 각각 관찰해야 한다. GitHub App 연결은 저장소 밖의 설정이고, 오래된 배포용 비밀값과 hook 자격 증명의 생명주기도 별도 정리가 필요했다.
얻은 경계는 명확했다. 글 revision은 DB와 공개 자산, cache freshness만 바꾸고 프런트엔드 code revision만 Vercel application deployment를 만든다. 자동화의 실행 계기를 분리한 것이며, 그 안의 desired state가 항상 정확히 수렴하는지는 별도의 문제로 남았다.