scene-capability-engine 3.3.5 → 3.3.10

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 (241) hide show
  1. package/CHANGELOG.md +130 -78
  2. package/README.md +6 -6
  3. package/README.zh.md +6 -6
  4. package/bin/scene-capability-engine.js +129 -7
  5. package/docs/331-poc-adaptation-roadmap.md +3 -3
  6. package/docs/331-poc-dual-track-integration-guide.md +8 -8
  7. package/docs/331-poc-weekly-delivery-checklist.md +6 -6
  8. package/docs/README.md +4 -0
  9. package/docs/adopt-migration-guide.md +13 -13
  10. package/docs/adoption-guide.md +28 -28
  11. package/docs/agent-hooks-analysis.md +10 -10
  12. package/docs/architecture.md +13 -13
  13. package/docs/articles/ai-driven-development-philosophy-and-practice.en.md +3 -3
  14. package/docs/articles/ai-driven-development-philosophy-and-practice.md +3 -3
  15. package/docs/autonomous-control-guide.md +35 -35
  16. package/docs/command-reference.md +192 -153
  17. package/docs/cross-tool-guide.md +7 -7
  18. package/docs/developer-guide.md +8 -8
  19. package/docs/document-governance.md +15 -15
  20. package/docs/environment-management-guide.md +6 -6
  21. package/docs/examples/add-export-command/design.md +1 -1
  22. package/docs/faq.md +13 -13
  23. package/docs/handoff-profile-integration-guide.md +3 -3
  24. package/docs/handoffs/evidence/ontology/moqui-template-baseline-2026-02-17-232922.json +7 -7
  25. package/docs/handoffs/evidence/ontology/moqui-template-baseline-2026-02-17-232922.md +1 -1
  26. package/docs/integration-modes.md +12 -12
  27. package/docs/integration-philosophy.md +11 -11
  28. package/docs/interactive-customization/331-poc-sce-integration-checklist.md +24 -24
  29. package/docs/interactive-customization/README.md +43 -43
  30. package/docs/interactive-customization/business-mode-policy-baseline.json +33 -0
  31. package/docs/interactive-customization/dual-ui-mode-integration-guide.md +1 -1
  32. package/docs/interactive-customization/moqui-adapter-interface.md +2 -2
  33. package/docs/interactive-customization/moqui-copilot-integration-guide.md +1 -1
  34. package/docs/interactive-customization/moqui-interactive-template-playbook.md +4 -4
  35. package/docs/interactive-customization/phase-acceptance-evidence.md +2 -2
  36. package/docs/knowledge-management-guide.md +6 -6
  37. package/docs/manual-workflows-guide.md +4 -4
  38. package/docs/moqui-capability-matrix.md +3 -3
  39. package/docs/moqui-standard-rebuild-guide.md +8 -8
  40. package/docs/moqui-template-core-library-playbook.md +27 -27
  41. package/docs/multi-agent-coordination-guide.md +19 -19
  42. package/docs/multi-repo-management-guide.md +17 -17
  43. package/docs/quick-start-with-ai-tools.md +7 -7
  44. package/docs/quick-start.md +2 -2
  45. package/docs/release-checklist.md +4 -4
  46. package/docs/sce-business-mode-map.md +103 -0
  47. package/docs/security-governance-default-baseline.md +12 -12
  48. package/docs/spec-collaboration-guide.md +3 -3
  49. package/docs/spec-locking-guide.md +2 -2
  50. package/docs/spec-workflow.md +3 -3
  51. package/docs/starter-kit/README.md +4 -4
  52. package/docs/starter-kit/handoff-manifest.starter.json +2 -2
  53. package/docs/starter-kit/release.workflow.sample.yml +1 -1
  54. package/docs/steering-strategy-guide.md +15 -15
  55. package/docs/team-collaboration-guide.md +69 -69
  56. package/docs/testing-strategy.md +2 -2
  57. package/docs/tools/claude-guide.md +14 -4
  58. package/docs/tools/cursor-guide.md +14 -14
  59. package/docs/tools/generic-guide.md +9 -9
  60. package/docs/tools/kiro-guide.md +4 -4
  61. package/docs/tools/vscode-guide.md +13 -13
  62. package/docs/tools/windsurf-guide.md +6 -6
  63. package/docs/troubleshooting.md +22 -22
  64. package/docs/upgrade-guide.md +8 -8
  65. package/docs/value-observability-guide.md +3 -3
  66. package/docs/zh/README.md +6 -0
  67. package/docs/zh/quick-start.md +15 -15
  68. package/docs/zh/release-checklist.md +3 -3
  69. package/docs/zh/tools/claude-guide.md +16 -6
  70. package/docs/zh/tools/cursor-guide.md +11 -11
  71. package/docs/zh/tools/generic-guide.md +13 -13
  72. package/docs/zh/tools/kiro-guide.md +2 -2
  73. package/docs/zh/tools/vscode-guide.md +11 -11
  74. package/docs/zh/tools/windsurf-guide.md +11 -11
  75. package/docs/zh/value-observability-guide.md +3 -3
  76. package/lib/adoption/adoption-logger.js +1 -1
  77. package/lib/adoption/adoption-strategy.js +28 -28
  78. package/lib/adoption/backup-manager.js +3 -3
  79. package/lib/adoption/conflict-resolver.js +2 -2
  80. package/lib/adoption/detection-engine.js +8 -8
  81. package/lib/adoption/error-formatter.js +4 -4
  82. package/lib/adoption/file-classifier.js +6 -6
  83. package/lib/adoption/progress-reporter.js +1 -1
  84. package/lib/adoption/smart-orchestrator.js +10 -10
  85. package/lib/adoption/strategy-selector.js +6 -6
  86. package/lib/adoption/summary-generator.js +1 -1
  87. package/lib/adoption/template-sync.js +8 -8
  88. package/lib/auto/autonomous-engine.js +7 -7
  89. package/lib/auto/checkpoint-manager.js +1 -1
  90. package/lib/auto/close-loop-runner.js +12 -12
  91. package/lib/auto/error-recovery-manager.js +1 -1
  92. package/lib/auto/goal-decomposer.js +1 -1
  93. package/lib/auto/moqui-recovery-sequence.js +2 -2
  94. package/lib/auto/progress-tracker.js +1 -1
  95. package/lib/auto/state-manager.js +1 -1
  96. package/lib/backup/backup-system.js +10 -10
  97. package/lib/backup/selective-backup.js +4 -4
  98. package/lib/collab/agent-registry.js +2 -2
  99. package/lib/collab/contract-manager.js +1 -1
  100. package/lib/collab/coordinator.js +2 -2
  101. package/lib/collab/dependency-manager.js +1 -1
  102. package/lib/collab/integration-manager.js +1 -1
  103. package/lib/collab/metadata-manager.js +1 -1
  104. package/lib/collab/multi-agent-config.js +2 -2
  105. package/lib/collab/spec-lifecycle-manager.js +2 -2
  106. package/lib/collab/visualizer.js +1 -1
  107. package/lib/commands/adopt.js +6 -6
  108. package/lib/commands/auto.js +56 -56
  109. package/lib/commands/collab.js +2 -2
  110. package/lib/commands/docs.js +3 -3
  111. package/lib/commands/doctor.js +1 -1
  112. package/lib/commands/knowledge.js +2 -2
  113. package/lib/commands/lock.js +1 -1
  114. package/lib/commands/ops.js +1 -1
  115. package/lib/commands/orchestrate.js +3 -3
  116. package/lib/commands/rollback.js +1 -1
  117. package/lib/commands/scene.js +135 -93
  118. package/lib/commands/session.js +139 -0
  119. package/lib/commands/spec-bootstrap.js +1 -1
  120. package/lib/commands/spec-gate.js +2 -2
  121. package/lib/commands/spec-pipeline.js +1 -1
  122. package/lib/commands/status.js +4 -4
  123. package/lib/commands/steering.js +119 -0
  124. package/lib/commands/value.js +1 -1
  125. package/lib/commands/watch.js +9 -9
  126. package/lib/commands/workspace-multi.js +1 -1
  127. package/lib/context/context-exporter.js +5 -7
  128. package/lib/context/prompt-generator.js +2 -2
  129. package/lib/environment/backup-system.js +1 -1
  130. package/lib/environment/environment-manager.js +2 -2
  131. package/lib/gitignore/gitignore-backup.js +3 -3
  132. package/lib/gitignore/gitignore-detector.js +13 -13
  133. package/lib/gitignore/gitignore-integration.js +3 -3
  134. package/lib/gitignore/gitignore-transformer.js +4 -4
  135. package/lib/gitignore/layered-rules-template.js +16 -16
  136. package/lib/governance/config-manager.js +1 -1
  137. package/lib/governance/doc-reference-checker.js +4 -4
  138. package/lib/governance/execution-logger.js +1 -1
  139. package/lib/governance/file-scanner.js +3 -3
  140. package/lib/interactive-customization/moqui-interactive-adapter.js +2 -2
  141. package/lib/knowledge/knowledge-manager.js +1 -1
  142. package/lib/lock/lock-manager.js +2 -2
  143. package/lib/lock/steering-file-lock.js +5 -5
  144. package/lib/lock/task-lock-manager.js +3 -3
  145. package/lib/operations/audit-logger.js +1 -1
  146. package/lib/operations/feedback-manager.js +1 -1
  147. package/lib/operations/operations-manager.js +3 -3
  148. package/lib/operations/permission-manager.js +2 -2
  149. package/lib/operations/template-loader.js +1 -1
  150. package/lib/orchestrator/agent-spawner.js +27 -2
  151. package/lib/orchestrator/bootstrap-prompt-builder.js +6 -6
  152. package/lib/orchestrator/orchestration-engine.js +1 -1
  153. package/lib/orchestrator/orchestrator-config.js +2 -2
  154. package/lib/repo/config-manager.js +3 -3
  155. package/lib/repo/handlers/init-handler.js +1 -1
  156. package/lib/repo/repo-manager.js +2 -2
  157. package/lib/runtime/business-mode-resolver.js +240 -0
  158. package/lib/runtime/session-store.js +207 -0
  159. package/lib/runtime/steering-contract.js +338 -0
  160. package/lib/scene-runtime/audit-emitter.js +1 -1
  161. package/lib/scene-runtime/binding-plugin-loader.js +3 -3
  162. package/lib/scene-runtime/eval-bridge.js +1 -1
  163. package/lib/scene-runtime/index.js +1 -1
  164. package/lib/scene-runtime/moqui-extractor.js +1 -1
  165. package/lib/scene-runtime/plan-compiler.js +1 -1
  166. package/lib/scene-runtime/policy-gate.js +1 -1
  167. package/lib/scene-runtime/runtime-executor.js +1 -1
  168. package/lib/scene-runtime/scene-loader.js +1 -1
  169. package/lib/spec/bootstrap/context-collector.js +1 -1
  170. package/lib/spec/pipeline/stage-adapters.js +3 -3
  171. package/lib/spec/pipeline/state-store.js +1 -1
  172. package/lib/spec-gate/policy/policy-loader.js +1 -1
  173. package/lib/spec-gate/rules/default-rules.js +6 -6
  174. package/lib/steering/adoption-config.js +1 -1
  175. package/lib/steering/compliance-error-reporter.js +3 -3
  176. package/lib/steering/context-sync-manager.js +2 -2
  177. package/lib/steering/index.js +1 -1
  178. package/lib/steering/spec-steering.js +2 -2
  179. package/lib/steering/steering-compliance-checker.js +1 -1
  180. package/lib/steering/steering-loader.js +4 -5
  181. package/lib/steering/steering-manager.js +4 -4
  182. package/lib/task/task-claimer.js +5 -5
  183. package/lib/task/task-status-store.js +2 -2
  184. package/lib/templates/content-generalizer.js +1 -1
  185. package/lib/templates/spec-reader.js +2 -2
  186. package/lib/templates/template-creator.js +1 -1
  187. package/lib/templates/template-exporter.js +3 -3
  188. package/lib/templates/template-manager.js +1 -1
  189. package/lib/upgrade/migration-engine.js +3 -3
  190. package/lib/upgrade/migrations/1.0.0-to-1.1.0.js +1 -1
  191. package/lib/utils/file-diff.js +6 -6
  192. package/lib/utils/tool-detector.js +10 -10
  193. package/lib/utils/validation.js +5 -5
  194. package/lib/value/metric-contract-loader.js +1 -1
  195. package/lib/version/version-manager.js +1 -1
  196. package/lib/watch/execution-logger.js +1 -1
  197. package/lib/watch/presets.js +8 -8
  198. package/lib/watch/watch-manager.js +2 -2
  199. package/lib/workspace/legacy-kiro-migrator.js +275 -0
  200. package/lib/workspace/multi/workspace-context-resolver.js +2 -2
  201. package/lib/workspace/multi/workspace-registry.js +2 -2
  202. package/lib/workspace/multi/workspace-state-manager.js +3 -3
  203. package/lib/workspace/workspace-manager.js +1 -1
  204. package/lib/workspace/workspace-sync.js +2 -2
  205. package/locales/en.json +4 -4
  206. package/locales/zh.json +4 -4
  207. package/package.json +9 -9
  208. package/template/{.kiro → .sce}/README.md +15 -15
  209. package/template/{.kiro → .sce}/hooks/check-spec-on-create.kiro.hook +2 -2
  210. package/template/{.kiro → .sce}/steering/CORE_PRINCIPLES.md +4 -4
  211. package/template/{.kiro → .sce}/steering/CURRENT_CONTEXT.md +1 -1
  212. package/template/{.kiro → .sce}/steering/ENVIRONMENT.md +3 -3
  213. package/template/{.kiro → .sce}/tools/backup_manager.py +3 -3
  214. package/template/{.kiro → .sce}/tools/configuration_manager.py +1 -1
  215. package/template/README.md +12 -12
  216. /package/template/{.kiro → .sce}/hooks/run-tests-on-save.kiro.hook +0 -0
  217. /package/template/{.kiro → .sce}/hooks/sync-tasks-on-edit.kiro.hook +0 -0
  218. /package/template/{.kiro → .sce}/specs/SPEC_WORKFLOW_GUIDE.md +0 -0
  219. /package/template/{.kiro → .sce}/steering/RULES_GUIDE.md +0 -0
  220. /package/template/{.kiro → .sce}/templates/operations/default/change-impact.md +0 -0
  221. /package/template/{.kiro → .sce}/templates/operations/default/deployment.md +0 -0
  222. /package/template/{.kiro → .sce}/templates/operations/default/feedback-response.md +0 -0
  223. /package/template/{.kiro → .sce}/templates/operations/default/migration-plan.md +0 -0
  224. /package/template/{.kiro → .sce}/templates/operations/default/monitoring.md +0 -0
  225. /package/template/{.kiro → .sce}/templates/operations/default/operations.md +0 -0
  226. /package/template/{.kiro → .sce}/templates/operations/default/rollback.md +0 -0
  227. /package/template/{.kiro → .sce}/templates/operations/default/tools.yaml +0 -0
  228. /package/template/{.kiro → .sce}/templates/operations/default/troubleshooting.md +0 -0
  229. /package/template/{.kiro → .sce}/tools/document_evaluator.py +0 -0
  230. /package/template/{.kiro → .sce}/tools/enhancement_logger.py +0 -0
  231. /package/template/{.kiro → .sce}/tools/error_handler.py +0 -0
  232. /package/template/{.kiro → .sce}/tools/improvement_identifier.py +0 -0
  233. /package/template/{.kiro → .sce}/tools/modification_applicator.py +0 -0
  234. /package/template/{.kiro → .sce}/tools/quality_gate_enforcer.py +0 -0
  235. /package/template/{.kiro → .sce}/tools/quality_scorer.py +0 -0
  236. /package/template/{.kiro → .sce}/tools/report_generator.py +0 -0
  237. /package/template/{.kiro → .sce}/tools/ultrawork_enhancer.py +0 -0
  238. /package/template/{.kiro → .sce}/tools/ultrawork_enhancer_refactored.py +0 -0
  239. /package/template/{.kiro → .sce}/tools/ultrawork_enhancer_v2.py +0 -0
  240. /package/template/{.kiro → .sce}/tools/ultrawork_enhancer_v3.py +0 -0
  241. /package/template/{.kiro → .sce}/tools/workflow_quality_gate.py +0 -0
