anchi-kit 1.1.3 → 1.1.4

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/README.md CHANGED
@@ -1,4 +1,4 @@
1
- # 💎 Anchi Kit v1.1.3
1
+ # 💎 Anchi Kit v1.1.4
2
2
 
3
3
  > **Hệ Điều Hành Tư Duy cho AI Code Editor (Cursor, Gemini, Windsurf)**
4
4
  > _Biến AI từ người thợ code (Coder) thành Kỹ sư trưởng (Senior Tech Lead)._
package/docs/ROADMAP.md CHANGED
@@ -100,12 +100,13 @@ Official release of Anchi Kit v1.0.0 với Dynamic Orchestration v2.0.
100
100
  ## 📊 Version Summary
101
101
 
102
102
  | Version | Status | Highlights |
103
- | ------- | ----------- | ------------------------------------------------------------- |
103
+ | ------- | ----------- | ------------------------------------------------------------- | --- |
104
104
  | v1.0.0 | ✅ Released | 22 commands, 21 agents, 55 skills, Dynamic Orchestration v2.0 |
105
105
  | v1.1.0 | ✅ Released | Team Support, Hive Mind (Git Sync) |
106
106
  | v1.1.1 | ✅ Released | Secure Install, IDE Auto-Detect, Policy Assurance |
107
107
  | v1.1.2 | ✅ Released | Fix: npm register conflict resolution |
108
108
  | v1.1.3 | ✅ Released | Fix: Missing source files in package |
109
+ | v1.1.4 | ✅ Released | UX Refinement: Capability-Driven Installation | |
109
110
  | v1.2+ | 🔮 Future | Voice commands, VS Code extension, Multi-repo |
110
111
 
111
112
  ---
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "anchi-kit",
3
- "version": "1.1.3",
3
+ "version": "1.1.4",
4
4
  "description": "The Ultimate AI-Native Toolkit for Cursor & Gemini. Installs into any existing project. Includes commands, agents, skills, and architecture presets.",
5
5
  "main": "src/cli.js",
