@su-record/vibe 2.8.47 → 2.8.48

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@su-record/vibe",
3
- "version": "2.8.47",
3
+ "version": "2.8.48",
4
4
  "description": "AI Coding Framework for Claude Code — 56 agents, 45 skills, multi-LLM orchestration",
5
5
  "type": "module",
6
6
  "main": "dist/cli/index.js",
@@ -18,6 +18,37 @@ Figma 트리가 코드의 원천이다. 스크린샷은 검증용이다.
18
18
  ✅ 스크린샷은 생성이 아닌 검증에만 사용
19
19
  ```
20
20
 
21
+ ## ⛔ 불변 규칙 (이 규칙을 위반하면 전체 결과물이 무효)
22
+
23
+ ```
24
+ 이 규칙들은 어떤 상황에서도 예외 없이 적용된다.
25
+ "복잡해서", "시간이 없어서", "렌더링이 안 돼서" 등의 이유로 우회할 수 없다.
26
+
27
+ 1. screenshot 명령으로 콘텐츠를 이미지화하는 것은 금지한다.
28
+ screenshot 명령의 허용 범위:
29
+ ✅ BG 프레임 렌더링 (TEXT 자식이 없는 순수 배경)
30
+ ✅ 벡터 글자 GROUP 렌더링 (웹폰트 없는 장식 타이틀)
31
+ ✅ 섹션별 스크린샷 → sections/ 폴더 (Phase 6 검증용)
32
+ screenshot 명령의 금지 범위:
33
+ ❌ TEXT 자식이 있는 프레임 → HTML로 구현
34
+ ❌ INSTANCE 반복 패턴이 있는 프레임 → HTML v-for로 구현
35
+ ❌ 버튼/가격/수량이 있는 프레임 → HTML로 구현
36
+ ❌ "섹션 콘텐츠"를 통째 렌더링 → HTML로 구현
37
+
38
+ 위반 시 발생하는 문제:
39
+ exchange-section1.webp (카드 4개를 이미지 1장으로) → 가격 수정 불가, 버튼 클릭 불가
40
+ daily-step2-list.webp (보상 목록을 이미지로) → 수량 변경 불가, 접근성 불가
41
+
42
+ 2. BG를 <img> 태그로 넣는 것은 금지한다.
43
+ ❌ <img src="bg.webp"> 또는 <div class="bg"><img src="bg.webp"></div>
44
+ ✅ .section { background-image: url('bg.webp'); background-size: cover; }
45
+
46
+ 3. Phase 4 코드 생성 중 새로운 screenshot 호출은 금지한다.
47
+ Phase 2에서 확보한 재료만 사용한다.
48
+ "이 부분이 복잡하니 screenshot으로 이미지화하자"는 금지된 사고방식이다.
49
+ 복잡한 UI도 tree.json의 구조를 따라 HTML+CSS로 구현한다.
50
+ ```
51
+
21
52
  ## 금지 사항
22
53
 
23
54
  ```
@@ -30,6 +61,22 @@ Figma 트리가 코드의 원천이다. 스크린샷은 검증용이다.
30
61
  ❌ 컴포넌트 파일 안에 <style> 블록 / 인라인 style=""
31
62
  ✅ tree.json의 CSS 속성을 SCSS에 직접 매핑
32
63
  ✅ 외부 SCSS 파일에만 스타일 작성
