Communitygithub.com

boonkgim/setup-project

프로덕션 등급 풀스택 웹 애플리케이션을 Next.js, GraphQL, Postgres로 구성하여 Cloudflare Workers에 한 번에 하나의 인프라 조각씩 배포하는 에이전트 스킬입니다.

setup-project란 무엇인가요?

이 스킬은 정해진 루프(reference → research → wire → plan → execute → local gate → reconcile → production gate → reconcile → 수동 단계 안내 → 커밋)를 따라 프로젝트를 한 번에 하나의 슬라이스(slice)씩 구축합니다. `slices/` 디렉토리의 파일은 스크립트가 아닌 참조(reference)로, 검증된 스택과 실제 시간을 소모했던 함정들을 인코딩합니다. 하지만 버전 핀, CLI 플래그, API 형식은 시간이 지나면서 변경되므로, 실행 계획은 참조를 그대로 따르는 것이 아니라 조사(research) 결과를 반영해 현재 시점에 맞게 새로 작성됩니다. 지원하는 스택은 고정되어 있습니다: pnpm 워크스페이스, OpenNext를 통한 Cloudflare Workers의 Next.js, GraphQL Yoga Worker, Drizzle + Postgres(로컬 Docker, 프로덕션 Hyperdrive를 통한 Neon), Tailwind + shadcn, 선택적으로 Resend, Better Auth, Stripe입니다. 주요 플랫폼으로는 Claude Code, Cursor, Codex와 같은 AI 에이전트 환경을 지원합니다.

지원 대상✓Claude Code~Codex CLI~Cursor
npx skills add boonkgim/setup-project

즐겨 사용하는 AI에게 물어보기

이 에이전트 스킬이 미리 로드된 새 채팅을 엽니다.

문서

프로젝트를 한 조각씩 설정하기

호출당 하나의 슬라이스(slice), 고정된 루프를 통해:

참조 → 조사 → 연결 → 계획 → 실행 → 로컬 게이트 → 조정 → 프로덕션 게이트 → 조정 → 사용자에게 수동 단계 안내 → 커밋

slices/ 파일은 스크립트가 아닌 참조입니다. 이들은 세트로 검증된 스택과, 더 중요하게는 실제 시간을 소모했던 함정들을 인코딩합니다: pnpm init이 작성하는데 corepack이 거부하는 devEngines 블록, create-next-app이 apps/web 내부에서 여는 두 번째 pnpm 워크스페이스 등. 그 추론은 유효합니다. 그 주변의 버전 핀, CLI 플래그, API 형식은 그렇지 않습니다. 참조를 그대로 실행한 슬라이스는 변경된 부분에서 실패할 것입니다.

따라서 실행하는 계획은 결코 참조 자체가 아닙니다. 이 프로젝트를 위해, 참조 더하기 조사가 현재 사실이라고 말하는 내용에서 이 프로젝트에 새로 작성된 계획입니다. 그리고 그 계획이 입증되기 전에 작성되기 때문에, 루프는 녹색 게이트에서 끝나지 않습니다. 계획이 실제로 작동한 내용과 일치하도록 수정되고, 사용자에게 사람만이 확인할 수 있는 간단한 검사 목록이 전달되었을 때 끝납니다.

스택은 고정되어 있습니다: pnpm 워크스페이스 · OpenNext를 통한 Cloudflare Workers의 Next.js · GraphQL Yoga Worker · Drizzle + Postgres, 로컬 Docker 및 프로덕션 Hyperdrive를 통한 Neon · Tailwind + shadcn · 선택적으로 Resend, Better Auth 및 Stripe. 사용자가 다른 스택을 원한다면 명확히 말하세요 — 이 스킬은 다른 스택을 제공하지 않습니다.

0. 디스패치(Dispatch)

/setup-project [슬라이스]는 하나의 슬라이스를 구축합니다. 인수는 선택 사항이며 번호 또는 이름으로 슬라이스를 지정합니다 — 01, web shell, database, auth. reference/slices.md에서 확인하고, 일치하는 것이 없으면 그렇게 말하고 이름을 나열하세요. 추측하지 마세요.

