feat: Implement Pipeline Templates for Company Suite and refine orchestration logic
This commit is contained in:
@@ -0,0 +1,211 @@
|
||||
/**
|
||||
* Built-in pipeline templates for 1인 기업 모드.
|
||||
*
|
||||
* These are *blueprints*, not data — they're surfaced in the manage panel's
|
||||
* "템플릿에서 추가" dropdown so a non-developer user can stamp out a
|
||||
* working pipeline in one click and then tweak the labels / 지시 / agent
|
||||
* assignments in the card editor. Once stamped, the pipeline lives in
|
||||
* `state.pipelines` like any other; templates themselves stay read-only in
|
||||
* code so a future Astra version can ship improved defaults without
|
||||
* trampling user edits.
|
||||
*
|
||||
* Why ship a template at all: the user's own description of the desired
|
||||
* workflow ("작업 수락 → 기획 → 시장 조사 → … → QA → 배포") is exactly the
|
||||
* shape this codifies. Without the template they'd have to author 13
|
||||
* cards from scratch the first time they open the editor — which is
|
||||
* exactly the friction we're trying to remove.
|
||||
*/
|
||||
import { PipelineDef } from './types';
|
||||
|
||||
export interface PipelineTemplate {
|
||||
/** Stable id used by the UI dropdown and `applyTemplate` call. */
|
||||
templateId: string;
|
||||
/** Korean display name shown in the dropdown. */
|
||||
name: string;
|
||||
/** One-line description of when this template fits. */
|
||||
description: string;
|
||||
/**
|
||||
* Default pipeline id when stamping. The UI will suggest this and let
|
||||
* the user override before saving so two stamps don't collide.
|
||||
*/
|
||||
suggestedPipelineId: string;
|
||||
/** Default human-readable name for the stamped pipeline. */
|
||||
suggestedPipelineName: string;
|
||||
/** Stage definitions — same shape as a saved PipelineDef.stages. */
|
||||
stages: PipelineDef['stages'];
|
||||
}
|
||||
|
||||
/**
|
||||
* "풀 프로덕트 개발" — the user's described workflow, codified:
|
||||
* 1. 작업 수락 — CEO 브리프 (자동, 별도 stage 아님)
|
||||
* 2. 기획 논의 — planner
|
||||
* 3. 시장 조사 — researcher
|
||||
* 4. 트렌드 조사 — researcher
|
||||
* 5. 방향성 정의 — planner
|
||||
* 6. 기획문서 작성 — planner
|
||||
* 7. 기획문서 검토 — inspector (재작업 발견 시 → 6번 loop-back)
|
||||
* 8. 기획문서 최종본 — planner
|
||||
* 9. 개발 설계 — developer
|
||||
* 10. 설계 검토 — inspector (재작업 발견 시 → 9번 loop-back)
|
||||
* 11. 개발 진행 — developer
|
||||
* 12. QA 진행 — qa (버그 발견 시 → 11번 loop-back)
|
||||
* 13. 라이브 배포 — developer
|
||||
*
|
||||
* 1번 "작업 수락"은 별도 stage가 아니라 CEO의 브리프 발신 — 모든 pipeline
|
||||
* turn은 자동으로 brief를 생성해 `{{brief}}` 토큰으로 사용 가능하다.
|
||||
*
|
||||
* 지시 템플릿은 작은 LLM이 가장 자주 어기는 두 가지 — (a) 기획 문맥 잊기,
|
||||
* (b) 단순 코드만 던지기 — 를 강하게 누른다. 사용자가 처음 보면 길어
|
||||
* 보일 수 있는데, "이 단계에서 정확히 뭘 해야 하나" 가이드가 필요한
|
||||
* 작은 모델 (gemma e2b·4b 등)에서 결과 품질을 크게 좌우한다.
|
||||
*/
|
||||
const FULL_PRODUCT_DEV: PipelineTemplate = {
|
||||
templateId: 'full-product-dev',
|
||||
name: '풀 프로덕트 개발 (13단계)',
|
||||
description: '기획 → 리서치 → 기획서 → 검토 → 설계 → 개발 → QA → 배포. 기획 누락 없이 풀 사이클을 도는 표준 워크플로.',
|
||||
suggestedPipelineId: 'product-dev',
|
||||
suggestedPipelineName: '제품 개발 파이프라인',
|
||||
stages: [
|
||||
{
|
||||
id: 'plan-discuss',
|
||||
label: '기획 논의',
|
||||
agentId: 'writer',
|
||||
roleCategory: 'planner',
|
||||
instructionTemplate:
|
||||
'사용자 요청: {{userPrompt}}\n\n' +
|
||||
'이번 작업의 목표·사용자·성공 기준을 정리하세요. 결정 사항이 아니라 *논의 정리* 단계입니다.\n' +
|
||||
'- 누구를 위한 결과물인가\n- 핵심 가치 한 줄\n- 우리가 모르는 것 / 더 알아봐야 할 것\n- 위험 요소',
|
||||
},
|
||||
{
|
||||
id: 'market-research',
|
||||
label: '시장 조사',
|
||||
agentId: 'researcher',
|
||||
roleCategory: 'researcher',
|
||||
instructionTemplate:
|
||||
'기획 논의 정리: {{stage.plan-discuss}}\n\n' +
|
||||
'위 맥락에서 *시장 측면*을 조사하세요. 추측 금지, 데이터/사례 기반.\n' +
|
||||
'- 비슷한 시도가 이미 있나 (3개 이상)\n- 시장 크기·고객 페르소나\n- 가격대·수익화 패턴\n결과는 "출처(또는 일반론임을 명시)" 표시.',
|
||||
},
|
||||
{
|
||||
id: 'trend-research',
|
||||
label: '트렌드 조사',
|
||||
agentId: 'researcher',
|
||||
roleCategory: 'researcher',
|
||||
instructionTemplate:
|
||||
'기획 논의: {{stage.plan-discuss}}\n시장 조사 결과: {{stage.market-research}}\n\n' +
|
||||
'*최근 트렌드*를 조사하세요. 6개월 이내 변화를 우선.\n' +
|
||||
'- 떠오르는 키워드/패턴\n- 사용자 기대치 변화\n- 우리가 활용할 수 있는 기술/문화 신호',
|
||||
},
|
||||
{
|
||||
id: 'direction',
|
||||
label: '방향성 정의',
|
||||
agentId: 'writer',
|
||||
roleCategory: 'planner',
|
||||
instructionTemplate:
|
||||
'기획 논의: {{stage.plan-discuss}}\n시장: {{stage.market-research}}\n트렌드: {{stage.trend-research}}\n\n' +
|
||||
'위 3개를 종합해 *우리가 갈 방향*을 한 문단으로 결론지어요.\n포함:\n' +
|
||||
'- 무엇을 만들 것인가 (제품 한 줄 설명)\n- 누가 첫 사용자인가\n- 안 만들 것 (out of scope)\n- 성공 판단 기준 1~3가지',
|
||||
},
|
||||
{
|
||||
id: 'plan-draft',
|
||||
label: '기획문서 초안',
|
||||
agentId: 'writer',
|
||||
roleCategory: 'planner',
|
||||
instructionTemplate:
|
||||
'방향성: {{stage.direction}}\n\n' +
|
||||
'이 방향에 맞는 *기획서 초안*을 마크다운으로 작성하세요.\n' +
|
||||
'필수 섹션:\n' +
|
||||
'## 배경\n## 목표\n## 핵심 사용자 시나리오 (3개 이상, 구체적)\n## 주요 기능 목록\n## 비기능 요구사항\n## 측정 지표 (KPI)\n## 미래 확장 / 비-목표\n\n' +
|
||||
'아직 *최종본 아님* — 검토자가 피드백 줄 수 있도록 가정·미확정 사항을 명시하세요.',
|
||||
},
|
||||
{
|
||||
id: 'plan-review',
|
||||
label: '기획문서 검토',
|
||||
agentId: 'inspector',
|
||||
roleCategory: 'inspector',
|
||||
instructionTemplate:
|
||||
'검토 대상: {{stage.plan-draft}}\n\n' +
|
||||
'*감리* 관점에서 기획서를 검토하세요. 칭찬 X, 구체적 피드백 O.\n' +
|
||||
'확인 사항:\n- 시나리오가 구체적인가 ("사용자가 X를 한다" vs "사용자가 잘 쓴다")\n' +
|
||||
'- 기능 vs 시나리오 매핑이 1:1로 되는가\n- 측정 가능한 성공 기준이 있는가\n- 빠진 케이스/엣지 케이스\n\n' +
|
||||
'결론은 반드시 "✅ 승인" 또는 "❌ 재작업 필요: <항목 나열>" 로 시작.',
|
||||
loopBackPattern: '재작업 필요|reject|보완 필요',
|
||||
loopBackTo: 'plan-draft',
|
||||
maxIterations: 3,
|
||||
},
|
||||
{
|
||||
id: 'plan-final',
|
||||
label: '기획문서 최종본',
|
||||
agentId: 'writer',
|
||||
roleCategory: 'planner',
|
||||
instructionTemplate:
|
||||
'초안: {{stage.plan-draft}}\n검토 피드백: {{stage.plan-review}}\n\n' +
|
||||
'피드백을 모두 반영해 *최종 기획서*를 다시 쓰세요. 다음 단계(개발 설계)에서 그대로 사양서로 쓸 정도로 명확해야 합니다.',
|
||||
},
|
||||
{
|
||||
id: 'dev-design',
|
||||
label: '개발 설계',
|
||||
agentId: 'developer',
|
||||
roleCategory: 'developer',
|
||||
instructionTemplate:
|
||||
'최종 기획서: {{stage.plan-final}}\n\n' +
|
||||
'이 기획서 기준으로 *개발 설계 문서*를 작성하세요. 아직 코드는 쓰지 않습니다.\n' +
|
||||
'포함:\n## 데이터 모델\n## 컴포넌트/모듈 분할\n## 외부 의존성\n## 단계별 구현 순서 (체크리스트)\n## 테스트 전략\n## 알려진 리스크',
|
||||
},
|
||||
{
|
||||
id: 'design-review',
|
||||
label: '설계 검토',
|
||||
agentId: 'inspector',
|
||||
roleCategory: 'inspector',
|
||||
instructionTemplate:
|
||||
'설계 문서: {{stage.dev-design}}\n기획서: {{stage.plan-final}}\n\n' +
|
||||
'설계가 기획 의도를 모두 커버하는지 *감리*하세요. 누락된 시나리오·과도한 over-engineering이 있나.\n' +
|
||||
'결론은 "✅ 승인" 또는 "❌ 재작업 필요: ..." 로 시작.',
|
||||
loopBackPattern: '재작업 필요|reject|보완 필요',
|
||||
loopBackTo: 'dev-design',
|
||||
maxIterations: 2,
|
||||
},
|
||||
{
|
||||
id: 'dev-impl',
|
||||
label: '개발 진행',
|
||||
agentId: 'developer',
|
||||
roleCategory: 'developer',
|
||||
instructionTemplate:
|
||||
'설계: {{stage.dev-design}}\n기획서: {{stage.plan-final}}\n\n' +
|
||||
'설계대로 *실제 코드를 작성*하세요. 반드시 ConnectAI 액션 태그(`<create_file>`, `<edit_file>`, `<run_command>`)를 사용해 디스크에 떨어지도록.\n' +
|
||||
'코드 블록만 보여주고 "생성 완료"라고 말하면 디스크엔 아무것도 안 만들어집니다. 작성 후 자가 검증 한 줄.',
|
||||
},
|
||||
{
|
||||
id: 'qa',
|
||||
label: 'QA 진행',
|
||||
agentId: 'qa',
|
||||
roleCategory: 'qa',
|
||||
instructionTemplate:
|
||||
'구현 결과: {{stage.dev-impl}}\n기획서: {{stage.plan-final}}\n\n' +
|
||||
'*테스트 시나리오를 직접 실행*해 기능을 검증하세요. 케이스별로 PASS/FAIL 명확히 적고, 실패 시 재현 방법을 적어요.\n' +
|
||||
'결론은 "✅ 모든 케이스 통과" 또는 "❌ 버그 발견: ..." 로 시작 (loop-back regex가 이걸 봅니다).',
|
||||
loopBackPattern: '버그 발견|❌|버그|오류|실패',
|
||||
loopBackTo: 'dev-impl',
|
||||
maxIterations: 4,
|
||||
},
|
||||
{
|
||||
id: 'deploy',
|
||||
label: '라이브 배포',
|
||||
agentId: 'developer',
|
||||
roleCategory: 'developer',
|
||||
instructionTemplate:
|
||||
'QA 통과 결과: {{stage.qa}}\n\n' +
|
||||
'배포 절차를 *실행*하세요. README 갱신, 버전 태깅, 배포 스크립트 실행 등 필요한 명령은 `<run_command>` 로.\n' +
|
||||
'마지막에 배포된 상태 요약과 사용자에게 안내할 한 줄 (📝 다음).',
|
||||
},
|
||||
],
|
||||
};
|
||||
|
||||
/** Read-only registry of templates the UI surfaces. Add more here later. */
|
||||
export const PIPELINE_TEMPLATES: PipelineTemplate[] = [
|
||||
FULL_PRODUCT_DEV,
|
||||
];
|
||||
|
||||
export function getPipelineTemplate(id: string): PipelineTemplate | undefined {
|
||||
return PIPELINE_TEMPLATES.find((t) => t.templateId === id);
|
||||
}
|
||||
Reference in New Issue
Block a user