64
+
65
+ ━━━ 이미지 vs HTML 판별 (가장 흔한 실수) ━━━
66
+
67
+ ❌ BG를 <img> 태그로 처리 → 반드시 CSS background-image
68
+ 잘못된 예: <img src="hero-bg.webp" class="bg-img" />
69
+ 올바른 예: .section { background-image: url('hero-bg.webp'); background-size: cover; }
70
+
71
+ ❌ 카드/아이템 그리드를 통째 이미지 1장으로 렌더링
72
+ 잘못된 예: <img src="exchange-section1.webp" /> (카드 4개가 한 이미지)
73
+ 올바른 예: v-for로 개별 카드 HTML 생성 + 내부 아이콘만 <img>
74
+
75
+ ❌ TEXT 자식이 있는 프레임을 이미지로 렌더링
76
+ 잘못된 예: <img src="daily-step2-list.webp" /> (텍스트+카드 포함)
77
+ 올바른 예: HTML로 텍스트/레이아웃 구현 + 순수 이미지 에셋만 <img>
78
+
79
+ ✅ 이미지로 렌더링 가능한 것: 벡터 글자, 합성 BG(텍스트 미포함), 래스터 에셋, 복잡 벡터
33
80
  ```
34
81
 
35
82
  ## 전체 플로우
@@ -365,15 +412,22 @@ URL에서 fileKey, nodeId 추출
365
412
  node "[FIGMA_SCRIPT]" images {fileKey} {nodeId} --out=/tmp/{feature}/images/ --depth=10
366
413
  → 모든 이미지 에셋 확보. 누락 0건, 0byte 0건.
367
414
 
368
- 3.5단계 — 아이템/아이콘 노드 렌더링 (추가 시각 재료):
369
- tree.json에서 INSTANCE/COMPONENT 타입 중 아이템 후보를 식별:
370
- - name에 "item", "icon", "reward", "token", "coin", "badge" 포함
415
+ 3.5단계 — 개별 에셋 노드 렌더링 (추가 시각 재료):
416
+ tree.json에서 이미지 에셋 후보를 식별:
417
+ - 아이콘: VECTOR/GROUP 크기 64px
418
+ - 아이템 썸네일: name에 "item", "icon", "reward", "token", "coin", "badge"
371
419
  - 크기 50~300px 범위의 독립 요소
372
420
  - fill 이미지가 없지만 시각적으로 의미 있는 노드
421
+
422
+ ⛔ 렌더링 전 TEXT 자식 검증 (BLOCKING):
423
+ 후보 노드의 자식 트리에 TEXT 노드가 있으면 → 렌더링 대상에서 제외
424
+ 후보 노드가 INSTANCE 반복 패턴의 부모이면 → 렌더링 대상에서 제외
425
+ "카드", "리스트", "그리드" 등 복합 UI를 통째 렌더링하지 않는다
426
+
373
427
  해당 노드를 개별 렌더링:
374
428
  node "[FIGMA_SCRIPT]" images {fileKey} {nodeId} --render --nodeIds={id1},{id2},... --out=/tmp/{feature}/images/
375
- → 이미지 fill이 아닌 벡터/인스턴스 에셋도 PNG로 확보
376
- → Phase 3에서 데이터의 image 경로에 연결
429
+ → 이미지 fill이 아닌 벡터/인스턴스 에셋도 webp로 확보
430
+ → Phase 4에서 카드 내부의 아이콘/썸네일로 사용
377
431
 
378
432
  4단계 — 섹션별 스크린샷 (부분 정답):
379
433
  트리의 1depth 자식 프레임 각각:
@@ -645,6 +699,14 @@ Phase 1에서 생성한 빈 SCSS 파일에 기본 내용 Write:
645
699
 
646
700
  섹션 3 (Daily) → ... 반복
647
701
 
702
+ ⛔ Phase 4에서 screenshot/render 호출 금지:
703
+ Phase 2에서 확보한 이미지만 사용한다.
704
+ "이 섹션이 복잡하니 screenshot으로 이미지화하자" → 금지된 접근.
705
+ 복잡한 섹션도 tree.json 구조를 따라 HTML+CSS로 구현한다.
706
+ 섹션 내부에 카드 그리드/보상 목록이 있으면:
707
+ → 카드 내부의 아이콘/썸네일(Phase 2에서 확보)만 <img>
708
+ → 가격, 수량, 버튼 텍스트, 제목은 모두 HTML
709
+
648
710
  각 섹션 완료 시:
649
711
  - 해당 섹션의 컴포넌트 + SCSS가 동작하는 상태
650
712
  - pages/{feature}.vue에 해당 섹션이 추가된 상태
@@ -660,22 +722,42 @@ Phase 1에서 생성한 빈 SCSS 파일에 기본 내용 Write:
660
722
  → Auto Layout 속성(flex, gap, padding)이 코드의 기반
661
723
  → 스크린샷은 검증용으로만 참조
662
724
 
663
- 2. 기계적 매핑 (추정 없음):
664
- a. 이미지 vs HTML 판별 (노드마다 vibe.figma.convert 체크리스트 참조):
665
- - TEXT 자식 있음 HTML (이미지에 텍스트 포함 금지)
666
- - INSTANCE 반복 패턴 → HTML 반복 구조 (내부 이미지 에셋만 추출)
667
- - 인터랙티브 요소 (btn, CTA) HTML <button>
668
- - 동적 데이터 (가격, 기간, 수량) HTML 텍스트
669
- - 위 모두 아님 → 이미지 렌더링 가능
670
- b. 이미지: 판별 통과한 노드만 static/images/{feature}/에 배치
725
+ 2. 이미지 vs HTML 판별 (BLOCKING — 코드 작성 전 반드시 실행):
726
+ 섹션의 모든 노드를 순회하여노드가 이미지인지 HTML인지 판별한다.
727
+ 판별하지 않고 코드를 작성하면 된다.
728
+
729
+ 판별 결과 테이블을 먼저 작성한 코드 생성:
730
+ | 노드 name | 타입 | 판별 | 근거 |
731
+ |-----------|------|------|------|
732
+ | BG | FRAME | CSS background-image | BG 프레임 |
733
+ | Title | TEXT 포함 FRAME | HTML | TEXT 자식 보유 |
734
+ | CardGrid | INSTANCE ×4 | HTML v-for | 반복 패턴 |
735
+ | CoinIcon | RECTANGLE+imageRef | <img> | 순수 에셋 |
736
+
737
+ 판별 규칙 (하나라도 YES → HTML):
738
+ Q1. TEXT 자식 있는가? → YES → HTML (텍스트를 이미지에 넣지 않는다)
739
+ Q2. INSTANCE 반복 패턴인가? → YES → HTML v-for (내부 이미지 에셋만 <img>)
740
+ Q3. 인터랙티브 요소인가? (btn, CTA) → YES → HTML <button>
741
+ Q4. 동적 데이터인가? (가격, 수량, 기간) → YES → HTML 텍스트
742
+ 모두 NO → 이미지 렌더링 가능
743
+
744
+ ⚠️ 특히 주의: 섹션을 통째로 이미지 렌더링하는 것은 절대 금지.
745
+ 섹션 안의 개별 요소를 판별하여 이미지/HTML을 분리해야 한다.
746
+
747
+ 3. 기계적 매핑 (추정 없음):
748
+ a. 이미지: 판별에서 "이미지"로 확정된 노드만 static/images/{feature}/에 배치
749
+ b. BG 프레임 처리:
750
+ ❌ <img src="bg.webp"> 또는 <div><img src="bg.webp" class="bg"></div> 금지
751
+ ✅ 부모에 CSS background-image만 사용:
752
+ .section { background-image: url('/images/{feature}/bg.webp'); background-size: cover; }
753
+ ✅ BG 프레임은 HTML에 아무 요소도 렌더링하지 않음
671
754
  c. 노드 → HTML 매핑:
672
- - BG 프레임 → CSS background-image (img 태그 아님)
673
755
  - Auto Layout 있음 → <div> + flex (direction/gap/padding 직접)
674
756
  - Auto Layout 없음 → <div> + position:relative (자식 absolute)
675
757
  - TEXT 노드 → <span> (Claude가 h2/p/button으로 승격)
676
758
  - 순수 이미지 에셋 → <img src="렌더링된 파일">
677
759
  - 반복 패턴 (동일 구조 2+) → v-for (카드 내 이미지만 <img>, 나머지 HTML)
678
- c. CSS 직접 매핑:
760
+ d. CSS 직접 매핑:
679
761
  - node.css의 모든 속성을 SCSS에 1:1 매핑
680
762
  - vw/clamp 반응형 단위 변환 (vibe.figma.convert 참조)
681
763
  - tree.json에 없는 CSS 값은 작성하지 않음
@@ -11,8 +11,15 @@ tier: standard
11
11
  **Claude는 시맨틱 판단(태그 선택, 컴포넌트 분리, 인터랙션)만 담당한다.**
12
12
 
13
13
  ```