@@ -9,8 +9,8 @@ const inquirer = require('inquirer');
9
9
  */
10
10
  class SteeringManager {
11
11
  constructor() {
12
- this.steeringDir = '.kiro/steering';
13
- this.backupBaseDir = '.kiro/backups';
12
+ this.steeringDir = '.sce/steering';
13
+ this.backupBaseDir = '.sce/backups';
14
14
  }
15
15
 
16
16
  /**
@@ -83,7 +83,7 @@ class SteeringManager {
83
83
  });
84
84
 
85
85
  console.log('');
86
- console.log('AI IDE loads all files in .kiro/steering/, which means you must');
86
+ console.log('AI IDE loads all files in .sce/steering/, which means you must');
87
87
  console.log('choose between sce steering rules OR your project\'s existing rules.');
88
88
  console.log('');
89
89
 
@@ -169,7 +169,7 @@ class SteeringManager {
169
169
  */
170
170
  async installKseSteering(projectPath) {
171
171
  const steeringPath = path.join(projectPath, this.steeringDir);
172
- const templatePath = path.join(__dirname, '../../template/.kiro/steering');
172
+ const templatePath = path.join(__dirname, '../../template/.sce/steering');
173
173
 
174
174
  try {
175
175
  // 确保 steering 目录存在
@@ -202,7 +202,7 @@ class TaskClaimer {
202
202
  * @returns {Promise<Object>} 认领结果
203
203
  */
204
204
  async claimTask(projectPath, specName, taskId, username, force = false) {
205
- const tasksPath = path.join(projectPath, '.kiro/specs', specName, 'tasks.md');
205
+ const tasksPath = path.join(projectPath, '.sce/specs', specName, 'tasks.md');
206
206
 
207
207
  try {
208
208
  // 检查文件是否存在
@@ -284,7 +284,7 @@ class TaskClaimer {
284
284
  * @returns {Promise<Object>} 释放结果
285
285
  */
286
286
  async unclaimTask(projectPath, specName, taskId, username) {
287
- const tasksPath = path.join(projectPath, '.kiro/specs', specName, 'tasks.md');
287
+ const tasksPath = path.join(projectPath, '.sce/specs', specName, 'tasks.md');
288
288
 
289
289
  try {
290
290
  // 检查文件是否存在
@@ -360,7 +360,7 @@ class TaskClaimer {
360
360
  * @returns {Promise<Array>} 已认领的任务列表
361
361
  */
362
362
  async getClaimedTasks(projectPath, specName) {
363
- const tasksPath = path.join(projectPath, '.kiro/specs', specName, 'tasks.md');
363
+ const tasksPath = path.join(projectPath, '.sce/specs', specName, 'tasks.md');
364
364
 
365
365
  try {
366
366
  const exists = await fs.pathExists(tasksPath);
@@ -397,7 +397,7 @@ class TaskClaimer {
397
397
  * @returns {Promise<Object>} 更新结果
398
398
  */
399
399
  async updateTaskStatus(projectPath, specName, taskId, status) {
400
- const tasksPath = path.join(projectPath, '.kiro/specs', specName, 'tasks.md');
400
+ const tasksPath = path.join(projectPath, '.sce/specs', specName, 'tasks.md');
401
401
 
402
402
  try {
403
403
  const exists = await fs.pathExists(tasksPath);
@@ -461,7 +461,7 @@ class TaskClaimer {
461
461
  * @returns {Promise<Array>} 所有已认领的任务
462
462
  */
463
463
  async getAllClaimedTasks(projectPath) {
464
- const specsPath = path.join(projectPath, '.kiro/specs');
464
+ const specsPath = path.join(projectPath, '.sce/specs');
465
465
 
466
466
  try {
467
467
  const exists = await fs.pathExists(specsPath);
@@ -233,7 +233,7 @@ class TaskStatusStore {
233
233
  * @returns {string}
234
234
  */
235
235
  _tasksPath(specName) {
236
- return path.join(this._workspaceRoot, '.kiro/specs', specName, 'tasks.md');
236
+ return path.join(this._workspaceRoot, '.sce/specs', specName, 'tasks.md');
237
237
  }
238
238
 
239
239
  /**
@@ -242,7 +242,7 @@ class TaskStatusStore {
242
242
  * @returns {string}
243
243
  */
244
244
  _lockPath(specName) {
245
- return path.join(this._workspaceRoot, '.kiro/specs', specName, 'tasks.md.lock');
245
+ return path.join(this._workspaceRoot, '.sce/specs', specName, 'tasks.md.lock');
246
246
  }
247
247
 
248
248
  // ---------------------------------------------------------------------------
@@ -152,7 +152,7 @@ class ContentGeneralizer {
152
152
  if (specMetadata.specPath) {
153
153
  replacements.push({
154
154
  pattern: new RegExp(this.escapeRegex(specMetadata.specPath), 'g'),
155
- variable: '.kiro/specs/{{SPEC_NAME}}',
155
+ variable: '.sce/specs/{{SPEC_NAME}}',
156
156
  priority: 5,
157
157
  description: 'Spec path'
158
158
  });
@@ -1,5 +1,5 @@
1
1
  /**
2
- * SpecReader - Reads and validates Spec files from .kiro/specs/ directory
2
+ * SpecReader - Reads and validates Spec files from .sce/specs/ directory
3
3
  */
4
4
 
5
5
  const fs = require('fs').promises;
@@ -8,7 +8,7 @@ const { execSync } = require('child_process');
8
8
 
9
9
  class SpecReader {
10
10
  constructor() {
11
- this.specsDir = '.kiro/specs';
11
+ this.specsDir = '.sce/specs';
12
12
  }
13
13
 
14
14
  /**
@@ -180,7 +180,7 @@ class TemplateCreator {
180
180
 
181
181
  // Check for remaining project-specific content (high confidence patterns)
182
182
  const projectSpecificPatterns = [
183
- /\.kiro\/specs\/\d+-\d+-[a-z-]+/g, // Specific spec paths
183
+ /\.sce\/specs\/\d+-\d+-[a-z-]+/g, // Specific spec paths
184
184
  /scene-capability-engine/g, // Project name (unless it's the template itself)
185
185
  ];
186
186
 
@@ -7,7 +7,7 @@ const path = require('path');
7
7
 
8
8
  class TemplateExporter {
9
9
  constructor() {
10
- this.defaultOutputDir = '.kiro/templates/exports';
10
+ this.defaultOutputDir = '.sce/templates/exports';
11
11
  }
12
12
 
13
13
  /**
@@ -177,7 +177,7 @@ Test your template locally before submitting:
177
177
  sce spec create test-spec --template ${metadata.name}
178
178
 
179
179
  # Verify the generated Spec is correct
180
- cd .kiro/specs/test-spec
180
+ cd .sce/specs/test-spec
181
181
  # Check that variables were replaced correctly
182
182
  \`\`\`
183
183
 
@@ -404,7 +404,7 @@ sce templates show ${metadata.category}/${metadata.name}
404
404
  sce spec create my-new-feature --template ${metadata.category}/${metadata.name}
405
405
  \`\`\`
406
406
 
407
- This will create a new Spec at \`.kiro/specs/XX-00-my-new-feature/\` with:
407
+ This will create a new Spec at \`.sce/specs/XX-00-my-new-feature/\` with:
408
408
  - \`requirements.md\` - Requirements document
409
409
  - \`design.md\` - Design document
410
410
  - \`tasks.md\` - Implementation tasks
@@ -716,7 +716,7 @@ class TemplateManager {
716
716
  }
717
717
 
718
718
  // Determine target directory
719
- const targetDir = path.join(process.cwd(), '.kiro', 'specs', specName);
719
+ const targetDir = path.join(process.cwd(), '.sce', 'specs', specName);
720
720
 
721
721
  // Apply template
722
722
  const result = await this.applicator.applyTemplate(
@@ -299,12 +299,12 @@ class MigrationEngine {
299
299
  const warnings = [];
300
300
 
301
301
  try {
302
- // Check if .kiro/ directory exists
303
- const kiroPath = path.join(projectPath, '.kiro');
302
+ // Check if .sce/ directory exists
303
+ const kiroPath = path.join(projectPath, '.sce');
304
304
  const kiroExists = await pathExists(kiroPath);
305
305
 
306
306
  if (!kiroExists) {
307
- errors.push('.kiro/ directory not found');
307
+ errors.push('.sce/ directory not found');
308
308
  return { success: false, errors, warnings };
309
309
  }
310
310
 
@@ -26,7 +26,7 @@ module.exports = {
26
26
  const changes = [];
27
27
 
28
28
  try {
29
- const kiroPath = path.join(projectPath, '.kiro');
29
+ const kiroPath = path.join(projectPath, '.sce');
30
30
 
31
31
  // 1. Ensure backups/ directory exists
32
32
  const backupsPath = path.join(kiroPath, 'backups');
@@ -157,12 +157,12 @@ class FileDiff {
157
157
  */
158
158
  async compareSteeringFiles(projectRoot, templateRoot) {
159
159
  const steeringFiles = [
160
- '.kiro/steering/CORE_PRINCIPLES.md',
161
- '.kiro/steering/ENVIRONMENT.md',
162
- '.kiro/steering/CURRENT_CONTEXT.md',
163
- '.kiro/steering/RULES_GUIDE.md',
164
- '.kiro/specs/SPEC_WORKFLOW_GUIDE.md',
165
- '.kiro/README.md'
160
+ '.sce/steering/CORE_PRINCIPLES.md',
161
+ '.sce/steering/ENVIRONMENT.md',
162
+ '.sce/steering/CURRENT_CONTEXT.md',
163
+ '.sce/steering/RULES_GUIDE.md',
164
+ '.sce/specs/SPEC_WORKFLOW_GUIDE.md',
165
+ '.sce/README.md'
166
166
  ];
167
167
 
168
168
  const filePairs = steeringFiles.map(file => ({
@@ -63,19 +63,19 @@ async function detectKiroIDE(projectPath) {
63
63
  let detected = false;
64
64
  let confidence = 'low';
65
65
 
66
- // Check for .kiro directory
67
- const kiroDir = path.join(projectPath, '.kiro');
66
+ // Check for .sce directory
67
+ const kiroDir = path.join(projectPath, '.sce');
68
68
  if (await fs.pathExists(kiroDir)) {
69
- indicators.push('.kiro directory exists');
69
+ indicators.push('.sce directory exists');
70
70
  detected = true;
71
71
  confidence = 'medium';
72
72
  }
73
73
 
74
74
  // Check for SCE-specific files
75
75
  const kiroFiles = [
76
- '.kiro/steering',
77
- '.kiro/specs',
78
- '.kiro/tools'
76
+ '.sce/steering',
77
+ '.sce/specs',
78
+ '.sce/tools'
79
79
  ];
80
80
 
81
81
  for (const file of kiroFiles) {
@@ -87,7 +87,7 @@ async function detectKiroIDE(projectPath) {
87
87
  }
88
88
 
89
89
  // Check for environment variables (if running in SCE)
90
- if (process.env.KIRO_IDE === 'true' || process.env.KIRO_VERSION) {
90
+ if (process.env.sce_IDE === 'true' || process.env.sce_VERSION) {
91
91
  indicators.push('SCE environment variables detected');
92
92
  detected = true;
93
93
  confidence = 'high';
@@ -215,7 +215,7 @@ function getRecommendations(primaryTool, detections) {
215
215
  type: 'native',
216
216
  title: 'Use SCE Agent Hooks',
217
217
  description: 'You can use native SCE agent hooks for seamless automation',
218
- action: 'Configure hooks in .kiro/hooks/'
218
+ action: 'Configure hooks in .sce/hooks/'
219
219
  });
220
220
  recommendations.push({
221
221
  type: 'optional',
@@ -317,7 +317,7 @@ async function generateAutoConfig(detection, projectPath) {
317
317
  case 'SCE':
318
318
  config.suggestedPresets = [];
319
319
  config.suggestedCommands = [
320
- 'Use native SCE agent hooks (see .kiro/hooks/)',
320
+ 'Use native SCE agent hooks (see .sce/hooks/)',
321
321
  'Optional: sce watch init (for watch mode fallback)'
322
322
  ];
323
323
  config.notes.push('AI IDE detected - native hooks are recommended');
@@ -332,7 +332,7 @@ async function generateAutoConfig(detection, projectPath) {
332
332
  'sce watch install auto-sync',
333
333
  'sce watch start'
334
334
  ];
335
- config.configPath = path.join(projectPath, '.kiro/watch-config.json');
335
+ config.configPath = path.join(projectPath, '.sce/watch-config.json');
336
336
  config.notes.push(`${primaryTool === 'vscode' ? 'VS Code' : 'Cursor'} detected - watch mode recommended`);
337
337
  config.notes.push('Run suggested commands to set up automation');
338
338
  break;
@@ -21,12 +21,12 @@ async function validateProjectStructure(projectPath) {
21
21
  const warnings = [];
22
22
 
23
23
  try {
24
- const kiroPath = path.join(projectPath, '.kiro');
24
+ const kiroPath = path.join(projectPath, '.sce');
25
25
 
26
- // Check if .kiro/ directory exists
26
+ // Check if .sce/ directory exists
27
27
  const kiroExists = await pathExists(kiroPath);
28
28
  if (!kiroExists) {
29
- errors.push('.kiro/ directory not found');
29
+ errors.push('.sce/ directory not found');
30
30
  return { success: false, errors, warnings };
31
31
  }
32
32
 
@@ -110,7 +110,7 @@ async function validateVersionFile(projectPath) {
110
110
  const warnings = [];
111
111
 
112
112
  try {
113
- const versionPath = path.join(projectPath, '.kiro', 'version.json');
113
+ const versionPath = path.join(projectPath, '.sce', 'version.json');
114
114
 
115
115
  // Check if version.json exists
116
116
  const exists = await pathExists(versionPath);
@@ -190,7 +190,7 @@ async function validateDependencies(projectPath) {
190
190
  }
191
191
 
192
192
  // Check Python version (if Ultrawork tools are present)
193
- const toolPath = path.join(projectPath, '.kiro/tools/ultrawork_enhancer.py');
193
+ const toolPath = path.join(projectPath, '.sce/tools/ultrawork_enhancer.py');
194
194
  const toolExists = await pathExists(toolPath);
195
195
 
196
196
  if (toolExists) {
@@ -49,7 +49,7 @@ class MetricContractLoader {
49
49
  getDefaultPath() {
50
50
  return path.join(
51
51
  this.projectPath,
52
- '.kiro',
52
+ '.sce',
53
53
  'specs',
54
54
  '112-00-spec-value-realization-program',
55
55
  'custom',
@@ -32,7 +32,7 @@ class VersionManager {
32
32
  * @returns {string} - Absolute path to version.json
33
33
  */
34
34
  getVersionFilePath(projectPath) {
35
- return path.join(projectPath, '.kiro', this.versionFileName);
35
+ return path.join(projectPath, '.sce', this.versionFileName);
36
36
  }
37
37
 
38
38
  /**
@@ -12,7 +12,7 @@ class ExecutionLogger extends EventEmitter {
12
12
  super();
13
13
 
14
14
  this.config = {
15
- logDir: config.logDir || '.kiro/watch/logs',
15
+ logDir: config.logDir || '.sce/watch/logs',
16
16
  logFile: config.logFile || 'execution.log',
17
17
  maxLogSize: config.maxLogSize || 10 * 1024 * 1024, // 10MB
18
18
  maxLogFiles: config.maxLogFiles || 5,
@@ -33,17 +33,17 @@ const promptRegenPreset = {
33
33
  name: 'prompt-regen',
34
34
  description: 'Regenerate prompts when requirements or design changes',
35
35
  patterns: [
36
- '**/.kiro/specs/*/requirements.md',
37
- '**/.kiro/specs/*/design.md'
36
+ '**/.sce/specs/*/requirements.md',
37
+ '**/.sce/specs/*/design.md'
38
38
  ],
39
39
  actions: {
40
- '**/.kiro/specs/*/requirements.md': {
40
+ '**/.sce/specs/*/requirements.md': {
41
41
  command: 'sce prompt regenerate ${spec}',
42
42
  debounce: 5000,
43
43
  retry: true,
44
44
  description: 'Regenerate prompts when requirements change'
45
45
  },
46
- '**/.kiro/specs/*/design.md': {
46
+ '**/.sce/specs/*/design.md': {
47
47
  command: 'sce prompt regenerate ${spec}',
48
48
  debounce: 5000,
49
49
  retry: true,
@@ -53,8 +53,8 @@ const promptRegenPreset = {
53
53
  debounce: {
54
54
  default: 5000,
55
55
  perPattern: {
56
- '**/.kiro/specs/*/requirements.md': 5000,
57
- '**/.kiro/specs/*/design.md': 5000
56
+ '**/.sce/specs/*/requirements.md': 5000,
57
+ '**/.sce/specs/*/design.md': 5000
58
58
  }
59
59
  }
60
60
  };
@@ -66,9 +66,9 @@ const promptRegenPreset = {
66
66
  const contextExportPreset = {
67
67
  name: 'context-export',
68
68
  description: 'Export context when work is complete',
69
- patterns: ['**/.kiro/specs/*/.complete'],
69
+ patterns: ['**/.sce/specs/*/.complete'],
70
70
  actions: {
71
- '**/.kiro/specs/*/.complete': {
71
+ '**/.sce/specs/*/.complete': {
72
72
  command: 'sce context export ${spec}',
73
73
  debounce: 1000,
74
74
  retry: true,
@@ -16,7 +16,7 @@ class WatchManager extends EventEmitter {
16
16
  super();
17
17
 
18
18
  this.config = {
19
- configFile: config.configFile || '.kiro/watch-config.json',
19
+ configFile: config.configFile || '.sce/watch-config.json',
20
20
  basePath: config.basePath || process.cwd(),
21
21
  autoStart: config.autoStart !== false,
22
22
  ...config
@@ -150,7 +150,7 @@ class WatchManager extends EventEmitter {
150
150
  async _initializeComponents() {
151
151
  // 1. 初始化 logger
152
152
  this.logger = new ExecutionLogger({
153
- logDir: path.join(this.config.basePath, '.kiro/watch/logs'),
153
+ logDir: path.join(this.config.basePath, '.sce/watch/logs'),
154
154
  logLevel: this.watchConfig.logging?.level || 'info',
155
155
  maxLogSize: this._parseSize(this.watchConfig.logging?.maxSize || '10MB'),
156
156
  enableRotation: this.watchConfig.logging?.rotation !== false
@@ -0,0 +1,275 @@
1
+ const fs = require('fs-extra');
2
+ const path = require('path');
3
+
4
+ const LEGACY_DIRNAME = '.kiro';
5
+ const TARGET_DIRNAME = '.sce';
6
+ const DEFAULT_MAX_DEPTH = 6;
7
+ const DEFAULT_IGNORE_DIRS = new Set([
8
+ '.git',
9
+ 'node_modules',
10
+ TARGET_DIRNAME,
11
+ 'dist',
12
+ 'build',
13
+ 'coverage',
14
+ '.next',
15
+ ]);
16
+
17
+ async function findLegacyKiroDirectories(rootDir, options = {}) {
18
+ const maxDepth = Number.isInteger(options.maxDepth) ? options.maxDepth : DEFAULT_MAX_DEPTH;
19
+ const ignoreDirs = options.ignoreDirs instanceof Set
20
+ ? options.ignoreDirs
21
+ : DEFAULT_IGNORE_DIRS;
22
+ const results = [];
23
+
24
+ async function walk(currentDir, depth) {
25
+ if (depth > maxDepth) {
26
+ return;
27
+ }
28
+ let entries;
29
+ try {
30
+ entries = await fs.readdir(currentDir, { withFileTypes: true });
31
+ } catch (_error) {
32
+ return;
33
+ }
34
+
35
+ for (const entry of entries) {
36
+ if (!entry.isDirectory()) {
37
+ continue;
38
+ }
39
+ const fullPath = path.join(currentDir, entry.name);
40
+ if (entry.name === LEGACY_DIRNAME) {
41
+ results.push(fullPath);
42
+ continue;
43
+ }
44
+ if (ignoreDirs.has(entry.name)) {
45
+ continue;
46
+ }
47
+ await walk(fullPath, depth + 1);
48
+ }
49
+ }
50
+
51
+ await walk(rootDir, 0);
52
+ results.sort((a, b) => a.length - b.length);
53
+ return results;
54
+ }
55
+
56
+ async function migrateLegacyKiroDirectories(rootDir, options = {}) {
57
+ const dryRun = options.dryRun === true;
58
+ const legacyDirs = await findLegacyKiroDirectories(rootDir, options);
59
+ const report = {
60
+ root: rootDir,
61
+ dryRun,
62
+ scanned: legacyDirs.length,
63
+ migrated: 0,
64
+ renamed: 0,
65
+ merged: 0,
66
+ moved_files: 0,
67
+ deduped_files: 0,
68
+ conflict_files: 0,
69
+ details: [],
70
+ };
71
+
72
+ // Deepest first avoids parent directory interactions in nested projects.
73
+ const ordered = [...legacyDirs].sort((a, b) => b.length - a.length);
74
+ for (const legacyDir of ordered) {
75
+ const detail = await _migrateSingleLegacyDirectory(legacyDir, { dryRun });
76
+ report.details.push(detail);
77
+ if (!detail.success) {
78
+ continue;
79
+ }
80
+ report.migrated += 1;
81
+ report.renamed += detail.action === 'rename' ? 1 : 0;
82
+ report.merged += detail.action === 'merge' ? 1 : 0;
83
+ report.moved_files += detail.moved_files || 0;
84
+ report.deduped_files += detail.deduped_files || 0;
85
+ report.conflict_files += detail.conflict_files || 0;
86
+ }
87
+
88
+ return report;
89
+ }
90
+
91
+ async function autoMigrateLegacyKiroDirectories(rootDir, options = {}) {
92
+ const dryRun = options.dryRun === true;
93
+ const report = await migrateLegacyKiroDirectories(rootDir, {
94
+ ...options,
95
+ dryRun,
96
+ });
97
+ return {
98
+ detected: report.scanned,
99
+ migrated: report.migrated,
100
+ report,
101
+ };
102
+ }
103
+
104
+ async function _migrateSingleLegacyDirectory(legacyDir, options) {
105
+ const dryRun = options.dryRun === true;
106
+ const parentDir = path.dirname(legacyDir);
107
+ const targetDir = path.join(parentDir, TARGET_DIRNAME);
108
+ const detail = {
109
+ source: legacyDir,
110
+ target: targetDir,
111
+ success: true,
112
+ action: 'rename',
113
+ moved_files: 0,
114
+ deduped_files: 0,
115
+ conflict_files: 0,
116
+ errors: [],
117
+ };
118
+
119
+ try {
120
+ const targetExists = await fs.pathExists(targetDir);
121
+ if (!targetExists) {
122
+ if (!dryRun) {
123
+ await fs.move(legacyDir, targetDir, { overwrite: false });
124
+ }
125
+ return detail;
126
+ }
127
+
128
+ detail.action = 'merge';
129
+ const mergeReport = await _mergeLegacyIntoTarget(legacyDir, targetDir, { dryRun });
130
+ detail.moved_files = mergeReport.moved_files;
131
+ detail.deduped_files = mergeReport.deduped_files;
132
+ detail.conflict_files = mergeReport.conflict_files;
133
+ detail.errors.push(...mergeReport.errors);
134
+ detail.success = mergeReport.errors.length === 0;
135
+ return detail;
136
+ } catch (error) {
137
+ detail.success = false;
138
+ detail.errors.push(error.message);
139
+ return detail;
140
+ }
141
+ }
142
+
143
+ async function _mergeLegacyIntoTarget(legacyDir, targetDir, options) {
144
+ const dryRun = options.dryRun === true;
145
+ const report = {
146
+ moved_files: 0,
147
+ deduped_files: 0,
148
+ conflict_files: 0,
149
+ errors: [],
150
+ };
151
+ const files = await _listFilesRecursive(legacyDir);
152
+
153
+ for (const sourcePath of files) {
154
+ const relative = path.relative(legacyDir, sourcePath);
155
+ const targetPath = path.join(targetDir, relative);
156
+ try {
157
+ const targetExists = await fs.pathExists(targetPath);
158
+ if (!targetExists) {
159
+ report.moved_files += 1;
160
+ if (!dryRun) {
161
+ await fs.ensureDir(path.dirname(targetPath));
162
+ await fs.move(sourcePath, targetPath, { overwrite: false });
163
+ }
164
+ continue;
165
+ }
166
+
167
+ const same = await _isSameFile(sourcePath, targetPath);
168
+ if (same) {
169
+ report.deduped_files += 1;
170
+ if (!dryRun) {
171
+ await fs.remove(sourcePath);
172
+ }
173
+ continue;
174
+ }
175
+
176
+ const conflictPath = await _nextConflictPath(targetPath);
177
+ report.conflict_files += 1;
178
+ if (!dryRun) {
179
+ await fs.ensureDir(path.dirname(conflictPath));
180
+ await fs.move(sourcePath, conflictPath, { overwrite: false });
181
+ }
182
+ } catch (error) {
183
+ report.errors.push(`${sourcePath}: ${error.message}`);
184
+ }
185
+ }
186
+
187
+ if (!dryRun) {
188
+ await _removeEmptyDirectories(legacyDir);
189
+ if (await fs.pathExists(legacyDir)) {
190
+ const remaining = await fs.readdir(legacyDir);
191
+ if (remaining.length === 0) {
192
+ await fs.remove(legacyDir);
193
+ }
194
+ }
195
+ }
196
+
197
+ return report;
198
+ }
199
+
200
+ async function _listFilesRecursive(rootDir) {
201
+ const files = [];
202
+
203
+ async function walk(currentDir) {
204
+ let entries = [];
205
+ try {
206
+ entries = await fs.readdir(currentDir, { withFileTypes: true });
207
+ } catch (_error) {
208
+ return;
209
+ }
210
+ for (const entry of entries) {
211
+ const fullPath = path.join(currentDir, entry.name);
212
+ if (entry.isDirectory()) {
213
+ await walk(fullPath);
214
+ } else if (entry.isFile()) {
215
+ files.push(fullPath);
216
+ }
217
+ }
218
+ }
219
+
220
+ await walk(rootDir);
221
+ return files;
222
+ }
223
+
224
+ async function _isSameFile(leftPath, rightPath) {
225
+ const [leftBuffer, rightBuffer] = await Promise.all([
226
+ fs.readFile(leftPath),
227
+ fs.readFile(rightPath),
228
+ ]);
229
+ return leftBuffer.equals(rightBuffer);
230
+ }
231
+
232
+ async function _nextConflictPath(targetPath) {
233
+ const { dir, name, ext } = path.parse(targetPath);
234
+ let counter = 1;
235
+ while (true) {
236
+ const candidate = path.join(dir, `${name}.legacy-kiro-${counter}${ext}`);
237
+ if (!await fs.pathExists(candidate)) {
238
+ return candidate;
239
+ }
240
+ counter += 1;
241
+ }
242
+ }
243
+
244
+ async function _removeEmptyDirectories(rootDir) {
245
+ let entries = [];
246
+ try {
247
+ entries = await fs.readdir(rootDir, { withFileTypes: true });
248
+ } catch (_error) {
249
+ return;
250
+ }
251
+ for (const entry of entries) {
252
+ if (!entry.isDirectory()) {
253
+ continue;
254
+ }
255
+ const fullPath = path.join(rootDir, entry.name);
256
+ await _removeEmptyDirectories(fullPath);
257
+ try {
258
+ const childEntries = await fs.readdir(fullPath);
259
+ if (childEntries.length === 0) {
260
+ await fs.rmdir(fullPath);
261
+ }
262
+ } catch (_error) {
263
+ // Ignore delete race/errors.
264
+ }
265
+ }
266
+ }
267
+
268
+ module.exports = {
269
+ LEGACY_DIRNAME,
270
+ TARGET_DIRNAME,
271
+ findLegacyKiroDirectories,
272
+ migrateLegacyKiroDirectories,
273
+ autoMigrateLegacyKiroDirectories,
274
+ };
275
+