codymaster 4.4.5 → 4.5.2

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.
Files changed (197) hide show
  1. package/CHANGELOG.md +33 -0
  2. package/README.md +29 -14
  3. package/commands/demo.md +1 -1
  4. package/dist/context-bus.js +70 -0
  5. package/dist/context-db.js +265 -0
  6. package/dist/continuity.js +12 -0
  7. package/dist/file-watcher.js +79 -0
  8. package/dist/index.js +152 -1
  9. package/dist/l0-indexer.js +158 -0
  10. package/dist/mcp-context-server.js +400 -0
  11. package/dist/migrate-json-to-sqlite.js +126 -0
  12. package/dist/skill-chain.js +19 -3
  13. package/dist/token-budget.js +108 -0
  14. package/dist/uri-resolver.js +203 -0
  15. package/package.json +5 -1
  16. package/scripts/gate-0-secrets.js +63 -0
  17. package/scripts/gate-1-syntax.js +53 -0
  18. package/scripts/gate-5-dist-verify.js +55 -0
  19. package/scripts/gate-6-smoke-test.js +30 -0
  20. package/scripts/index-codebase.sh +552 -0
  21. package/scripts/mcp-bridge.js +284 -0
  22. package/scripts/postinstall.js +301 -0
  23. package/scripts/security-fixer.js +143 -0
  24. package/scripts/security-scan.js +55 -0
  25. package/scripts/test-gemini.js +13 -0
  26. package/scripts/todo-bridge.js +112 -0
  27. package/skills/_shared/helpers.md +50 -14
  28. package/skills/cm-autopilot/SKILL.md +29 -0
  29. package/skills/cm-autopilot/scripts/autopilot.py +190 -0
  30. package/skills/cm-continuity/SKILL.md +90 -28
  31. package/skills/cm-skill-chain/SKILL.md +47 -1
  32. package/skills/cm-start/SKILL.md +11 -2
  33. package/skills/boxme-git-config/SKILL.md +0 -56
  34. package/skills/boxme-local-dev/SKILL.md +0 -66
  35. package/skills/jobs-to-be-done/SKILL.md +0 -266
  36. package/skills/jobs-to-be-done/references/case-studies.md +0 -154
  37. package/skills/jobs-to-be-done/references/competitive-strategy.md +0 -280
  38. package/skills/jobs-to-be-done/references/diagnostics.md +0 -158
  39. package/skills/jobs-to-be-done/references/innovation-process.md +0 -392
  40. package/skills/jobs-to-be-done/references/organizational-change.md +0 -328
  41. package/skills/marketplace-report-crawler/SKILL.md +0 -176
  42. package/skills/marketplace-report-crawler/config/accounts.json +0 -41
  43. package/skills/marketplace-report-crawler/config/report-types.json +0 -422
  44. package/skills/marketplace-report-crawler/config/sessions.json +0 -3
  45. package/skills/marketplace-report-crawler/scripts/ab-wrapper.sh +0 -102
  46. package/skills/marketplace-report-crawler/scripts/browser-actions/lazada/lazada-actions.js +0 -114
  47. package/skills/marketplace-report-crawler/scripts/browser-actions/shopee/shopee-actions.js +0 -94
  48. package/skills/marketplace-report-crawler/scripts/browser-actions/tiktok/tiktok-actions.js +0 -272
  49. package/skills/marketplace-report-crawler/scripts/crawl-runner.js +0 -281
  50. package/skills/marketplace-report-crawler/scripts/session-check.sh +0 -72
  51. package/skills/marketplace-report-crawler/scripts/session-manager.sh +0 -349
  52. package/skills/marketplace-report-crawler/scripts/setup-folders.sh +0 -83
  53. package/skills/medical-research/SKILL.md +0 -194
  54. package/skills/medical-research/scripts/evidence_checker.py +0 -288
  55. package/skills/mom-test/SKILL.md +0 -267
  56. package/skills/mom-test/references/avoiding-bad-data.md +0 -221
  57. package/skills/mom-test/references/case-studies.md +0 -306
  58. package/skills/mom-test/references/commitment-advancement.md +0 -219
  59. package/skills/mom-test/references/finding-conversations.md +0 -251
  60. package/skills/mom-test/references/processing-learning.md +0 -256
  61. package/skills/mom-test/references/question-patterns.md +0 -198
  62. package/skills/pandasai-analytics/SKILL.md +0 -251
  63. package/skills/release-it/SKILL.md +0 -235
  64. package/skills/release-it/references/anti-patterns.md +0 -279
  65. package/skills/release-it/references/capacity-planning.md +0 -285
  66. package/skills/release-it/references/chaos-engineering.md +0 -325
  67. package/skills/release-it/references/deployment-strategies.md +0 -331
  68. package/skills/release-it/references/observability.md +0 -301
  69. package/skills/release-it/references/stability-patterns.md +0 -355
  70. package/skills/skill-creator-ultra/.agents/workflows/skill-audit.md +0 -37
  71. package/skills/skill-creator-ultra/.agents/workflows/skill-compare.md +0 -34
  72. package/skills/skill-creator-ultra/.agents/workflows/skill-export.md +0 -51
  73. package/skills/skill-creator-ultra/.agents/workflows/skill-generate.md +0 -39
  74. package/skills/skill-creator-ultra/.agents/workflows/skill-scaffold.md +0 -52
  75. package/skills/skill-creator-ultra/.agents/workflows/skill-simulate.md +0 -25
  76. package/skills/skill-creator-ultra/.agents/workflows/skill-stats.md +0 -31
  77. package/skills/skill-creator-ultra/.agents/workflows/skill-validate.md +0 -25
  78. package/skills/skill-creator-ultra/README.md +0 -1242
  79. package/skills/skill-creator-ultra/SKILL.md +0 -388
  80. package/skills/skill-creator-ultra/agents/analyzer.md +0 -274
  81. package/skills/skill-creator-ultra/agents/comparator.md +0 -202
  82. package/skills/skill-creator-ultra/agents/grader.md +0 -223
  83. package/skills/skill-creator-ultra/assets/eval_review.html +0 -146
  84. package/skills/skill-creator-ultra/eval-viewer/generate_review.py +0 -471
  85. package/skills/skill-creator-ultra/eval-viewer/viewer.html +0 -1325
  86. package/skills/skill-creator-ultra/examples/example_anthropic_frontend.md +0 -109
  87. package/skills/skill-creator-ultra/examples/example_anthropic_pdf.md +0 -116
  88. package/skills/skill-creator-ultra/examples/example_api_docs.md +0 -189
  89. package/skills/skill-creator-ultra/examples/example_db_migration.md +0 -253
  90. package/skills/skill-creator-ultra/examples/example_git_commit.md +0 -111
  91. package/skills/skill-creator-ultra/install.ps1 +0 -289
  92. package/skills/skill-creator-ultra/install.sh +0 -313
  93. package/skills/skill-creator-ultra/phases/phase1_interview.md +0 -202
  94. package/skills/skill-creator-ultra/phases/phase2_extract.md +0 -55
  95. package/skills/skill-creator-ultra/phases/phase3_detect.md +0 -57
  96. package/skills/skill-creator-ultra/phases/phase4_generate.md +0 -543
  97. package/skills/skill-creator-ultra/phases/phase5_test.md +0 -319
  98. package/skills/skill-creator-ultra/phases/phase6_eval.md +0 -301
  99. package/skills/skill-creator-ultra/phases/phase7_iterate.md +0 -103
  100. package/skills/skill-creator-ultra/phases/phase8_optimize.md +0 -113
  101. package/skills/skill-creator-ultra/resources/advanced_patterns.md +0 -499
  102. package/skills/skill-creator-ultra/resources/anti_patterns.md +0 -376
  103. package/skills/skill-creator-ultra/resources/blueprints.md +0 -498
  104. package/skills/skill-creator-ultra/resources/checklist.md +0 -243
  105. package/skills/skill-creator-ultra/resources/composition_cookbook.md +0 -291
  106. package/skills/skill-creator-ultra/resources/description_optimization.md +0 -90
  107. package/skills/skill-creator-ultra/resources/eval_guide.md +0 -133
  108. package/skills/skill-creator-ultra/resources/industry_questions.md +0 -189
  109. package/skills/skill-creator-ultra/resources/interview_questions.md +0 -200
  110. package/skills/skill-creator-ultra/resources/pattern_detection.md +0 -200
  111. package/skills/skill-creator-ultra/resources/prompt_engineering.md +0 -531
  112. package/skills/skill-creator-ultra/resources/schemas.md +0 -430
  113. package/skills/skill-creator-ultra/resources/script_integration.md +0 -593
  114. package/skills/skill-creator-ultra/resources/scripts_guide.md +0 -339
  115. package/skills/skill-creator-ultra/resources/skill_template.md +0 -124
  116. package/skills/skill-creator-ultra/resources/skill_writing_guide.md +0 -634
  117. package/skills/skill-creator-ultra/resources/versioning_guide.md +0 -193
  118. package/skills/skill-creator-ultra/scripts/ci_eval.py +0 -200
  119. package/skills/skill-creator-ultra/scripts/package_skill.py +0 -165
  120. package/skills/skill-creator-ultra/scripts/simulate_skill.py +0 -398
  121. package/skills/skill-creator-ultra/scripts/skill_audit.py +0 -611
  122. package/skills/skill-creator-ultra/scripts/skill_compare.py +0 -265
  123. package/skills/skill-creator-ultra/scripts/skill_export.py +0 -334
  124. package/skills/skill-creator-ultra/scripts/skill_scaffold.py +0 -403
  125. package/skills/skill-creator-ultra/scripts/skill_stats.py +0 -339
  126. package/skills/skill-creator-ultra/scripts/validate_skill.py +0 -411
  127. package/skills/tailwind-mastery/SKILL.md +0 -229
  128. package/skills/vercel-react-best-practices/AGENTS.md +0 -3373
  129. package/skills/vercel-react-best-practices/README.md +0 -123
  130. package/skills/vercel-react-best-practices/SKILL.md +0 -143
  131. package/skills/vercel-react-best-practices/rules/_sections.md +0 -46
  132. package/skills/vercel-react-best-practices/rules/_template.md +0 -28
  133. package/skills/vercel-react-best-practices/rules/advanced-event-handler-refs.md +0 -55
  134. package/skills/vercel-react-best-practices/rules/advanced-init-once.md +0 -42
  135. package/skills/vercel-react-best-practices/rules/advanced-use-latest.md +0 -39
  136. package/skills/vercel-react-best-practices/rules/async-api-routes.md +0 -38
  137. package/skills/vercel-react-best-practices/rules/async-defer-await.md +0 -80
  138. package/skills/vercel-react-best-practices/rules/async-dependencies.md +0 -51
  139. package/skills/vercel-react-best-practices/rules/async-parallel.md +0 -28
  140. package/skills/vercel-react-best-practices/rules/async-suspense-boundaries.md +0 -99
  141. package/skills/vercel-react-best-practices/rules/bundle-barrel-imports.md +0 -59
  142. package/skills/vercel-react-best-practices/rules/bundle-conditional.md +0 -31
  143. package/skills/vercel-react-best-practices/rules/bundle-defer-third-party.md +0 -49
  144. package/skills/vercel-react-best-practices/rules/bundle-dynamic-imports.md +0 -35
  145. package/skills/vercel-react-best-practices/rules/bundle-preload.md +0 -50
  146. package/skills/vercel-react-best-practices/rules/client-event-listeners.md +0 -74
  147. package/skills/vercel-react-best-practices/rules/client-localstorage-schema.md +0 -71
  148. package/skills/vercel-react-best-practices/rules/client-passive-event-listeners.md +0 -48
  149. package/skills/vercel-react-best-practices/rules/client-swr-dedup.md +0 -56
  150. package/skills/vercel-react-best-practices/rules/js-batch-dom-css.md +0 -107
  151. package/skills/vercel-react-best-practices/rules/js-cache-function-results.md +0 -80
  152. package/skills/vercel-react-best-practices/rules/js-cache-property-access.md +0 -28
  153. package/skills/vercel-react-best-practices/rules/js-cache-storage.md +0 -70
  154. package/skills/vercel-react-best-practices/rules/js-combine-iterations.md +0 -32
  155. package/skills/vercel-react-best-practices/rules/js-early-exit.md +0 -50
  156. package/skills/vercel-react-best-practices/rules/js-flatmap-filter.md +0 -60
  157. package/skills/vercel-react-best-practices/rules/js-hoist-regexp.md +0 -45
  158. package/skills/vercel-react-best-practices/rules/js-index-maps.md +0 -37
  159. package/skills/vercel-react-best-practices/rules/js-length-check-first.md +0 -49
  160. package/skills/vercel-react-best-practices/rules/js-min-max-loop.md +0 -82
  161. package/skills/vercel-react-best-practices/rules/js-set-map-lookups.md +0 -24
  162. package/skills/vercel-react-best-practices/rules/js-tosorted-immutable.md +0 -57
  163. package/skills/vercel-react-best-practices/rules/rendering-activity.md +0 -26
  164. package/skills/vercel-react-best-practices/rules/rendering-animate-svg-wrapper.md +0 -47
  165. package/skills/vercel-react-best-practices/rules/rendering-conditional-render.md +0 -40
  166. package/skills/vercel-react-best-practices/rules/rendering-content-visibility.md +0 -38
  167. package/skills/vercel-react-best-practices/rules/rendering-hoist-jsx.md +0 -46
  168. package/skills/vercel-react-best-practices/rules/rendering-hydration-no-flicker.md +0 -82
  169. package/skills/vercel-react-best-practices/rules/rendering-hydration-suppress-warning.md +0 -30
  170. package/skills/vercel-react-best-practices/rules/rendering-resource-hints.md +0 -85
  171. package/skills/vercel-react-best-practices/rules/rendering-script-defer-async.md +0 -68
  172. package/skills/vercel-react-best-practices/rules/rendering-svg-precision.md +0 -28
  173. package/skills/vercel-react-best-practices/rules/rendering-usetransition-loading.md +0 -75
  174. package/skills/vercel-react-best-practices/rules/rerender-defer-reads.md +0 -39
  175. package/skills/vercel-react-best-practices/rules/rerender-dependencies.md +0 -45
  176. package/skills/vercel-react-best-practices/rules/rerender-derived-state-no-effect.md +0 -40
  177. package/skills/vercel-react-best-practices/rules/rerender-derived-state.md +0 -29
  178. package/skills/vercel-react-best-practices/rules/rerender-functional-setstate.md +0 -74
  179. package/skills/vercel-react-best-practices/rules/rerender-lazy-state-init.md +0 -58
  180. package/skills/vercel-react-best-practices/rules/rerender-memo-with-default-value.md +0 -38
  181. package/skills/vercel-react-best-practices/rules/rerender-memo.md +0 -44
  182. package/skills/vercel-react-best-practices/rules/rerender-move-effect-to-event.md +0 -45
  183. package/skills/vercel-react-best-practices/rules/rerender-no-inline-components.md +0 -82
  184. package/skills/vercel-react-best-practices/rules/rerender-simple-expression-in-memo.md +0 -35
  185. package/skills/vercel-react-best-practices/rules/rerender-split-combined-hooks.md +0 -64
  186. package/skills/vercel-react-best-practices/rules/rerender-transitions.md +0 -40
  187. package/skills/vercel-react-best-practices/rules/rerender-use-deferred-value.md +0 -59
  188. package/skills/vercel-react-best-practices/rules/rerender-use-ref-transient-values.md +0 -73
  189. package/skills/vercel-react-best-practices/rules/server-after-nonblocking.md +0 -73
  190. package/skills/vercel-react-best-practices/rules/server-auth-actions.md +0 -96
  191. package/skills/vercel-react-best-practices/rules/server-cache-lru.md +0 -41
  192. package/skills/vercel-react-best-practices/rules/server-cache-react.md +0 -76
  193. package/skills/vercel-react-best-practices/rules/server-dedup-props.md +0 -65
  194. package/skills/vercel-react-best-practices/rules/server-hoist-static-io.md +0 -142
  195. package/skills/vercel-react-best-practices/rules/server-parallel-fetching.md +0 -83
  196. package/skills/vercel-react-best-practices/rules/server-serialization.md +0 -38
  197. package/skills/web-design-guidelines/SKILL.md +0 -39
