getpersona.md를 시작하며 — AI 에이전트용 페르소나 플랫폼, Day 1 Foundation
getpersona.md는 AI 코딩 에이전트와 팀에게 말투·성향·판단 기준·지식 경계를 구조화해서 전달하는 PERSONA.md 플랫폼입니다. getdesign.md가 “AI에게 디자인 감각을 주는 DESIGN.md 컬렉션”이라면, getpersona.md는 “AI에게 페르소나를 주는 PERSONA.md 컬렉션”을 목표로 합니다. 오늘은 카탈로그나 결제 UI 같은 겉모습은 거의 없습니다. 대신 모노레포, 제품 계약서, 디자인 시스템, SEO/AEO/GEO 골격까지 — 나중에 후회하지 않을 Foundation만 쌓았습니다.
왜 이 프로젝트를 시작했나
에이전트를 쓰다 보면 반복되는 문제가 있습니다.
- 시스템 프롬프트는 대화마다 날아갑니다
- “이번엔 좀 더 formal하게” 같은 지시는 버전 관리·검증·공유가 안 됩니다
- 팀에서 같은 페르소나를 쓰려면 누가 무엇을 바꿨는지 추적이 어렵습니다
- 공식/영감/고위험 도메인 같은 신뢰·안전 라벨을 UI로 일관되게 보여줄 곳이 없습니다
getpersona.md는 이걸 버전 있는 패키지(PERSONA.md, persona.json, memory cards, permissions)와 런타임으로 풀려고 합니다.
카탈로그에서 고르고 → 워크스페이스에 넣고 → 태스크에 맞는 context를 받고 → Codex/Claude/Cursor로 export — 이 루프가 제품의 중심입니다.
계획은 어떻게 잡았나
1) 로드맵을 “기능 목록”이 아니라 TASK 단위로 쪼갬
planning/implementation-roadmap.md에 80개가 넘는 TASK를 milestone별로 정리해 두었습니다.
각 TASK는 대략 3시간짜리 한 MR이 되도록 크기를 제한합니다.
원칙:
- Foundation(모노레포, auth, DB, 디자인, CI) → 그다음 product UI
- Launch 1 / Launch 2 경계를 문서로 고정 (크리에이터 정산·�ayout은 Launch 2)
- UI TASK는
DESIGN.md필수, 런타임/결제 TASK는 테스트·감사 로그 필수
2) VibeOps + Cursor로 “채팅”이 아니라 문서가 진실의 원천
워크플로:
vibeops task add → TASK md 읽고 구현 → task ship (MR) → merge → 다음 TASK
한 번에 하나의 TASK, 하나의 �ranch, 하나의 MR.
에이전트와 사람이 같이 일할 때 “어제 채팅에서 뭐라고 했더라?” 문제를 줄이려는 선택입니다.
3) PRODUCT_CONTRACT.md — 제품의 헌법
README는 엔지니어 온보딩, 로드맵은 일정, **계약서는 “뭘 만들고 뭘 안 만드는지”**만 담습니다.
예: Launch 1에는 Polar로 getPersona 소유 상품 결제만.
크리에이터 수익 분배 UX는 의도적으로 제외.
처음 시작할 때 고민해야 할 것들 (내가 실제로 고민한 것)
A. 프로토타입 vs 프로덕션
선택: 처음부터 프로덕션 품질.
이유: 페르소나·결제·고위험 라벨은 “나중에 고치자”가 신뢰 사고로 이어지기 쉽습니다.
그래서 오늘 health page 하나만 있어도:
- strict TypeScript
- shared package로 workspace linking 검증
- lint / typecheck / build를 root에서 통과
B. UI를 먼저 vs Foundation을 먼저
선택: Foundation first.
대안: 카탈로그 목업부터 → 빠른 데모는 가능하지만, auth/DB/결제 붙일 때 전면 재작업 위험이 큼.
C. 마케팅 랜딩 vs 유용한 디렉터리
getDesign.md에서 배운 점: 공개 surface는 히어로 마케팅 페이지보다 쓸모 있는 catalog가 낫다.
getpersona.md도 Milestone 12에서 persona directory + GitHub trust + npx getpersona 루프를 계획 중.
그래서 SEO/AEO/GEO도 “랜딩 카피”가 아니라 FAQ + llms.txt + JSON-LD 중심으로 잡았습니다.
D. Launch 1 결제 범위
선택: Polar, getPersona-owned 상품만.
미룬 것: 크리에이터 marketplace, PayPal payout, “페르소나로 돈 벌기” UX — 법·세무·분쟁 대응 게이트 전까지는 코드로도 노출하지 않음.
E. AI 에이전트와 함께 일 때의 문서 전략
DESIGN.md— UI 계약 (에이전트가 hex를 임의로 넣지 못하게)docs/tasks/TASK-NNN-*.md— 작업 범위·Acceptance Criteriadocs/project/06-decisions.md— D-001, D-002… 결정 로그
기술 스택 — 선택과 대안 비교
모노레포
| 선택 | 대안 | 왜 이쪽 |
|---|---|---|
pnpm + Turborepo | npm/yarn workspaces, Nx | pnpm disk 효율·속도, Turborepo는 dev/build 캐시가 단순하고 팀 규모에 맞음 |
Nx | 기능은 강력하지만 foundation 단계엔 과한 설정 비용 | |
단일 Next full-stack | Nest runtime·MCP·장기 API 분리에 불리 |
오늘 상태: apps/web, apps/api, packages/shared, packages/db — web↔api health 연동까지 확인.
Frontend
| 영역 | 선택 | 대안 | 비고 |
|---|---|---|---|
Framework | Next.js 16 App Router | Remix, Vite+SPA | RSC·SEO·디렉터리형 public surface에 유리 |
UI | Tailwind v4 + shadcn/ui | CSS Modules, MUI, Chakra | DESIGN.md 토큰과 1:1 매핑, 컴포넌트 소유권 |
Motion | Framer Motion | CSS only | reduced-motion 대응 helper로 통제 |
Design contract | root DESIGN.md | Figma-only, Storybook-first | getdesign.md와 동일 철학 — 에이전트가 읽는 UI 스펙 |
Font (wordmark) | Geist Pixel Square | Inter only | getdesign.md 로고와 동일 계열; 본문은 Inter |
오늘 상태: /design 프리뷰, health page 디자인 시스템 적용, getpersona.md 워드마크 (persona 노란색 accent).
Backend
| 선택 | 대안 | 왜 |
|---|---|---|
NestJS 11 | Hono, Fastify raw, tRPC-only | 모듈 경계·OpenAPI·MCP/장기 서비스 확장 |
Better Auth (Nest) | Auth.js 단독, Clerk, Supabase Auth | self-hosted·GitLab CI·Infisical과 맞는 자체 통제 |
OpenAPI | schema-first 없음 | public MCP·외부 연동 대비 |
오늘 상태: GET /health + shared/db stub import로 workspace wiring 검증.
Data
| 선택 | 대안 | 왜 |
|---|---|---|
PostgreSQL + Drizzle | Prisma, Kysely, Supabase DB only | SQL 친화·migration·타입; Prisma는 무겁고 ESLint/TS edge case 관리 부담 |
Redis (planned) | 없음 | cache/queue — TASK-010 |
Toolchain (오늘 올린 버전)
| Component | Version | 메모 |
|---|---|---|
Node | 24 LTS | Active LTS |
pnpm | 11.9 | corepack pin |
TypeScript | 6.0 | strict, ignoreDeprecations on API where needed |
ESLint | 10 | web는 root flat config (eslint-plugin-react 호환 이슈) |
Vitest | 4.1 |
솔직한 트레이드오ff: 최신 스택은 생태계 lag이 있습니다. ESLint 10 + Next 공식 config 조합은 아직 매끄럽지 않아 root flat ESLint로 우회했습니다. “최신”과 “안정” 사이에서 타입·빌드 통과를 기준으로 결정했습니다.
Infra & Commerce (planned, 문서에만 고정)
| 영역 | 선택 | 대안 |
|---|---|---|
CI/CD | Self-hosted GitLab | GitHub Actions — org 인프라와 일치 |
Secrets | Infisical | .env only, Vault |
Storage | MinIO (S3) | Cloudflare R2 |
Launch 1 billing | Polar | Stripe Billing, Lemon Squeezy — 초기 subscription + dev-friendly |
오늘 실제로 ship한 것 (Foundation Day 1)
TASK-001 · Monorepo bootstrap
- pnpm + Turborepo, web
:3100/ api:3101 - health dashboard + API health fetch
pnpm dev/lint/typecheck/build
TASK-002 · Product contract + README
PRODUCT_CONTRACT.md— pillars, Launch 1/2, non-goals- 엔지니어 onboarding README (GitLab SSH
:2222, VibeOps)
TASK-003 · DESIGN.md + UI foundation
- organization design.md 토큰 verbatim + getPersona extension
- Tailwind v4
@theme, shadcn-style primitives, Framer Motion /design스타일 프리뷰
그 외 오늘 손댄 것
- SEO / AEO / GEO: sitemap, robots.txt (Content-Signal),
llms.txt, FAQ + JSON-LD pnpm dev:stop— 포트 점유 정리- 브랜드: getdesign.md 스타일 워드마크 (Geist Pixel,
persona노란 accent)
아직 없는 것 (의도적으로)
- Auth, DB migration, catalog UI
- CI pipeline (GitLab runner 이슈로 merge는 수동 진행)
- Polar live 연동
npx getpersonaCLI
다음 TASK 후보: TASK-004 (DB wiring), TASK-005 (OpenAPI), TASK-006 (app shell + TanStack Query)…
마치며 — Day 1에서 배운 것
- 에이전트와 제품을 같이 만들려면 “문서가 API”다.
DESIGN.md, PRODUCT_CONTRACT, TASK md 없이 UI부터 그리면 매 MR마다 방향이 흔들립니다. - getDesign.md의 교훈을 그대로 가져올 수 있다.
DESIGN.md → PERSONA.md, catalog-first, llms.txt, GitHub contribution loop. - Foundation이 지루해 보여도 공개 블로그에는 남길 가치가 있다.
health page 하나지만, 그 아래엔 80+ TASK 로드맵과 Launch 경계가 있습니다.
다음 글 예고 (후보)
- TASK-004: Drizzle + PostgreSQL — schema-first로 persona package를 DB에 어떻게 모델링할지
- Better Auth on NestJS — session을 web/api/MCP가 어떻게 공유할지
- Polar mock mode — Launch 1 checkout를 credentials 없이 어떻게 테스트할지