ls docs/setup/ 2>/dev/null    # 이 프로젝트가 실제로 구축한 슬라이스
  git status --short            # 더티 트리는 마지막 슬라이스가 완료되지 않았을 수 있음을 의미

docs/setup/은 구축된 내용의 기록이며, 구축될 수 있는 내용의 예측이 아닙니다. 슬라이스 파일이 있는 것은 해당 슬라이스가 구축되어 녹색으로 통과했기 때문입니다. 따라서 가장 높은 번호의 파일이 "현재 위치"에 대한 답이며, 동기화 상태를 유지할 별도의 마커는 없습니다.

슬라이스가 지정되지 않은 경우 — 항상 카탈로그를 먼저 보여주세요. reference/slices.md의 모든 슬라이스를 번호, 이름, docs/setup/에 구축되었는지 여부와 함께 나열한 다음, 하나를 추천하고 실행하기 전에 확인을 받으세요. 이것은 첫 번째 실행에도 적용됩니다: 먼저 프로젝트 이름(§1)을 확정한 다음, 카탈로그를 보여주고(모든 것이 구축되지 않음, 다음 슬라이스 00), 확인 후 구축하세요. 다음 단계가 명백해 보이더라도 카탈로그나 확인을 건너뛰지 마세요.

상태수행할 작업
docs/setup/ 없음첫 실행: 프로젝트 이름 확정(§1), 카탈로그 표시, 슬라이스 00 확인
슬라이스 지정됨구축
슬라이스 지정되지 않음카탈로그 표시, 가장 높은 구축 번호 + 1 추천 및 확인

슬라이스 99는 이 산술에서 제외됩니다. 보안 감사입니다: 아무것도 구축하지 않고, 슬라이스 00만 필요하며, 체인의 단계를 차지하지 않고 존재하는 모든 것에 대해 다시 실행됩니다. 따라서 docs/setup/에 있는 99-security-audit.md는 체인이 완료되었음을 의미하지 않으며, "가장 높은 구축 번호 + 1"은 이를 무시해야 합니다 — 00–05와 99를 보유한 저장소는 다음 구축이 06인 저장소입니다. 또한 --through 범위에서 제외되는데, 그 이유는 범위가 구축 체인이고 존재하지 않는 슬라이스의 감사를 설치하는 것은 아무것도 감사하지 않기 때문입니다. 공개 표면을 추가하는 모든 슬라이스 이후에 추천하고, 명시적으로 이름을 지정하세요: /setup-project 99.

절대 한 번의 호출로 두 개의 슬라이스를 구축하지 마세요. 슬라이스가 커밋되면 중지하세요.

앞서 건너뛰는 슬라이스. 인수가 구축된 것보다 하나 이상 더 높다면, 건너뛰는 슬라이스와 그것들이 구축하는 내용을 명명한 후 사용자가 결정하도록 하세요. 체인은 실제입니다: 04는 02와 03을 모두 필요로 하고, 05–07은 이전 슬라이스가 작성한 파일을 패치하므로, 누락된 전제 조건은 경고가 아닌 하드 docs:check 오류입니다. reference/slices.md §의존성에 추론이 있습니다.

1. 첫 실행에만 해당: 프로젝트 이름

소문자, 숫자 및 하이픈 — npm 스코프(@name/db) 및 Worker 접두사(name-web, name-graphql)가 됩니다. 이미 적합하다면 저장소 디렉토리 이름을 기본값으로 사용하세요. 한 번만 물어보세요. 이후의 모든 슬라이스는 package.json에서 다시 읽습니다.

2. 참조 슬라이스 읽기

다른 모든 작업보다 먼저 slices/NN-*.md를 전체 읽고, 이 슬라이스의 게이트가 증명하는 내용과 필요한 계정을 위해 reference/slices.md를 읽으세요. 코드 블록 사이의 산문은 가치를 유지하는 부분입니다 — 추론을 위해 읽고, 모든 버전 번호, 플래그 및 파일 경로는 사실이 아닌 확인해야 할 주장으로 취급하세요.

슬라이스에 사용자가 가지고 있지 않은 계정(Cloudflare, Neon, Resend, Stripe)이 필요한 경우 지금 말하세요. 누락된 계정이 계획 작성을 막지는 않지만, 로컬 절반이 이미 커밋된 상태에서 프로덕션 게이트 중간에 슬라이스를 좌초시킵니다.