6
6
  "bin": {
@@ -8,7 +8,7 @@ const fs = require('fs');
8
8
  const path = require('path');
9
9
  const readline = require('readline');
10
10
 
11
- const { PROFILES, getProfile, getProfileList, getProfileEstimate } = require('../lib/profiles');
11
+ const { getCapabilities, resolveCapabilities, getInstallEstimate } = require('../lib/profiles');
12
12
  const { getSkillPackList, resolveSkillPacks } = require('../lib/skillPacks');
13
13
  const { detectTechStack, suggestSkills, formatDetectedStack } = require('../lib/detector');
14
14
  const { calculateInstallSize, getComponentPaths, formatSize } = require('../lib/sizeCalculator');
@@ -180,50 +180,44 @@ async function init() {
180
180
  log.success(` 💡 Suggested skills: ${suggestedSkills.join(', ')}`);
181
181
  }
182
182
 
183
- // Step 2: Choose profile
184
- const profiles = getProfileList();
185
- const profileOptions = profiles.map(p => ({
186
- label: `${p.name}`,
187
- description: p.description,
188
- estimate: getProfileEstimate(p.key).formatted || '',
189
- value: p.key,
183
+ // Step 2: Select Capabilities (Professional UX)
184
+ const { getCapabilities, resolveCapabilities, getInstallEstimate } = require('../lib/profiles');
185
+ const capabilities = getCapabilities();
186
+
187
+ const capOptions = capabilities.map(c => ({
188
+ label: `${c.label} - ${colors.gray}${c.description}${colors.reset}`,
189
+ value: c.key,
190
+ default: c.default
190
191
  }));
191
192
 
192
- const selectedProfile = await askChoice('Chọn profile:', profileOptions);
193
- const profile = getProfile(selectedProfile);
194
-
195
- // Step 3: Customize (if not minimal or fullstack)
196
- let finalConfig = { ...profile };
197
-
198
- if (selectedProfile !== 'minimal' && selectedProfile !== 'fullstack') {
199
- const customize = await ask(`\n${colors.yellow}Customize thêm? (y/N): ${colors.reset}`);
193
+ const selectedKeys = await askMultiSelect('What capabilities do you need?', capOptions);
194
+
195
+ if (selectedKeys.includes('custom')) {
196
+ // Fallback logic if needed, but for now we trust the multiselect
197
+ }
200
198
 
201
- if (customize.toLowerCase() === 'y') {
202
- // Skill packs
203
- const packs = getSkillPackList();
204
- const packOptions = packs.map(p => ({
205
- label: `${p.name} (${p.skillCount} skills)`,
206
- value: p.key,
207
- default: false,
208
- }));
199
+ const finalConfig = resolveCapabilities(selectedKeys);
209
200
 
210
- const selectedPacks = await askMultiSelect('Thêm skill packs:', packOptions);
211
- if (selectedPacks.length > 0) {
212
- const extraSkills = resolveSkillPacks(selectedPacks);
213
- finalConfig.skills = [...new Set([...finalConfig.skills, ...extraSkills])];
214
- }
215
-
216
- // Include presets?
217
- if (!finalConfig.includePresets) {
218
- const includePresets = await ask(`\n${colors.yellow}Include presets folder? (y/N): ${colors.reset}`);
219
- finalConfig.includePresets = includePresets.toLowerCase() === 'y';
220
- }
201
+ // Step 3: Customize (Optional Add-ons)
202
+ const customize = await ask(`\n${colors.yellow}Advanced options? (y/N): ${colors.reset}`);
203
+
204
+ if (customize.toLowerCase() === 'y') {
205
+ const packs = getSkillPackList();
206
+ const packOptions = packs.map(p => ({
207
+ label: `${p.name} (${p.skillCount} skills)`,
208
+ value: p.key,
209
+ default: false,
210
+ }));
211
+
212
+ const selectedPacks = await askMultiSelect('Add extra skill packs:', packOptions);
213
+ if (selectedPacks.length > 0) {
214
+ const extraSkills = resolveSkillPacks(selectedPacks);
215
+ finalConfig.skills = [...new Set([...finalConfig.skills, ...extraSkills])];
216
+ }
221
217
 
222
- // Include docs?
223
- if (!finalConfig.includeDocs) {
224
- const includeDocs = await ask(`${colors.yellow}Include docs folder? (y/N): ${colors.reset}`);
225
- finalConfig.includeDocs = includeDocs.toLowerCase() === 'y';
226
- }
218
+ if (!finalConfig.includePresets) {
219
+ const inc = await ask(`Include architecture presets? (y/N): `);
220
+ finalConfig.includePresets = inc.toLowerCase() === 'y';
227
221
  }
228
222
  }
229
223
 
@@ -402,7 +396,7 @@ async function init() {
402
396
  registerProject(targetPath, {
403
397
  name: path.basename(targetPath),
404
398
  tech_stack: Object.keys(detected).filter(k => detected[k]),
405
- architecture: selectedProfile,
399
+ architecture: selectedKeys.join('+'),
406
400
  installed_at: new Date().toISOString(),
407
401
  env: installName
408
402
  });
@@ -1,100 +1,111 @@
1
1
  // =============================================================================
2
- // Role-based Profiles
2
+ // Capability-Driven Installation
3
3
  // =============================================================================
4
4
 
5
- const PROFILES = {
6
- minimal: {
7
- name: 'Minimal',
8
- description: 'Core commands only (fastest install)',
9
- commands: ['start', 'plan', 'cook', 'fix'],
10
- agents: [],
11
- skills: [],
12
- includePresets: false,
13
- includeDocs: false,
5
+ const CAPABILITIES = [
6
+ {
7
+ key: 'coding',
8
+ label: ' Coding Assistant',
9
+ description: 'Daily coding, debugging, refactoring & tests',
10
+ default: true,
11
+ agents: ['fullstack-developer', 'debugger', 'code-reviewer'],
12
+ skills: ['frontend-development', 'backend-development', 'debugging', 'testing'],
13
+ commands: ['start', 'do', 'fix', 'test', 'clean']
14
14
  },
15
-
16
- developer: {
17
- name: 'Developer',
18
- description: 'Daily coding (commands + basic agents)',
19
- commands: ['start', 'plan', 'cook', 'fix', 'scout', 'generate'],
20
- agents: ['planner', 'scout', 'fullstack-developer', 'debugger'],
21
- skills: ['frontend-development', 'backend-development', 'databases'],
22
- includePresets: false,
23
- includeDocs: false,
15
+ {
16
+ key: 'architect',
17
+ label: '🏗️ System Architect',
18
+ description: 'Planning, DDD, Documentation & Research',
19
+ default: false,
20
+ agents: ['planner', 'architect', 'researcher', 'docs-manager'],
21
+ skills: ['planning', 'ddd-modular-monolith', 'writing-docs', 'research'],
22
+ commands: ['plan', 'design-domain', 'generate']
24
23
  },
25
-
26
- ui_ux: {
27
- name: 'UI/UX Designer',
28
- description: 'Frontend & Design focus',
29
- commands: ['start', 'plan', 'cook', 'design-ui', 'generate'],
30
- agents: ['ui-ux-designer', 'design-system-architect', 'planner'],
31
- skills: ['frontend-development', 'frontend-design', 'ui-styling', 'aesthetic'],
32
- includePresets: false,
33
- includeDocs: false,
24
+ {
25
+ key: 'team',
26
+ label: '👥 Team Collaboration',
27
+ description: 'Hive Mind sync, Git hooks & Team guidelines',
28
+ default: false,
29
+ agents: ['git-manager', 'project-manager'],
30
+ skills: ['git-workflow', 'team-processes'],
31
+ commands: ['team', 'sync', 'status'],
32
+ includePresets: true // Often needed for team standards
34
33
  },
35
-
36
- architect: {
37
- name: 'Architect',
38
- description: 'System design & DDD',
39
- commands: ['start', 'plan', 'cook', 'fix', 'design-domain', 'review'],
40
- agents: ['planner', 'ddd-architect', 'code-reviewer', 'researcher'],
41
- skills: ['ddd-modular-monolith', 'planning', 'backend-development', 'databases'],
42
- includePresets: true,
43
- includeDocs: true,
34
+ {
35
+ key: 'design',
36
+ label: '🎨 UX/UI Design',
37
+ description: 'Design systems, prototyping & frontend patterns',
38
+ default: false,
39
+ agents: ['ui-ux-designer', 'design-system-architect'],
40
+ skills: ['ui-styling', 'frontend-design', 'aesthetic'],
41
+ commands: ['design-ui', 'demo']
44
42
  },
43
+ {
44
+ key: 'security',
45
+ label: '🛡️ Quality & Security',
46
+ description: 'Audit logs, security polices & compliance',
47
+ default: false,
48
+ agents: ['auditor', 'security-guard'],
49
+ skills: ['security-audit', 'code-analysis'],
50
+ commands: ['audit', 'scout'],
51
+ includeDocs: true // Security policies usually need docs
52
+ }
53
+ ];
45
54
 
46
- lead: {
47
- name: 'Team Lead',
48
- description: 'Code review & management',
49
- commands: ['start', 'plan', 'cook', 'fix', 'review', 'scout', 'summary'],
50
- agents: ['planner', 'code-reviewer', 'project-manager', 'docs-manager', 'git-manager'],
51
- skills: ['code-review', 'planning', 'debugging'],
52
- includePresets: false,
53
- includeDocs: true,
54
- },
55
+ function getCapabilities() {
56
+ return CAPABILITIES;
57
+ }
55
58
 
56
- fullstack: {
57
- name: 'Full Stack',
58
- description: 'Everything included',
59
- commands: 'all',
60
- agents: 'all',
61
- skills: 'all',
62
- includePresets: true,
63
- includeDocs: true,
64
- },
65
- };
59
+ function resolveCapabilities(selectedKeys) {
60
+ const config = {
61
+ commands: new Set(['start', 'help']), // Always include core
62
+ agents: new Set(),
63
+ skills: new Set(),
64
+ includePresets: false,
65
+ includeDocs: false
66
+ };
66
67
 
67
- function getProfile(name) {
68
- return PROFILES[name] || null;
69
- }
68
+ selectedKeys.forEach(key => {
69
+ const cap = CAPABILITIES.find(c => c.key === key);
70
+ if (cap) {
71
+ cap.commands.forEach(c => config.commands.add(c));
72
+ cap.agents.forEach(a => config.agents.add(a));
73
+ cap.skills.forEach(s => config.skills.add(s));
74
+ if (cap.includePresets) config.includePresets = true;
75
+ if (cap.includeDocs) config.includeDocs = true;
76
+ }
77
+ });
70
78
 
71
- function getProfileList() {
72
- return Object.entries(PROFILES).map(([key, profile]) => ({
73
- key,
74
- name: profile.name,
75
- description: profile.description,
76
- }));
79
+ return {
80
+ commands: Array.from(config.commands),
81
+ agents: Array.from(config.agents),
82
+ skills: Array.from(config.skills),
83
+ includePresets: config.includePresets,
84
+ includeDocs: config.includeDocs
85
+ };
77
86
  }
78
87
 
79
- function getProfileEstimate(profileKey) {
80
- const profile = PROFILES[profileKey];
81
- if (!profile) return null;
88
+ function getInstallEstimate(selectedKeys) {
89
+ // Rough estimate logic
90
+ let files = 10;
91
+ let sizeKB = 50;
92
+
93
+ selectedKeys.forEach(key => {
94
+ if (key === 'coding') { files += 20; sizeKB += 200; }
95
+ if (key === 'architect') { files += 15; sizeKB += 150; }
96
+ if (key === 'team') { files += 10; sizeKB += 50; }
97
+ if (key === 'design') { files += 15; sizeKB += 150; }
98
+ if (key === 'security') { files += 5; sizeKB += 20; }
99
+ });
82
100
 
83
- const estimates = {
84
- minimal: { files: 5, size: '~50KB' },
85
- developer: { files: 30, size: '~300KB' },
86
- ui_ux: { files: 25, size: '~250KB' },
87
- architect: { files: 50, size: '~500KB' },
88
- lead: { files: 40, size: '~400KB' },
89
- fullstack: { files: 400, size: '~5MB' },
101
+ return {
102
+ files: `~${files}`,
103
+ size: `~${Math.ceil(sizeKB)}KB`
90
104
  };
91
-
92
- return estimates[profileKey] || { files: '?', size: '?' };
93
105
  }
94
106
 
95
107
  module.exports = {
96
- PROFILES,
97
- getProfile,
98
- getProfileList,
99
- getProfileEstimate,
108
+ getCapabilities,
109
+ resolveCapabilities,
110
+ getInstallEstimate
100
111
  };