14
+ ⛔ 불변 규칙 — 복잡한 UI도 반드시 HTML로 구현한다:
15
+ "복잡하니까 이미지로 처리하자" → 이 사고방식 자체가 금지.
16
+ 카드 그리드, 보상 목록, 교환소, 가격 표시 → 전부 HTML+CSS.
17
+ <img>는 순수 이미지 에셋(아이콘, 썸네일, 벡터 글자)에만 사용.
18
+ BG는 CSS background-image만 사용. <img> 태그 금지.
19
+
14
20
  ❌ 스크린샷을 보고 CSS 추정 (범용 LLM의 약점)
15
21
  ❌ Figma 레이어를 무분별하게 div soup로 변환
22
+ ❌ 복잡한 섹션을 screenshot으로 이미지화 (코드 생성 중 screenshot 호출 금지)
16
23
  ✅ Figma Auto Layout → CSS Flexbox 1:1 매핑 (기계적)
17
24
  ✅ Figma CSS 속성 → SCSS 직접 변환 (추정 없음)
18
25
  ✅ Claude → 시맨틱 태그 선택 + 컴포넌트 설계 + 인터랙션
@@ -55,11 +62,45 @@ component-index (/tmp/{feature}/component-index.json) 에서 매칭되는 컴포
55
62
  ### 1-1. 노드 → HTML 매핑 규칙 (기계적)