@@ -1,193 +0,0 @@
1
- # 🔄 Versioning Guide — Hướng Dẫn Nâng Cấp Skill Theo Thời Gian
2
-
3
- ---
4
-
5
- ## Tại sao cần Versioning?
6
-
7
- Skill không phải "tạo xong là xong". Theo thời gian:
8
-
9
- - 🔧 Tool/API thay đổi → Skill lỗi thời
10
- - 📈 Quy trình cải tiến → Cần cập nhật
11
- - 🐛 Phát hiện bugs → Cần fix
12
- - 💡 Có ý tưởng mới → Cần mở rộng
13
-
14
- ---
15
-
16
- ## Quy tắc Versioning
17
-
18
- ### Semantic Versioning cho Skill: `vX.Y.Z`
19
-
20
- | Thay đổi | Version | Ví dụ |
21
- |---|---|---|
22
- | **MAJOR (X)** — Breaking change, thay đổi lớn | v1.0 → v**2**.0 | Viết lại Instructions, đổi pattern |
23
- | **MINOR (Y)** — Thêm tính năng, không phá cũ | v1.0 → v1.**1** | Thêm ví dụ, thêm constraint |
24
- | **PATCH (Z)** — Sửa lỗi nhỏ | v1.0.0 → v1.0.**1** | Fix typo, chỉnh wording |
25
-
26
- ---
27
-
28
- ## Cách ghi Version trong SKILL.md
29
-
30
- ### Thêm vào cuối YAML frontmatter
31
-
32
- ```markdown
33
- ---
34
- name: my-skill
35
- description: ...
36
- version: 2.1.0
37
- last_updated: 2026-06-15
38
- ---
39
- ```
40
-
41
- ### Thêm Changelog section
42
-
43
- ```markdown
44
- # Changelog
45
-
46
- ## v2.1.0 (2026-06-15)
47
- ### Added
48
- - Thêm ví dụ edge case cho input Unicode
49
- - Thêm constraint: Không xóa file gốc
50
-
51
- ### Changed
52
- - Cải thiện Step 3: Thêm validation sau transform
53
-
54
- ## v2.0.0 (2026-04-01) — BREAKING
55
- ### Changed
56
- - Viết lại Instructions theo chuỗi pipeline
57
- - Đổi từ Pattern Basic → Pattern Pipeline
58
-
59
- ### Removed
60
- - Bỏ Step cũ "Xử lý thủ công"
61
-
62
- ## v1.0.0 (2026-03-03)
63
- - Initial release
64
- ```
65
-
66
- ---
67
-
68
- ## Quy trình nâng cấp Skill
69
-
70
- ### Step 1: Đánh giá (khi nào cần upgrade?)
71
-
72
- Checklist review hàng quý:
73
-
74
- - [ ] Skill có hoạt động đúng không? (Test với input mới)
75
- - [ ] Tool/API skill dùng có thay đổi không?
76
- - [ ] User phản hồi gì? Có pain point nào?
77
- - [ ] Có anti-pattern nào trong skill hiện tại không? (Xem `anti_patterns.md`)
78
- - [ ] Complexity có tăng không? Cần tách skill?
79
-
80
- ### Step 2: Lên kế hoạch
81
-
82
- ```markdown
83
- ## Upgrade Plan: [tên-skill] v1.0 → v2.0
84
-
85
- ### Mục tiêu:
86
- - [Gì cần thay đổi]
87
-
88
- ### Thay đổi cụ thể:
89
- - [ ] Instructions bước X: Thêm validation
90
- - [ ] Examples: Thêm 1 edge case mới
91
- - [ ] Constraints: Thêm quy tắc bảo mật
92
-
93
- ### Backward Compatibility:
94
- - Có phá gì không? [CÓ/KHÔNG]
95
- - Nếu CÓ → MAJOR version bump (v2.0)
96
- ```
97
-
98
- ### Step 3: Thực hiện
99
-
100
- 1. Sửa SKILL.md
101
- 2. Cập nhật version trong frontmatter
102
- 3. Thêm entry vào Changelog
103
- 4. Chạy validate_skill.py
104
- 5. Test với input mẫu
105
-
106
- ### Step 4: Deploy
107
-
108
- 1. Copy file mới vào đúng vị trí (global/workspace)
109
- 2. Mở chat mới để AI reload skill
110
- 3. Test lại 1 lần
111
-
112
- ---
113
-
114
- ## Template Changelog Entry
115
-
116
- ```markdown
117
- ## vX.Y.Z (YYYY-MM-DD)
118
-
119
- ### Added
120
- - [Tính năng mới / Ví dụ mới / Constraint mới]
121
-
122
- ### Changed
123
- - [Thay đổi behavior / Cải thiện instruction]
124
-
125
- ### Fixed
126
- - [Bug fix / Typo fix]
127
-
128
- ### Removed
129
- - [Chức năng bị bỏ]
130
-
131
- ### Deprecated
132
- - [Chức năng sẽ bỏ trong tương lai]
133
-
134
- ### Security
135
- - [Cải thiện bảo mật]
136
- ```
137
-
138
- ---
139
-
140
- ## Branching Strategy (Cho team dùng Git)
141
-
142
- ```
143
- main branch: Skill production (đang dùng)
144
- develop branch: Skill đang phát triển
145
- feature/xxx: Tính năng mới cho skill
146
- ```
147
-
148
- ### Workflow
149
-
150
- ```mermaid
151
- gitgraph
152
- commit id:"v1.0.0 release"
153
- branch develop
154
- commit id:"Thêm ví dụ mới"
155
- commit id:"Fix constraint"
156
- checkout main
157
- merge develop id:"v1.1.0 release"
158
- branch feature/safety
159
- commit id:"Thêm Safety Check"
160
- checkout develop
161
- merge feature/safety
162
- checkout main
163
- merge develop id:"v2.0.0 release"
164
- ```
165
-
166
- ---
167
-
168
- ## Quy tắc Deprecation
169
-
170
- Khi cần bỏ tính năng:
171
-
172
- 1. **Ghi chú Deprecated** trong MINOR version (v1.2)
173
-
174
- ```markdown
175
- # Instructions
176
- ## Step 3: [DEPRECATED — Sẽ bỏ ở v2.0]
177
- Dùng Step 3b thay thế.
178
-
179
- ## Step 3b: (Mới)
180
- ...
181
- ```
182
-
183
- 1. **Xóa thực sự** trong MAJOR version (v2.0)
184
-
185
- 2. **Ghi vào Changelog:**
186
-
187
- ```markdown
188
- ### Deprecated (v1.2.0)
189
- - Step 3 "Xử lý thủ công" — Dùng Step 3b "Xử lý tự động" thay thế
190
-
191
- ### Removed (v2.0.0)
192
- - Step 3 "Xử lý thủ công" — Đã bỏ hoàn toàn
193
- ```
@@ -1,200 +0,0 @@
1
- #!/usr/bin/env python3
2
- """
3
- ci_eval.py — Chạy skill eval trong CI/CD pipeline.
4
-
5
- Đọc eval_results.json, kiểm tra pass/fail, return exit code phù hợp.
6
- Dùng trong GitHub Actions, GitLab CI, hoặc bất kỳ CI system nào.
7
-
8
- Usage:
9
- python ci_eval.py <path/to/eval_results.json> [--min-score 80] [--strict]
10
-
11
- Options:
12
- --min-score N Minimum overall score % to pass (default: 80)
13
- --strict Fail on any security warning (not just critical fails)
14
- --format text|json Output format (default: text)
15
- --badge Generate badge-compatible output
16
-
17
- Examples:
18
- # Basic: pass if score >= 80%
19
- python ci_eval.py evals/eval_results.json
20
-
21
- # Strict: pass if score >= 90% and zero security issues
22
- python ci_eval.py evals/eval_results.json --min-score 90 --strict
23
-
24
- # In GitHub Actions:
25
- # - name: Eval skill
26
- # run: python scripts/ci_eval.py evals/eval_results.json --min-score 85
27
- """
28
-
29
- import json
30
- import sys
31
- import argparse
32
- from pathlib import Path
33
-
34
-
35
- def grade_from_score(score):
36
- """Convert percentage score to letter grade."""
37
- if score >= 95:
38
- return "S"
39
- elif score >= 90:
40
- return "A"
41
- elif score >= 80:
42
- return "B"
43
- elif score >= 70:
44
- return "C"
45
- elif score >= 60:
46
- return "D"
47
- else:
48
- return "F"
49
-
50
-
51
- def check_security(security, strict=False):
52
- """Check security results. Returns (passed, issues)."""
53
- issues = []
54
- critical_checks = ["prompt_injection", "pii_exposure", "secret_leakage"]
55
- warning_checks = ["scope_escape", "destructive_commands"]
56
-
57
- for check in critical_checks:
58
- result = security.get(check, "unknown")
59
- if result not in ("pass", "PASS"):
60
- issues.append(f"🔴 CRITICAL: {check} = {result}")
61
-
62
- for check in warning_checks:
63
- result = security.get(check, "unknown")
64
- if result not in ("pass", "PASS"):
65
- issues.append(f"🟡 WARNING: {check} = {result}")
66
-
67
- if strict:
68
- return len(issues) == 0, issues
69
-
70
- # Non-strict: only fail on critical
71
- critical_issues = [i for i in issues if "CRITICAL" in i]
72
- return len(critical_issues) == 0, issues
73
-
74
-
75
- def format_text(data, score, grade, security_passed, security_issues, min_score, verdict):
76
- """Format output as human-readable text."""
77
- lines = []
78
- lines.append("=" * 50)
79
- lines.append(f"📊 CI EVAL REPORT — {data.get('skill', 'unknown')}")
80
- lines.append("=" * 50)
81
- lines.append("")
82
-
83
- # Test results
84
- tests = data.get("tests", [])
85
- if tests:
86
- lines.append("📋 Test Results:")
87
- for t in tests:
88
- name = t.get("name", "?")
89
- ws = t.get("weighted_score", 0)
90
- pr = t.get("pass_rate", 0)
91
- lines.append(f" {name}: {ws*100:.0f}% (pass rate: {pr*100:.0f}%)")
92
- lines.append("")
93
-
94
- # Dimensions (average across tests)
95
- if tests and tests[0].get("dimensions"):
96
- lines.append("📊 Dimension Averages:")
97
- dim_keys = ["correctness", "completeness", "format", "adherence",
98
- "safety", "efficiency", "robustness"]
99
- for dk in dim_keys:
100
- vals = [t["dimensions"].get(dk, 0) for t in tests if "dimensions" in t]
101
- avg = sum(vals) / len(vals) if vals else 0
102
- bar = "█" * int(avg) + "░" * (5 - int(avg))
103
- lines.append(f" {dk:20s} {avg:.1f}/5 {bar}")
104
- lines.append("")
105
-
106
- # Security
107
- lines.append(f"🔐 Security: {'PASS ✅' if security_passed else 'FAIL ❌'}")
108
- for issue in security_issues:
109
- lines.append(f" {issue}")
110
- lines.append("")
111
-
112
- # Overall
113
- lines.append(f"📈 Overall Score: {score:.0f}% ({grade})")
114
- lines.append(f"🎯 Minimum: {min_score}%")
115
- lines.append(f"🏁 Verdict: {verdict}")
116
- lines.append("=" * 50)
117
-
118
- return "\n".join(lines)
119
-
120
-
121
- def format_json_output(data, score, grade, security_passed, security_issues, verdict):
122
- """Format output as JSON for downstream tools."""
123
- return json.dumps({
124
- "skill": data.get("skill", "unknown"),
125
- "score": round(score, 1),
126
- "grade": grade,
127
- "security_passed": security_passed,
128
- "security_issues": security_issues,
129
- "verdict": verdict
130
- }, indent=2)
131
-
132
-
133
- def main():
134
- parser = argparse.ArgumentParser(
135
- description="CI/CD Skill Eval Checker — validate eval_results.json"
136
- )
137
- parser.add_argument("eval_file", help="Path to eval_results.json")
138
- parser.add_argument("--min-score", type=float, default=80,
139
- help="Minimum overall score %% to pass (default: 80)")
140
- parser.add_argument("--strict", action="store_true",
141
- help="Fail on any security warning (not just criticals)")
142
- parser.add_argument("--format", choices=["text", "json"], default="text",
143
- help="Output format")
144
- parser.add_argument("--badge", action="store_true",
145
- help="Print badge-compatible single line")
146
- args = parser.parse_args()
147
-
148
- # Read eval results
149
- eval_path = Path(args.eval_file)
150
- if not eval_path.exists():
151
- print(f"❌ File not found: {eval_path}")
152
- sys.exit(2)
153
-
154
- try:
155
- data = json.loads(eval_path.read_text(encoding="utf-8"))
156
- except json.JSONDecodeError as e:
157
- print(f"❌ Invalid JSON: {e}")
158
- sys.exit(2)
159
-
160
- # Extract score
161
- score = data.get("overall_score", 0)
162
- if isinstance(score, float) and score <= 1.0:
163
- score *= 100 # Convert 0-1 to 0-100
164
-
165
- grade = grade_from_score(score)
166
-
167
- # Check security
168
- security = data.get("security", {})
169
- security_passed, security_issues = check_security(security, args.strict)
170
-
171
- # Determine verdict
172
- if not security_passed:
173
- verdict = "BLOCKED_SECURITY"
174
- elif score >= args.min_score:
175
- verdict = "DEPLOY_OK"
176
- else:
177
- verdict = "NEEDS_ITERATION"
178
-
179
- # Output
180
- if args.badge:
181
- emoji = "✅" if verdict == "DEPLOY_OK" else "❌"
182
- print(f"{emoji} {grade} ({score:.0f}%) | Security: {'✅' if security_passed else '❌'}")
183
- elif args.format == "json":
184
- print(format_json_output(data, score, grade, security_passed,
185
- security_issues, verdict))
186
- else:
187
- print(format_text(data, score, grade, security_passed,
188
- security_issues, args.min_score, verdict))
189
-
190
- # Exit code
191
- if verdict == "DEPLOY_OK":
192
- sys.exit(0)
193
- elif verdict == "BLOCKED_SECURITY":
194
- sys.exit(3)
195
- else:
196
- sys.exit(1)
197
-
198
-
199
- if __name__ == "__main__":
200
- main()
@@ -1,165 +0,0 @@
1
- #!/usr/bin/env python3
2
- """
3
- package_skill.py — Đóng gói skill thành file .skill (zip) để phân phối.
4
-
5
- Adapted from Anthropic's skill-creator package_skill.py.
6
- Standalone version — không dependency ngoài Python stdlib.
7
-
8
- Usage:
9
- python package_skill.py <path/to/skill-folder> [output-directory]
10
-
11
- Example:
12
- python package_skill.py ~/.gemini/antigravity/skills/my-skill
13
- python package_skill.py ~/.gemini/antigravity/skills/my-skill ./dist
14
- """
15
-
16
- import fnmatch
17
- import sys
18
- import zipfile
19
- import yaml
20
- from pathlib import Path
21
-
22
- # Patterns to exclude when packaging
23
- EXCLUDE_DIRS = {"__pycache__", "node_modules", ".git", "evals"}
24
- EXCLUDE_GLOBS = {"*.pyc", "*.pyo"}
25
- EXCLUDE_FILES = {".DS_Store", "Thumbs.db"}
26
-
27
-
28
- def should_exclude(rel_path: Path) -> bool:
29
- """Check if a path should be excluded from packaging."""
30
- parts = rel_path.parts
31
- if any(part in EXCLUDE_DIRS for part in parts):
32
- return True
33
- name = rel_path.name
34
- if name in EXCLUDE_FILES:
35
- return True
36
- return any(fnmatch.fnmatch(name, pat) for pat in EXCLUDE_GLOBS)
37
-
38
-
39
- def validate_skill(skill_path: Path) -> tuple:
40
- """
41
- Validate skill structure — standalone version.
42
- Returns (is_valid: bool, message: str).
43
- """
44
- skill_md = skill_path / "SKILL.md"
45
- if not skill_md.exists():
46
- return False, "SKILL.md not found"
47
-
48
- content = skill_md.read_text(encoding="utf-8")
49
-
50
- # Check YAML frontmatter
51
- if not content.startswith("---"):
52
- return False, "SKILL.md missing YAML frontmatter (---)"
53
-
54
- try:
55
- end = content.index("---", 3)
56
- frontmatter = content[3:end].strip()
57
- meta = yaml.safe_load(frontmatter)
58
- except (ValueError, yaml.YAMLError) as e:
59
- return False, f"Invalid YAML frontmatter: {e}"
60
-
61
- if not meta or not isinstance(meta, dict):
62
- return False, "YAML frontmatter is empty"
63
-
64
- if "name" not in meta:
65
- return False, "Missing 'name' in frontmatter"
66
-
67
- if "description" not in meta:
68
- return False, "Missing 'description' in frontmatter"
69
-
70
- desc = str(meta.get("description", ""))
71
- if len(desc) < 20:
72
- return False, f"Description too short ({len(desc)} chars) — minimum 20"
73
-
74
- return True, f"Valid skill: {meta['name']}"
75
-
76
-
77
- def package_skill(skill_path, output_dir=None):
78
- """
79
- Package a skill folder into a .skill file (zip format).
80
-
81
- Args:
82
- skill_path: Path to the skill folder
83
- output_dir: Optional output directory (defaults to cwd)
84
-
85
- Returns:
86
- Path to created .skill file, or None if error
87
- """
88
- skill_path = Path(skill_path).resolve()
89
-
90
- if not skill_path.exists():
91
- print(f"❌ Error: Skill folder not found: {skill_path}")
92
- return None
93
-
94
- if not skill_path.is_dir():
95
- print(f"❌ Error: Not a directory: {skill_path}")
96
- return None
97
-
98
- # Validate before packaging
99
- print("🔍 Validating skill...")
100
- valid, message = validate_skill(skill_path)
101
- if not valid:
102
- print(f"❌ Validation failed: {message}")
103
- return None
104
- print(f"✅ {message}\n")
105
-
106
- # Output location
107
- skill_name = skill_path.name
108
- if output_dir:
109
- output_path = Path(output_dir).resolve()
110
- output_path.mkdir(parents=True, exist_ok=True)
111
- else:
112
- output_path = Path.cwd()
113
-
114
- skill_filename = output_path / f"{skill_name}.skill"
115
-
116
- # Create .skill file (zip)
117
- try:
118
- file_count = 0
119
- with zipfile.ZipFile(skill_filename, 'w', zipfile.ZIP_DEFLATED) as zipf:
120
- for file_path in sorted(skill_path.rglob('*')):
121
- if not file_path.is_file():
122
- continue
123
- arcname = file_path.relative_to(skill_path.parent)
124
- if should_exclude(arcname):
125
- print(f" ⏭ Skipped: {arcname}")
126
- continue
127
- zipf.write(file_path, arcname)
128
- print(f" 📄 Added: {arcname}")
129
- file_count += 1
130
-
131
- size_kb = skill_filename.stat().st_size / 1024
132
- print(f"\n✅ Packaged {file_count} files → {skill_filename}")
133
- print(f"📦 Size: {size_kb:.1f} KB")
134
- return skill_filename
135
-
136
- except Exception as e:
137
- print(f"❌ Error creating .skill file: {e}")
138
- return None
139
-
140
-
141
- def main():
142
- if len(sys.argv) < 2:
143
- print("📦 Skill Packager — Đóng gói skill thành .skill file")
144
- print()
145
- print("Usage: python package_skill.py <path/to/skill> [output-dir]")
146
- print()
147
- print("Example:")
148
- print(" python package_skill.py ~/.gemini/antigravity/skills/my-skill")
149
- print(" python package_skill.py ./my-skill ./dist")
150
- sys.exit(1)
151
-
152
- skill_path = sys.argv[1]
153
- output_dir = sys.argv[2] if len(sys.argv) > 2 else None
154
-
155
- print(f"📦 Packaging skill: {skill_path}")
156
- if output_dir:
157
- print(f" Output: {output_dir}")
158
- print()
159
-
160
- result = package_skill(skill_path, output_dir)
161
- sys.exit(0 if result else 1)
162
-
163
-
164
- if __name__ == '__main__':
165
- main()