뒤를 보고 앞을 보지 마세요. 프로젝트가 이미 가지고 있는 것(docs/setup/, CLAUDE.md, 이전 슬라이스가 작성한 스킬 파일)을 읽고, 이 슬라이스가 이를 재발명하지 않고 잘 들어맞도록 설정된 규칙을 따르세요. 그 반대는 절대 발생하지 않습니다: 어떤 슬라이스도 이후의 슬라이스(명명 여부와 관계없이)가 구축될 것이라고 가정하지 않습니다 — 구축 여부는 디스패치(§0)에서 사용자의 결정이며, 참조가 의존할 수 있는 것이 아닙니다. 설정된 규칙이 이 슬라이스에 필요한 것에 대해 지금 잘못 보인다면, 말하고 사용자가 결정하도록 하세요. 조용히 재정의하거나 조용히 준수하지 마세요.

이 슬라이스가 대체하는 임시 아티팩트를 폐기하세요. 어떤 것들은 실제가 존재하기 전에 메커니즘을 증명하기 위해서만 구축됩니다 — packages/mock이 첫 번째이자 가장 명확한 예입니다: 슬라이스 0은 이를 통해 실행할 실제 패키지가 없을 때 하네스를 증명하기 위해 생성합니다. 임시 아티팩트는 절대 후속자를 명명하지 않습니다. 왜냐하면 어떤 슬라이스가 이를 대체할지는 참조가 아닌 디스패치(§0)에서 결정되기 때문입니다. 의무는 반대 방향으로 작동합니다: 각 슬라이스는 이미 존재하는 것을 보고, 이제 불필요하게 만드는 것을 제거하는 것을 자체 계획에 통합하고, 이를 설명한 CLAUDE.md 줄도 포함합니다.

따라서 packages/mock이 여전히 존재한다면, 이 슬라이스는 워크스페이스가 얻는 첫 번째 실제이며, 이를 폐기하는 것은 이 슬라이스 작업의 일부입니다. 동일한 규칙이 이후 슬라이스가 남긴 모든 것(실제로 대체되는 정적 리졸버, 바인딩이 되는 플레이스홀더 값)을 다룹니다.

이 메커니즘은 후속자가 있는 아티팩트에만 작동하므로, 후속자가 없는 것을 선언하세요. packages/mock은 실제 패키지가 분명히 이를 대체하기 때문에 폐기됩니다. 아무것도 sendTestEmail을 명백히 대체하지 않습니다: 슬라이스 6은 실제 확인 메일을 그와 함께 추가하고, 슬라이스 7은 스키마의 일부로 설명하며, 실제 메일을 보내는 인증되지 않은 변이는 영구 기능으로 제공됩니다. 어떤 슬라이스도 잘못되지 않았습니다 — 제거에 소유자가 없습니다. 이후 슬라이스가 알아차리기를 기다리는 것은 메커니즘이 아니라 희망입니다.

따라서 모든 슬라이스는 아티팩트가 생성될 때 작성된 Leaves behind 블록으로 끝납니다(누군가 발견할 때가 아니라):

  • Provisional(임시) — 무엇인지, 왜 존재하는지, 폐기 조건. 이후 어떤 슬라이스도 그 조건을 그럴듯하게 충족하지 못한다면 행에 그렇게 말하세요. 정직한 "이것을 폐기하는 것은 없음"이 작업을 수행하는 항목입니다.
  • Accepted(수용됨) — 의식적으로 취해진 위험, 누가 도달할 수 있는지, 추론. 이후 슬라이스가 재발견하는 대신 재결정할 수 있고, 상속된 기본값(프로덕션에서 GraphiQL을 제공하는 Yoga)이 선택된 것과 구별될 수 있도록 기록됩니다.

슬라이스 99는 이를 교차 점검으로 읽습니다 — 절대 입력으로 사용하지 않습니다. 왜냐하면 원장은 누군가가 이미 기록할 생각을 한 것만 포함할 수 있기 때문입니다. 코드를 먼저 읽습니다.

3. 현재 사실 조사