56
63
 
57
64
  ```
65
+ ⛔ 코드 작성 전: 이미지 vs HTML 판별 테이블을 먼저 작성한다 (BLOCKING).
66
+ 섹션의 모든 1~2depth 노드를 순회하여 각각의 처리 방법을 결정.
67
+ 판별 없이 코드를 작성하면 안 된다.
68
+
69
+ 판별 규칙 (순서대로 적용, 하나라도 YES → HTML):
70
+ Q1. 이 노드의 자식 트리에 TEXT 노드가 있는가?
71
+ YES → HTML로 구현 (이미지에 텍스트를 넣지 않는다)
72
+ ※ "가격 1,000", "보상 교환하기", "이벤트 기간" 등이 있으면 무조건 HTML
73
+ Q2. 같은 부모 아래 동일 구조 INSTANCE가 2개 이상인가?
74
+ YES → HTML 반복 구조 (v-for/.map) — 내부 아이콘/썸네일만 <img>
75
+ ※ 카드 4개 그리드를 이미지 1장으로 렌더링하면 절대 안 됨
76
+ Q3. 클릭/인터랙션이 필요한가? (btn, CTA, link, tab)
77
+ YES → HTML <button>/<a>
78
+ Q4. 동적으로 변경되는 데이터인가? (가격, 수량, 기간, 상태)
79
+ YES → HTML 텍스트
80
+ 모두 NO → 이미지 렌더링 가능 (벡터 글자, 래스터 에셋, 합성 BG 등)
81
+
58
82
  각 노드에 대해 아래 규칙을 순서대로 적용:
59
83
 
60
- 1. 타입별 기본 매핑:
84
+ 1. 배경 레이어 (BG 프레임 — 가장 먼저 처리):
85
+ BG 프레임 (name에 "BG"/"bg" 또는 부모와 동일 크기)
86
+
87
+ ❌ 절대 금지 패턴 (이렇게 쓰면 안 됨):
88
+ <img src="hero-bg.webp" class="bg-img" />
89
+ <div class="bg"><img src="bg.webp" /></div>
90
+ position: absolute; inset: 0; → 이미지 배치
91
+
92
+ ✅ 유일하게 허용되는 패턴:
93
+ 부모 요소의 SCSS에 background-image로 처리:
94
+ .heroSection {
95
+ background-image: url('/images/{feature}/hero-bg.webp');
96
+ background-size: cover;
97
+ background-position: center top;
98
+ }
99
+ HTML에는 BG 관련 요소를 아무것도 넣지 않음.
100
+
101
+ 2. 타입별 기본 매핑:
61
102
  TEXT 노드 → <span> (Claude가 <h1>~<h6>, <p>, <button> 등으로 승격)
62
- IMAGE fill → <img src="다운로드된 경로" />
103
+ IMAGE fill → <img src="다운로드된 경로" /> (판별 통과한 순수 에셋만)
63
104
  VECTOR/GROUP → 크기가 작으면(≤64px) 아이콘 후보 → <img> (렌더링 이미지)
64
105
  크기가 크면 장식 요소 → <div> + background
65
106
  FRAME/INSTANCE:
@@ -67,20 +108,21 @@ component-index (/tmp/{feature}/component-index.json) 에서 매칭되는 컴포
67
108
  Auto Layout 없음 → <div> + position:relative (자식은 absolute)
68
109
  children 없음 → 빈 div 또는 스킵
69
110
 
70
- 2. 배경 레이어 판별:
71
- BG 프레임 (name에 "BG"/"bg" 또는 부모와 동일 크기)
72
- ❌ <img> 태그로 배경 처리 금지
73
- ❌ position:absolute + inset:0 으로 이미지 배치 금지
74
- ✅ 부모 요소에 CSS background-image로 처리:
75
- background-image: url('/images/{feature}/{section}-bg.webp');
76
- background-size: cover;
77
- background-position: center top;
78
- ✅ BG 프레임은 HTML에 아무것도 렌더링하지 않음 (CSS만)
79
-
80
111
  3. 반복 패턴 감지:
81
- 같은 부모 아래 동일 타입 + 유사 구조(children 수 동일) 노드 3개 이상
112
+ 같은 부모 아래 동일 타입 + 유사 구조(children 수 동일) INSTANCE 2개 이상
82
113
  → v-for (Vue) 또는 .map() (React)
83
114
  → 첫 번째 노드를 기준으로 템플릿 생성
115
+ → 카드 내부의 이미지 에셋(아이콘, 썸네일)만 <img>
116
+ → 카드 레이아웃, 텍스트, 버튼, 가격은 HTML로 구현
117
+
118
+ ❌ 잘못된 예: <img src="exchange-section1.webp" /> (카드 4개가 한 이미지)
119
+ ✅ 올바른 예:
120
+ <div v-for="card in weeklyCards" :key="card.id" class="card">
121
+ <img :src="card.icon" :alt="card.name" class="card__icon" />
122
+ <span class="card__name">{{ card.name }}</span>
123
+ <span class="card__price">{{ card.price }}</span>
124
+ <button class="card__btn">보상 교환하기</button>
125
+ </div>
84
126
 
85
127
  4. 스킵 대상:
86
128
  크기 0px 노드
@@ -53,6 +53,19 @@ Q4. 이 노드의 콘텐츠가 동적 데이터인가? (가격, 수량, 기간,
53
53
 
54
54
  위 체크에서 하나라도 YES → HTML로 구현
55
55
  모두 NO → 이미지(벡터 글자, BG, 래스터, 복잡 그래픽)로 렌더링
56
+
57
+ 실제 테스트에서 발생한 잘못된 패턴:
58
+
59
+ ❌ <img src="hero-bg.webp" class="bg-img" /> → BG를 img 태그로
60
+ ❌ <img src="exchange-section1.webp" /> → 카드 4개를 이미지 1장으로
61
+ ❌ <img src="daily-step2-list.webp" /> → 보상 목록을 통째 이미지로
62
+ ❌ <img src="hero-period-bg-mo.webp" class="period-bg"> → Period BG를 img로
63
+
64
+ ✅ .heroSection { background-image: url('hero-bg.webp'); background-size: cover; }
65
+ ✅ <div v-for="card in cards" :key="card.id">
66
+ <img :src="card.icon" /> <span>{{ card.price }}</span>
67
+ <button>보상 교환하기</button>
68
+ </div>
56
69
  ```