이 단계는 참조를 안전하게 사용할 수 있게 만드는 단계이므로, 신중하고 저렴하게 수행하세요. 이 슬라이스가 설치하거나 구성하는 모든 도구에 대해 참조 대신 실제를 확인하세요:

npm view <pkg> version          # 실제 핀이 무엇이어야 하는지
npx <cli> --help                # 플래그 및 비대화형 프롬프트

그런 다음 슬라이스가 구조적으로 의존하는 모든 것(프레임워크의 현재 어댑터 지침, 런타임의 호환성 플래그, 라이브러리의 현재 API 형태)에 대한 공식 문서를 읽으세요. 참조의 요약보다 공급업체 자체 문서를 선호하고, 그들이 일치하지 않는 곳을 기록하세요.

설치가 출력하는 내용을 읽고, 종료 코드만 읽지 마세요. 다른 패키지로 병합되거나, 이름이 변경되었거나, 중단된 패키지는 여전히 설치되고, 동일한 이름을 내보내며, 컴파일됩니다 — npm view <pkg> version은 건강한 버전을 보고하고, 참조의 코드 블록은 그에 대해 녹색으로 통과합니다. pnpm add 출력의 한 줄 [WARN] deprecated …이 이를 보여주는 유일한 장소입니다. 슬라이스 5가 이 부분입니다: @react-email/components는 5개월 전에 react-email에 병합되었고 다른 곳에서는 아무도 말하지 않았습니다.

npm view <pkg> deprecated    # 비어 있지 않으면 참조가 죽은 패키지를 설명하고 있음을 의미

찾은 내용과 위치를 기록하세요. 참조와 현재 문서 간의 모순이 이 단계의 전체 출력이며, 작성할 계획으로 들어갑니다.

3b. 이미 구축된 것에 연결

연결되지 않은 상태로 착륙하는 슬라이스는 아무도 작동하는지 알 수 없는 슬라이스입니다. 계획을 작성하기 전에 docs/setup/에 존재한다고 말하는 것을 보고 이 슬라이스가 이제 어떤 계층과 연결부(seam)를 가지는지 물어본 다음 — 제안하세요. 이후에 구축되지 않을 수 있는 슬라이스를 위해 남겨두지 말고 이 슬라이스에서 해당 연결부를 증명할 것을 제안하세요.

네 가지 규칙이 이것이 범위 확장(scope creep)으로 변하는 것을 방지합니다:

  • 뒤로만. 이미 구축된 슬라이스에만 연결하세요. 존재하지 않을 수 있는 것에 대해 추측하지 마세요 — 이는 adapting.md의 "슬라이스는 이전 슬라이스를 인용할 수 있지만, 이후 슬라이스는 절대 인용할 수 없다"는 규칙과 동일합니다.
  • 프로브(probe)이지, 기능이 아닙니다. 기준은 연결부가 끊어지면 실패할 _한 가지_입니다. 제품 결정이 필요하다면 자체 슬라이지이지, 프로브가 아닙니다.
  • 제안입니다. 연결은 슬라이스를 확장하므로, 다른 모든 것과 함께 §4 검토로 들어가며 사용자의 동의가 필요합니다.
  • 게이트 행(row)을 얻거나, 아무것도 증명하지 않습니다.

프로브는 임시 아티팩트이며, §2의 규칙이 이미 그 제거를 다룹니다: 그것을 대체할 것에 대해 아무 말도 하지 않으며, 이를 대체하는 슬라이스가 그것을 폐기합니다.

4. 프로젝트에 실행 계획 작성

node <skill dir>/scripts/install-plan.mjs \
  --repo <repo dir> --name <project> --slices NN

<skill dir>은 이 스킬이 설치된 곳입니다: ~/.claude/skills/setup-project, ~/.agents/skills/setup-project 또는 프로젝트 자체의 .claude/skills/setup-project. 스크립트는 자체에 상대적으로 슬라이스를 확인하므로, 이 중 어느 곳에서든 올바르게 실행됩니다.