57
70
 
58
71
  ## CSS 직접 매핑 규칙
@@ -107,6 +120,9 @@ BEM 패턴: `.sectionName__childName`
107
120
 
108
121
  ## 자가 검증 (코드 작성 후)
109
122
 
123
+ - [ ] ⛔ BG 프레임이 <img> 태그로 처리되지 않았는가? (CSS background-image만 허용)
124
+ - [ ] ⛔ TEXT 자식이 있는 프레임이 통째 이미지로 처리되지 않았는가?
125
+ - [ ] ⛔ INSTANCE 반복 패턴(카드/아이템)이 이미지 1장으로 처리되지 않았는가?
110
126
  - [ ] template 클래스 ↔ SCSS 클래스 1:1 일치
111
127
  - [ ] 모든 img src가 static/에 실제 존재
112
128
  - [ ] Auto Layout 노드 → SCSS에 flex 속성 존재
@@ -9,6 +9,18 @@ tier: standard
9
9
 
10
10
  Figma REST API(`src/infra/lib/figma/`)를 사용하여 **구조적 코드 생성에 필요한 모든 데이터**를 추출.
11
11
 
12
+ ```
13
+ ⛔ 불변 규칙 — screenshot 명령의 허용 범위:
14
+ ✅ BG 프레임 렌더링 (TEXT 자식이 없는 순수 배경만)
15
+ ✅ 벡터 글자 GROUP (웹폰트 없는 장식 타이틀)
16
+ ✅ 개별 아이콘/썸네일 (50~300px 독립 에셋)
17
+ ✅ 섹션별 전체 스크린샷 → sections/ (Phase 6 검증용)
18
+ ❌ TEXT 자식이 있는 프레임 (가격, 수량, 설명 등)
19
+ ❌ INSTANCE 반복 패턴 프레임 (카드 그리드, 보상 목록)
20
+ ❌ 버튼/인터랙티브 요소가 있는 프레임
21
+ ❌ "섹션 콘텐츠"를 통째로 렌더링
22
+ ```
23
+
12
24
  ```
13
25
  추출 우선순위:
14
26
  1순위: 노드 트리 + CSS (코드 생성의 PRIMARY 소스)
@@ -4,7 +4,15 @@
4
4
 
5
5
  ```
6
6
  ❌ imageRef 개별 다운로드 금지 (텍스처 fill 공유 문제)
7
+ ❌ 섹션/그룹을 통째 이미지로 렌더링 금지 (내부 TEXT/INSTANCE 포함 시)
7
8
  ✅ 모든 이미지는 Figma screenshot API로 노드 렌더링
9
+ ✅ 렌더링 전 반드시 2-1.5 판별 규칙 확인 → HTML 대상은 렌더링하지 않음
10
+
11
+ 실제 테스트에서 발생한 잘못된 렌더링:
12
+ ❌ exchange-section1.webp (카드 4개 그리드를 이미지 1장으로)
13
+ ❌ daily-step2-list.webp (보상 목록을 텍스트 포함하여 통째로)
14
+ ❌ prize-section1.webp (응모 아이템을 텍스트 포함하여 통째로)
15
+ ✅ 올바른 접근: 카드 내부의 아이콘/썸네일만 개별 렌더링
8
16
  ```
9
17
 
10
18
  ## Render Methods