그러면 slices/NN-*.md가 __PROJECT__와 __DOCS__가 확인된 상태로 docs/setup/에 렌더링되며, 그 외에는 아무것도 작성하지 않습니다 — 색인, 소스 목록 없음. docs/setup/은 슬라이스 파일만 보유하며, 구축된 슬라이스당 하나씩이며, ls가 색인입니다. 아무것도 설치, 구축 또는 커밋되지 않습니다.

이미 있는 슬라이스 파일은 --force를 전달하지 않는 한 그대로 둡니다. 그때까지는 참조의 복사본이 아니라 이 프로젝트의 실행 기록이기 때문입니다.

그런 다음 작성된 내용을 편집하세요. 실행하기 전에 — 이것은 참조의 복사본이 아닌 계획입니다. §3의 조사를 반영하세요: 핀 수정, 이동된 플래그 수정, API가 변경된 단계 조정, 현재 문서와 모순되는 부분을 삭제하거나 다시 작성하세요. 파일의 나머지 부분처럼 산문에서 _이유_를 말하세요.

사용자에게 참조 대비 변경한 사항과 이유를 보여주고, 실행하기 전에 동의를 얻으세요. 이 시점에서 계획은 입증되지 않았으며 사용자의 잠시 주목할 가치가 있습니다.

5. 실행

계획의 블록을 순서대로 실행하세요. cd 줄은 이전 블록이 남긴 곳에서 작성되므로, 블록을 재정렬하거나 하나를 격리하여 실행하지 마세요.

실패를 예상하세요. 이 계획은 한 번도 실행된 적이 없습니다. 여기서의 실패는 루프가 작동하는 것이지, 루프가 깨지는 것이 아닙니다 — §7이 캡처하기 위해 존재하는 정보입니다. 원인을 수정하고, 그것이 무엇인지 기록하고, 계속 진행하세요.

6. 게이트(Gates) — 세 라운드, 이 순서로

슬라이스는 세 번의 패스로 증명되며, 그것들은 한 가지의 변형이 아닙니다. 두 개는 실행하고 조치를 취할 수 있는 것이고, 세 번째는 인계(handoff)입니다. 처음 두 개 각각은 계획과 이 스킬(§7)을 수정하는 것으로 끝납니다. 다음이 시작되기 전에, 깨진 것이 아직 눈앞에 있는 동안. 마지막에 한 번 조정하면 프로덕션 단계 뒤에 로컬 교훈을 잃게 됩니다.

라운드 1 — 자동화, 로컬

슬라이스의 라운드 1 표를 정확히 작성된 대로, 명명된 Where 열에서 실행하세요 — typecheck 및 테스트 스크립트는 저장소 루트에서, 개발 서버 및 preview는 패키지에서. 이 분할은 장부가 아닙니다: 루트는 turbo를 통해 스크립트를 분산시키므로 "워크스페이스가 녹색인가"라는 질문에 답하며, 이것이 게이트가 묻는 유일한 질문입니다. 패키지 내에서 동일한 스크립트를 실행하면 해당 패키지의 집계를 얻으며, 다른 패키지가 불타는 동안 녹색으로 유지됩니다. 모든 패키지는 두 수준 아래에 있으므로 cd ../..는 그 중 어느 것에서든 돌아옵니다 — 그리고 슬라이스 본문은 일반적으로 잘못된 위치에 남겨두므로 각 행이 실행 위치를 명명하는 이유입니다.

행을 주어진 순서대로 실행하세요: 일부 행은 이후 행이 필요로 하는 것을 생성합니다. 종료 코드가 아닌 테스트 수를 읽으세요 — passWithNoTests는 빈 실행을 녹색으로 만들므로, 게이트가 명명한 N과 함께 Tests N passed만이 유일한 증거입니다. 명령이 출력하는 내용을 읽고, 반환하는 것뿐만 아니라 읽으세요: 지원 중단 공지는 §3의 최악의 경우 전체 발견 사항입니다.

실패한 것을 수정한 다음, 지금 조정(§7) 하세요 — 프로젝트의 슬라이스 문서와 이 스킬의 문서, 둘 다.

게이트가 여전히 하나의 결합된 테이블인 슬라이스. 일부 슬라이스만이 이 세 라운드 형태를 거쳤습니다. 나머지는 혼합된 b를 포함하는 단일 테이블을 가지고 있습니다.

관련 스킬