@lumenflow/cli 3.1.1 → 3.1.3
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 +36 -35
- package/dist/agent-issues-query.js +13 -8
- package/dist/agent-log-issue.js +15 -4
- package/dist/agent-session-end.js +15 -4
- package/dist/agent-session.js +18 -6
- package/dist/backlog-prune.js +1 -1
- package/dist/commands/integrate.js +32 -18
- package/dist/config-get.js +27 -15
- package/dist/config-set.js +104 -37
- package/dist/delegation-list.js +1 -1
- package/dist/doctor.js +19 -13
- package/dist/file-delete.js +1 -1
- package/dist/file-edit.js +1 -1
- package/dist/file-read.js +1 -1
- package/dist/file-write.js +1 -1
- package/dist/flow-bottlenecks.js +1 -1
- package/dist/flow-report.js +10 -9
- package/dist/gates.js +3 -2
- package/dist/git-branch.js +1 -1
- package/dist/git-diff.js +1 -1
- package/dist/git-log.js +1 -1
- package/dist/init.js +244 -61
- package/dist/initiative-add-wu.js +1 -1
- package/dist/initiative-bulk-assign-wus.js +1 -1
- package/dist/initiative-create.js +2 -2
- package/dist/initiative-edit.js +1 -1
- package/dist/initiative-list.js +1 -1
- package/dist/initiative-plan.js +1 -3
- package/dist/initiative-status.js +47 -6
- package/dist/lane-edit.js +19 -10
- package/dist/lane-health.js +13 -24
- package/dist/lane-lock.js +4 -5
- package/dist/lane-setup.js +5 -5
- package/dist/lane-status.js +4 -5
- package/dist/lane-suggest.js +9 -7
- package/dist/lane-validate.js +4 -5
- package/dist/lumenflow-upgrade.js +17 -11
- package/dist/mem-checkpoint.js +1 -1
- package/dist/mem-cleanup.js +6 -23
- package/dist/mem-context.js +1 -1
- package/dist/mem-create.js +1 -1
- package/dist/mem-delete.js +1 -1
- package/dist/mem-export.js +1 -1
- package/dist/mem-inbox.js +1 -1
- package/dist/mem-init.js +1 -1
- package/dist/mem-ready.js +1 -1
- package/dist/mem-recover.js +1 -1
- package/dist/mem-signal.js +1 -1
- package/dist/mem-start.js +1 -1
- package/dist/mem-summarize.js +8 -7
- package/dist/mem-triage.js +7 -5
- package/dist/metrics-cli.js +1 -1
- package/dist/metrics-snapshot.js +1 -1
- package/dist/onboard.js +295 -120
- package/dist/orchestrate-init-status.js +12 -7
- package/dist/orchestrate-initiative.js +23 -12
- package/dist/orchestrate-monitor.js +20 -8
- package/dist/pack-scaffold.js +1 -1
- package/dist/plan-create.js +1 -3
- package/dist/plan-edit.js +1 -3
- package/dist/plan-link.js +1 -3
- package/dist/plan-promote.js +1 -3
- package/dist/release.js +1 -3
- package/dist/signal-cleanup.js +4 -18
- package/dist/state-bootstrap.js +11 -8
- package/dist/state-cleanup.js +5 -19
- package/dist/state-doctor.js +213 -9
- package/dist/task-claim.js +1 -1
- package/dist/validate.js +1 -1
- package/dist/workspace-init.js +61 -61
- package/dist/wu-block.js +1 -1
- package/dist/wu-brief.js +1 -1
- package/dist/wu-claim.js +1 -1
- package/dist/wu-cleanup.js +1 -1
- package/dist/wu-create.js +3 -3
- package/dist/wu-delegate.js +1 -1
- package/dist/wu-deps.js +1 -1
- package/dist/wu-done.js +66 -34
- package/dist/wu-edit.js +1 -1
- package/dist/wu-infer-lane.js +1 -1
- package/dist/wu-preflight.js +1 -1
- package/dist/wu-prep.js +1 -1
- package/dist/wu-proto.js +1 -1
- package/dist/wu-prune.js +1 -1
- package/dist/wu-recover.js +1 -1
- package/dist/wu-release.js +1 -1
- package/dist/wu-repair.js +1 -1
- package/dist/wu-sandbox.js +40 -27
- package/dist/wu-status.js +1 -1
- package/dist/wu-unblock.js +1 -1
- package/dist/wu-unlock-lane.js +1 -1
- package/dist/wu-validate.js +1 -1
- package/package.json +12 -8
- package/packs/software-delivery/constants.ts +10 -0
- package/packs/software-delivery/extensions.ts +140 -0
- package/packs/software-delivery/gate-policies.ts +134 -0
- package/packs/software-delivery/index.ts +8 -0
- package/packs/software-delivery/manifest-schema.ts +236 -0
- package/packs/software-delivery/manifest.ts +417 -0
- package/packs/software-delivery/manifest.yaml +711 -0
- package/packs/software-delivery/pack-registration.ts +113 -0
- package/packs/software-delivery/tool-impl/agent-tools.ts +263 -0
- package/packs/software-delivery/tool-impl/delegation-tools.ts +66 -0
- package/packs/software-delivery/tool-impl/flow-metrics-tools.ts +219 -0
- package/packs/software-delivery/tool-impl/git-runner.ts +113 -0
- package/packs/software-delivery/tool-impl/git-tools.ts +316 -0
- package/packs/software-delivery/tool-impl/index.ts +15 -0
- package/packs/software-delivery/tool-impl/initiative-orchestration-tools.ts +720 -0
- package/packs/software-delivery/tool-impl/lane-lock.ts +246 -0
- package/packs/software-delivery/tool-impl/memory-tools.ts +415 -0
- package/packs/software-delivery/tool-impl/pending-runtime-tools.ts +21 -0
- package/packs/software-delivery/tool-impl/runtime-cli-adapter.ts +328 -0
- package/packs/software-delivery/tool-impl/runtime-native-tools.ts +687 -0
- package/packs/software-delivery/tool-impl/worker-loader.ts +52 -0
- package/packs/software-delivery/tool-impl/worktree-tools.ts +46 -0
- package/packs/software-delivery/tool-impl/wu-lifecycle-tools.ts +759 -0
- package/packs/software-delivery/tools/delegation-tools.ts +23 -0
- package/packs/software-delivery/tools/git-tools.ts +55 -0
- package/packs/software-delivery/tools/index.ts +8 -0
- package/packs/software-delivery/tools/lane-lock-tool.ts +37 -0
- package/packs/software-delivery/tools/types.ts +71 -0
- package/packs/software-delivery/tools/worktree-tools.ts +49 -0
- package/templates/core/LUMENFLOW.md.template +3 -3
- package/templates/core/ai/onboarding/agent-invocation-guide.md.template +1 -1
- package/templates/core/ai/onboarding/lumenflow-force-usage.md.template +1 -1
- package/templates/core/ai/onboarding/quick-ref-commands.md.template +5 -5
- package/templates/core/ai/onboarding/starting-prompt.md.template +3 -3
- package/templates/core/ai/onboarding/vendor-support.md.template +1 -1
- package/templates/core/ai/onboarding/wu-create-checklist.md.template +1 -1
- package/dist/agent-issues-query.js.map +0 -1
- package/dist/agent-log-issue.js.map +0 -1
- package/dist/agent-session-end.js.map +0 -1
- package/dist/agent-session.js.map +0 -1
- package/dist/backlog-prune.js.map +0 -1
- package/dist/cli-entry-point.js +0 -149
- package/dist/cli-entry-point.js.map +0 -1
- package/dist/commands/integrate.js.map +0 -1
- package/dist/commands.js.map +0 -1
- package/dist/config-get.js.map +0 -1
- package/dist/config-set.js.map +0 -1
- package/dist/delegation-list.js.map +0 -1
- package/dist/deps-add.js +0 -259
- package/dist/deps-add.js.map +0 -1
- package/dist/deps-remove.js +0 -105
- package/dist/deps-remove.js.map +0 -1
- package/dist/docs-sync.js.map +0 -1
- package/dist/doctor.js.map +0 -1
- package/dist/file-delete.js.map +0 -1
- package/dist/file-edit.js.map +0 -1
- package/dist/file-read.js.map +0 -1
- package/dist/file-write.js.map +0 -1
- package/dist/flow-bottlenecks.js.map +0 -1
- package/dist/flow-report.js.map +0 -1
- package/dist/formatters.js +0 -151
- package/dist/formatters.js.map +0 -1
- package/dist/gate-defaults.js +0 -131
- package/dist/gate-defaults.js.map +0 -1
- package/dist/gate-registry.js +0 -73
- package/dist/gate-registry.js.map +0 -1
- package/dist/gates-graceful-degradation.js +0 -153
- package/dist/gates-graceful-degradation.js.map +0 -1
- package/dist/gates-plan-resolvers.js +0 -152
- package/dist/gates-plan-resolvers.js.map +0 -1
- package/dist/gates-runners.js +0 -509
- package/dist/gates-runners.js.map +0 -1
- package/dist/gates-types.js +0 -4
- package/dist/gates-types.js.map +0 -1
- package/dist/gates-utils.js +0 -323
- package/dist/gates-utils.js.map +0 -1
- package/dist/gates.js.map +0 -1
- package/dist/git-branch.js.map +0 -1
- package/dist/git-diff.js.map +0 -1
- package/dist/git-log.js.map +0 -1
- package/dist/git-status.js.map +0 -1
- package/dist/guard-locked.js +0 -172
- package/dist/guard-locked.js.map +0 -1
- package/dist/guard-main-branch.js +0 -217
- package/dist/guard-main-branch.js.map +0 -1
- package/dist/guard-worktree-commit.js +0 -163
- package/dist/guard-worktree-commit.js.map +0 -1
- package/dist/hooks/auto-checkpoint-utils.js +0 -54
- package/dist/hooks/auto-checkpoint-utils.js.map +0 -1
- package/dist/hooks/enforcement-checks.js +0 -399
- package/dist/hooks/enforcement-checks.js.map +0 -1
- package/dist/hooks/enforcement-generator.js +0 -139
- package/dist/hooks/enforcement-generator.js.map +0 -1
- package/dist/hooks/enforcement-sync.js +0 -385
- package/dist/hooks/enforcement-sync.js.map +0 -1
- package/dist/hooks/generators/auto-checkpoint.js +0 -125
- package/dist/hooks/generators/auto-checkpoint.js.map +0 -1
- package/dist/hooks/generators/enforce-worktree.js +0 -190
- package/dist/hooks/generators/enforce-worktree.js.map +0 -1
- package/dist/hooks/generators/index.js +0 -18
- package/dist/hooks/generators/index.js.map +0 -1
- package/dist/hooks/generators/pre-compact-checkpoint.js +0 -136
- package/dist/hooks/generators/pre-compact-checkpoint.js.map +0 -1
- package/dist/hooks/generators/require-wu.js +0 -117
- package/dist/hooks/generators/require-wu.js.map +0 -1
- package/dist/hooks/generators/session-start-recovery.js +0 -103
- package/dist/hooks/generators/session-start-recovery.js.map +0 -1
- package/dist/hooks/generators/signal-utils.js +0 -54
- package/dist/hooks/generators/signal-utils.js.map +0 -1
- package/dist/hooks/generators/warn-incomplete.js +0 -67
- package/dist/hooks/generators/warn-incomplete.js.map +0 -1
- package/dist/hooks/index.js +0 -10
- package/dist/hooks/index.js.map +0 -1
- package/dist/index.js.map +0 -1
- package/dist/init-detection.js +0 -230
- package/dist/init-detection.js.map +0 -1
- package/dist/init-lane-validation.js +0 -143
- package/dist/init-lane-validation.js.map +0 -1
- package/dist/init-scaffolding.js +0 -158
- package/dist/init-scaffolding.js.map +0 -1
- package/dist/init-templates.js +0 -1964
- package/dist/init-templates.js.map +0 -1
- package/dist/init.js.map +0 -1
- package/dist/initiative-add-wu.js.map +0 -1
- package/dist/initiative-bulk-assign-wus.js.map +0 -1
- package/dist/initiative-create.js.map +0 -1
- package/dist/initiative-edit.js.map +0 -1
- package/dist/initiative-list.js.map +0 -1
- package/dist/initiative-plan.js.map +0 -1
- package/dist/initiative-remove-wu.js.map +0 -1
- package/dist/initiative-status.js.map +0 -1
- package/dist/lane-edit.js.map +0 -1
- package/dist/lane-health.js.map +0 -1
- package/dist/lane-lifecycle-process.js +0 -366
- package/dist/lane-lifecycle-process.js.map +0 -1
- package/dist/lane-lock.js.map +0 -1
- package/dist/lane-setup.js.map +0 -1
- package/dist/lane-status.js.map +0 -1
- package/dist/lane-suggest.js.map +0 -1
- package/dist/lane-validate.js.map +0 -1
- package/dist/lifecycle-regression-harness.js +0 -181
- package/dist/lifecycle-regression-harness.js.map +0 -1
- package/dist/lumenflow-upgrade.js.map +0 -1
- package/dist/mem-checkpoint.js.map +0 -1
- package/dist/mem-cleanup.js.map +0 -1
- package/dist/mem-context.js.map +0 -1
- package/dist/mem-create.js.map +0 -1
- package/dist/mem-delete.js.map +0 -1
- package/dist/mem-export.js.map +0 -1
- package/dist/mem-inbox.js.map +0 -1
- package/dist/mem-index.js +0 -214
- package/dist/mem-index.js.map +0 -1
- package/dist/mem-init.js.map +0 -1
- package/dist/mem-profile.js +0 -210
- package/dist/mem-profile.js.map +0 -1
- package/dist/mem-promote.js +0 -257
- package/dist/mem-promote.js.map +0 -1
- package/dist/mem-ready.js.map +0 -1
- package/dist/mem-recover.js.map +0 -1
- package/dist/mem-signal.js.map +0 -1
- package/dist/mem-start.js.map +0 -1
- package/dist/mem-summarize.js.map +0 -1
- package/dist/mem-triage.js.map +0 -1
- package/dist/merge-block.js +0 -225
- package/dist/merge-block.js.map +0 -1
- package/dist/metrics-cli.js.map +0 -1
- package/dist/metrics-snapshot.js.map +0 -1
- package/dist/onboard.js.map +0 -1
- package/dist/onboarding-smoke-test.js +0 -418
- package/dist/onboarding-smoke-test.js.map +0 -1
- package/dist/orchestrate-init-status.js.map +0 -1
- package/dist/orchestrate-initiative.js.map +0 -1
- package/dist/orchestrate-monitor.js.map +0 -1
- package/dist/pack-author.js.map +0 -1
- package/dist/pack-hash.js.map +0 -1
- package/dist/pack-install.js.map +0 -1
- package/dist/pack-publish.js.map +0 -1
- package/dist/pack-scaffold.js.map +0 -1
- package/dist/pack-search.js.map +0 -1
- package/dist/pack-validate.js.map +0 -1
- package/dist/plan-create.js.map +0 -1
- package/dist/plan-edit.js.map +0 -1
- package/dist/plan-link.js.map +0 -1
- package/dist/plan-promote.js.map +0 -1
- package/dist/public-manifest.js +0 -920
- package/dist/public-manifest.js.map +0 -1
- package/dist/release.js.map +0 -1
- package/dist/rotate-progress.js +0 -253
- package/dist/rotate-progress.js.map +0 -1
- package/dist/session-coordinator.js +0 -303
- package/dist/session-coordinator.js.map +0 -1
- package/dist/shared-validators.js +0 -81
- package/dist/shared-validators.js.map +0 -1
- package/dist/signal-cleanup.js.map +0 -1
- package/dist/state-bootstrap.js.map +0 -1
- package/dist/state-cleanup.js.map +0 -1
- package/dist/state-doctor-fix.js +0 -226
- package/dist/state-doctor-fix.js.map +0 -1
- package/dist/state-doctor-stamps.js +0 -23
- package/dist/state-doctor-stamps.js.map +0 -1
- package/dist/state-doctor.js.map +0 -1
- package/dist/strict-progress.js +0 -255
- package/dist/strict-progress.js.map +0 -1
- package/dist/sync-templates.js.map +0 -1
- package/dist/task-claim.js.map +0 -1
- package/dist/trace-gen.js +0 -401
- package/dist/trace-gen.js.map +0 -1
- package/dist/validate-agent-skills.js +0 -223
- package/dist/validate-agent-skills.js.map +0 -1
- package/dist/validate-agent-sync.js +0 -151
- package/dist/validate-agent-sync.js.map +0 -1
- package/dist/validate-backlog-sync.js +0 -77
- package/dist/validate-backlog-sync.js.map +0 -1
- package/dist/validate-skills-spec.js +0 -211
- package/dist/validate-skills-spec.js.map +0 -1
- package/dist/validate.js.map +0 -1
- package/dist/validator-defaults.js +0 -107
- package/dist/validator-defaults.js.map +0 -1
- package/dist/validator-registry.js +0 -71
- package/dist/validator-registry.js.map +0 -1
- package/dist/workspace-init.js.map +0 -1
- package/dist/wu-block.js.map +0 -1
- package/dist/wu-brief.js.map +0 -1
- package/dist/wu-claim-branch.js +0 -123
- package/dist/wu-claim-branch.js.map +0 -1
- package/dist/wu-claim-cloud.js +0 -79
- package/dist/wu-claim-cloud.js.map +0 -1
- package/dist/wu-claim-mode.js +0 -82
- package/dist/wu-claim-mode.js.map +0 -1
- package/dist/wu-claim-output.js +0 -85
- package/dist/wu-claim-output.js.map +0 -1
- package/dist/wu-claim-repair-guidance.js +0 -12
- package/dist/wu-claim-repair-guidance.js.map +0 -1
- package/dist/wu-claim-resume-handler.js +0 -87
- package/dist/wu-claim-resume-handler.js.map +0 -1
- package/dist/wu-claim-state.js +0 -581
- package/dist/wu-claim-state.js.map +0 -1
- package/dist/wu-claim-validation.js +0 -457
- package/dist/wu-claim-validation.js.map +0 -1
- package/dist/wu-claim-worktree.js +0 -223
- package/dist/wu-claim-worktree.js.map +0 -1
- package/dist/wu-claim.js.map +0 -1
- package/dist/wu-cleanup-cloud.js +0 -78
- package/dist/wu-cleanup-cloud.js.map +0 -1
- package/dist/wu-cleanup.js.map +0 -1
- package/dist/wu-code-path-coverage.js +0 -83
- package/dist/wu-code-path-coverage.js.map +0 -1
- package/dist/wu-create-cloud.js +0 -30
- package/dist/wu-create-cloud.js.map +0 -1
- package/dist/wu-create-content.js +0 -264
- package/dist/wu-create-content.js.map +0 -1
- package/dist/wu-create-readiness.js +0 -59
- package/dist/wu-create-readiness.js.map +0 -1
- package/dist/wu-create-validation.js +0 -128
- package/dist/wu-create-validation.js.map +0 -1
- package/dist/wu-create.js.map +0 -1
- package/dist/wu-delegate.js.map +0 -1
- package/dist/wu-delete.js.map +0 -1
- package/dist/wu-deps.js.map +0 -1
- package/dist/wu-done-auto-cleanup.js +0 -203
- package/dist/wu-done-auto-cleanup.js.map +0 -1
- package/dist/wu-done-check.js +0 -38
- package/dist/wu-done-check.js.map +0 -1
- package/dist/wu-done-cloud.js +0 -48
- package/dist/wu-done-cloud.js.map +0 -1
- package/dist/wu-done-decay.js +0 -86
- package/dist/wu-done-decay.js.map +0 -1
- package/dist/wu-done.js.map +0 -1
- package/dist/wu-edit-operations.js +0 -399
- package/dist/wu-edit-operations.js.map +0 -1
- package/dist/wu-edit-validators.js +0 -282
- package/dist/wu-edit-validators.js.map +0 -1
- package/dist/wu-edit.js.map +0 -1
- package/dist/wu-infer-lane.js.map +0 -1
- package/dist/wu-preflight.js.map +0 -1
- package/dist/wu-prep.js.map +0 -1
- package/dist/wu-proto.js.map +0 -1
- package/dist/wu-prune.js.map +0 -1
- package/dist/wu-recover.js.map +0 -1
- package/dist/wu-release.js.map +0 -1
- package/dist/wu-repair.js.map +0 -1
- package/dist/wu-sandbox.js.map +0 -1
- package/dist/wu-spawn-completion.js +0 -33
- package/dist/wu-spawn-completion.js.map +0 -1
- package/dist/wu-spawn-prompt-builders.js +0 -1197
- package/dist/wu-spawn-prompt-builders.js.map +0 -1
- package/dist/wu-spawn-strategy-resolver.js +0 -322
- package/dist/wu-spawn-strategy-resolver.js.map +0 -1
- package/dist/wu-spawn.js +0 -59
- package/dist/wu-spawn.js.map +0 -1
- package/dist/wu-state-cloud.js +0 -41
- package/dist/wu-state-cloud.js.map +0 -1
- package/dist/wu-status.js.map +0 -1
- package/dist/wu-unblock.js.map +0 -1
- package/dist/wu-unlock-lane.js.map +0 -1
- package/dist/wu-validate.js.map +0 -1
package/dist/init.js
CHANGED
|
@@ -19,6 +19,7 @@ import * as path from 'node:path';
|
|
|
19
19
|
import * as yaml from 'yaml';
|
|
20
20
|
import { execFileSync } from 'node:child_process';
|
|
21
21
|
import { getDefaultConfig, createWUParser, WU_OPTIONS, CLAUDE_HOOKS, LUMENFLOW_CLIENT_IDS, } from '@lumenflow/core';
|
|
22
|
+
import { WORKSPACE_V2_KEYS } from '@lumenflow/core/config-schema';
|
|
22
23
|
// WU-1067: Import GATE_PRESETS for --preset support
|
|
23
24
|
import { GATE_PRESETS } from '@lumenflow/core/gates-config';
|
|
24
25
|
// WU-1362: Import worktree guard utilities for branch checking
|
|
@@ -34,13 +35,14 @@ import { getPublicManifest } from './public-manifest.js';
|
|
|
34
35
|
import { runCLI } from './cli-entry-point.js';
|
|
35
36
|
import { buildInitLaneLifecycleMessage, LANE_LIFECYCLE_STATUS } from './lane-lifecycle-process.js';
|
|
36
37
|
// WU-1643: Import template constants from dedicated data module
|
|
37
|
-
import { AGENTS_MD_TEMPLATE, LUMENFLOW_MD_TEMPLATE, CONSTRAINTS_MD_TEMPLATE, CLAUDE_MD_TEMPLATE, CLAUDE_SETTINGS_TEMPLATE, CURSOR_RULES_TEMPLATE, WINDSURF_RULES_TEMPLATE, CLINE_RULES_TEMPLATE, AIDER_CONF_TEMPLATE, MCP_JSON_TEMPLATE, BACKLOG_TEMPLATE, STATUS_TEMPLATE, WU_TEMPLATE_YAML, FRAMEWORK_HINT_TEMPLATE, FRAMEWORK_OVERLAY_TEMPLATE, QUICK_REF_COMMANDS_TEMPLATE, FIRST_WU_MISTAKES_TEMPLATE, TROUBLESHOOTING_WU_DONE_TEMPLATE, AGENT_SAFETY_CARD_TEMPLATE, STARTING_PROMPT_TEMPLATE, WU_CREATE_CHECKLIST_TEMPLATE, FIRST_15_MINS_TEMPLATE, LOCAL_ONLY_TEMPLATE, LANE_INFERENCE_DOC_TEMPLATE, WU_SIZING_GUIDE_TEMPLATE, WU_LIFECYCLE_SKILL_TEMPLATE, WORKTREE_DISCIPLINE_SKILL_TEMPLATE, LUMENFLOW_GATES_SKILL_TEMPLATE, GITIGNORE_TEMPLATE, PRETTIERIGNORE_TEMPLATE, SAFE_GIT_TEMPLATE, PRE_COMMIT_TEMPLATE, GATE_STUB_SCRIPTS, SCRIPT_ARG_OVERRIDES, DEFAULT_LANE_DEFINITIONS, } from './init-templates.js';
|
|
38
|
+
import { AGENTS_MD_TEMPLATE, LUMENFLOW_MD_TEMPLATE, CONSTRAINTS_MD_TEMPLATE, CLAUDE_MD_TEMPLATE, CLAUDE_SETTINGS_TEMPLATE, CURSOR_RULES_TEMPLATE, WINDSURF_RULES_TEMPLATE, CLINE_RULES_TEMPLATE, AIDER_CONF_TEMPLATE, MCP_JSON_TEMPLATE, BACKLOG_TEMPLATE, STATUS_TEMPLATE, WU_TEMPLATE_YAML, FRAMEWORK_HINT_TEMPLATE, FRAMEWORK_OVERLAY_TEMPLATE, QUICK_REF_COMMANDS_TEMPLATE, FIRST_WU_MISTAKES_TEMPLATE, TROUBLESHOOTING_WU_DONE_TEMPLATE, AGENT_SAFETY_CARD_TEMPLATE, STARTING_PROMPT_TEMPLATE, WU_CREATE_CHECKLIST_TEMPLATE, FIRST_15_MINS_TEMPLATE, LOCAL_ONLY_TEMPLATE, LANE_INFERENCE_DOC_TEMPLATE, WU_SIZING_GUIDE_TEMPLATE, WU_LIFECYCLE_SKILL_TEMPLATE, WORKTREE_DISCIPLINE_SKILL_TEMPLATE, LUMENFLOW_GATES_SKILL_TEMPLATE, GITIGNORE_TEMPLATE, REQUIRED_GITIGNORE_EXCLUSIONS, PRETTIERIGNORE_TEMPLATE, SAFE_GIT_TEMPLATE, PRE_COMMIT_TEMPLATE, GATE_STUB_SCRIPTS, SCRIPT_ARG_OVERRIDES, DEFAULT_LANE_DEFINITIONS, } from './init-templates.js';
|
|
38
39
|
// WU-1644: Import detection helpers from dedicated module
|
|
39
|
-
import {
|
|
40
|
+
import { getDocsPath, detectDocsStructure, detectDefaultClient, isGitRepo, hasGitCommits, detectGitStateConfig, } from './init-detection.js';
|
|
40
41
|
// WU-1644: Re-export detection functions for backwards compatibility
|
|
41
42
|
export { detectIDEEnvironment, checkPrerequisites, getDocsPath, detectDocsStructure, } from './init-detection.js';
|
|
42
43
|
// WU-1644: Import scaffolding helpers from dedicated module
|
|
43
44
|
import { processTemplate, loadTemplate, createFile, createDirectory, createExecutableScript, } from './init-scaffolding.js';
|
|
45
|
+
import { CANONICAL_BOOTSTRAP_COMMAND, DEFAULT_PROJECT_NAME, getDefaultWorkspaceConfig, WORKSPACE_FILENAME, } from './workspace-init.js';
|
|
44
46
|
/**
|
|
45
47
|
* WU-1085: CLI option definitions for init command
|
|
46
48
|
* WU-1171: Added --merge and --client options
|
|
@@ -84,8 +86,33 @@ const INIT_OPTIONS = {
|
|
|
84
86
|
flags: '--preset <preset>',
|
|
85
87
|
description: 'Gate preset for config (node, python, go, rust, dotnet)',
|
|
86
88
|
},
|
|
89
|
+
bootstrapDomain: {
|
|
90
|
+
name: 'bootstrapDomain',
|
|
91
|
+
flags: '--bootstrap-domain <domain>',
|
|
92
|
+
description: 'Bootstrap domain: software-delivery, infra, or custom',
|
|
93
|
+
},
|
|
94
|
+
skipBootstrap: {
|
|
95
|
+
name: 'skipBootstrap',
|
|
96
|
+
flags: '--skip-bootstrap',
|
|
97
|
+
description: 'Skip workspace bootstrap-all flow (workspace.yaml + pack install)',
|
|
98
|
+
},
|
|
99
|
+
skipBootstrapPackInstall: {
|
|
100
|
+
name: 'skipBootstrapPackInstall',
|
|
101
|
+
flags: '--skip-bootstrap-pack-install',
|
|
102
|
+
description: 'Skip registry pack install during bootstrap',
|
|
103
|
+
},
|
|
87
104
|
force: WU_OPTIONS.force,
|
|
88
105
|
};
|
|
106
|
+
function parseBootstrapDomain(rawDomain) {
|
|
107
|
+
if (!rawDomain) {
|
|
108
|
+
return BOOTSTRAP_DEFAULT_DOMAIN;
|
|
109
|
+
}
|
|
110
|
+
if (BOOTSTRAP_VALID_DOMAINS.has(rawDomain)) {
|
|
111
|
+
return rawDomain;
|
|
112
|
+
}
|
|
113
|
+
const validDomains = Array.from(BOOTSTRAP_VALID_DOMAINS).join(', ');
|
|
114
|
+
throw new Error(`${BOOTSTRAP_ERROR_PREFIX} Invalid --bootstrap-domain "${rawDomain}". Valid values: ${validDomains}`);
|
|
115
|
+
}
|
|
89
116
|
/**
|
|
90
117
|
* WU-1085: Parse init command options using createWUParser
|
|
91
118
|
* WU-1171: Added --merge, --client options
|
|
@@ -97,7 +124,8 @@ export function parseInitOptions() {
|
|
|
97
124
|
name: 'lumenflow-init',
|
|
98
125
|
description: 'Initialize LumenFlow in a project\n\n' +
|
|
99
126
|
'Subcommands:\n' +
|
|
100
|
-
' lumenflow commands
|
|
127
|
+
' lumenflow commands List all available CLI commands\n' +
|
|
128
|
+
' lumenflow cloud connect Configure cloud control-plane access',
|
|
101
129
|
options: Object.values(INIT_OPTIONS),
|
|
102
130
|
});
|
|
103
131
|
// WU-1171: --client takes precedence, --vendor is alias
|
|
@@ -105,6 +133,7 @@ export function parseInitOptions() {
|
|
|
105
133
|
// WU-1286: --full is now the default (true), use --minimal to disable
|
|
106
134
|
// --minimal explicitly sets full to false, otherwise full defaults to true
|
|
107
135
|
const fullMode = opts.minimal ? false : (opts.full ?? true);
|
|
136
|
+
const bootstrapDomain = parseBootstrapDomain(opts.bootstrapDomain);
|
|
108
137
|
return {
|
|
109
138
|
force: opts.force ?? false,
|
|
110
139
|
full: fullMode,
|
|
@@ -113,10 +142,48 @@ export function parseInitOptions() {
|
|
|
113
142
|
client: clientValue,
|
|
114
143
|
vendor: clientValue,
|
|
115
144
|
preset: opts.preset,
|
|
145
|
+
bootstrapDomain,
|
|
146
|
+
skipBootstrap: Boolean(opts.skipBootstrap),
|
|
147
|
+
skipBootstrapPackInstall: Boolean(opts.skipBootstrapPackInstall),
|
|
116
148
|
};
|
|
117
149
|
}
|
|
118
150
|
const DEFAULT_CLIENT_CLAUDE = LUMENFLOW_CLIENT_IDS.CLAUDE_CODE;
|
|
119
|
-
const
|
|
151
|
+
const BOOTSTRAP_DEFAULT_DOMAIN = 'software-delivery';
|
|
152
|
+
const BOOTSTRAP_INFRA_DOMAIN = 'infra';
|
|
153
|
+
const BOOTSTRAP_CUSTOM_DOMAIN = 'custom';
|
|
154
|
+
const BOOTSTRAP_VALID_DOMAINS = new Set([
|
|
155
|
+
BOOTSTRAP_DEFAULT_DOMAIN,
|
|
156
|
+
BOOTSTRAP_INFRA_DOMAIN,
|
|
157
|
+
BOOTSTRAP_CUSTOM_DOMAIN,
|
|
158
|
+
]);
|
|
159
|
+
const BOOTSTRAP_SKIP_REASON_FLAG = '--skip-bootstrap';
|
|
160
|
+
const BOOTSTRAP_SKIP_REASON_EXISTING_WORKSPACE = `${WORKSPACE_FILENAME} already exists`;
|
|
161
|
+
const BOOTSTRAP_ERROR_PREFIX = '[lumenflow bootstrap]';
|
|
162
|
+
const INIT_SUBCOMMANDS = {
|
|
163
|
+
COMMANDS: 'commands',
|
|
164
|
+
CLOUD: 'cloud',
|
|
165
|
+
};
|
|
166
|
+
const LEGACY_SUBCOMMANDS = {
|
|
167
|
+
ONBOARD: 'onboard',
|
|
168
|
+
WORKSPACE_INIT_COLON: 'workspace:init',
|
|
169
|
+
WORKSPACE_INIT_DASH: 'workspace-init',
|
|
170
|
+
};
|
|
171
|
+
const CLOUD_SUBCOMMANDS = {
|
|
172
|
+
CONNECT: 'connect',
|
|
173
|
+
};
|
|
174
|
+
const CLOUD_CONNECT_BIN = 'cloud-connect';
|
|
175
|
+
const INIT_ERROR_PREFIX = '[lumenflow init]';
|
|
176
|
+
const INIT_CLOUD_CONNECT_HELP = 'Usage: lumenflow cloud connect --endpoint <url> --org-id <id> --project-id <id> [--token-env <name>]';
|
|
177
|
+
const LEGACY_SUBCOMMAND_ERROR_PREFIX = `${INIT_ERROR_PREFIX} Legacy onboarding subcommand`;
|
|
178
|
+
const LEGACY_SUBCOMMAND_GUIDANCE = `Use "${CANONICAL_BOOTSTRAP_COMMAND}" for bootstrap-all onboarding`;
|
|
179
|
+
const LEGACY_SUBCOMMAND_HELP_HINT = `Run "${CANONICAL_BOOTSTRAP_COMMAND} --help" for supported options`;
|
|
180
|
+
const CONFIG_FILE_NAME = WORKSPACE_FILENAME;
|
|
181
|
+
const SOFTWARE_DELIVERY_KEY = WORKSPACE_V2_KEYS.SOFTWARE_DELIVERY;
|
|
182
|
+
const SOFTWARE_DELIVERY_CONFIG_KEYS = {
|
|
183
|
+
AGENTS: 'agents',
|
|
184
|
+
CLIENTS: 'clients',
|
|
185
|
+
ENFORCEMENT: 'enforcement',
|
|
186
|
+
};
|
|
120
187
|
const FRAMEWORK_HINT_FILE = '.lumenflow.framework.yaml';
|
|
121
188
|
const LUMENFLOW_DIR = '.lumenflow';
|
|
122
189
|
const LUMENFLOW_AGENTS_DIR = `${LUMENFLOW_DIR}/agents`;
|
|
@@ -210,30 +277,77 @@ function detectProjectTooling(targetDir) {
|
|
|
210
277
|
return { hasTurbo: false };
|
|
211
278
|
}
|
|
212
279
|
}
|
|
280
|
+
function asRecord(value) {
|
|
281
|
+
return value && typeof value === 'object' && !Array.isArray(value)
|
|
282
|
+
? value
|
|
283
|
+
: null;
|
|
284
|
+
}
|
|
285
|
+
function mergeConfigDefaults(defaults, existing) {
|
|
286
|
+
const merged = { ...defaults };
|
|
287
|
+
for (const [key, existingValue] of Object.entries(existing)) {
|
|
288
|
+
const defaultValue = merged[key];
|
|
289
|
+
const existingRecord = asRecord(existingValue);
|
|
290
|
+
const defaultRecord = asRecord(defaultValue);
|
|
291
|
+
if (defaultRecord && existingRecord) {
|
|
292
|
+
merged[key] = mergeConfigDefaults(defaultRecord, existingRecord);
|
|
293
|
+
continue;
|
|
294
|
+
}
|
|
295
|
+
merged[key] = existingValue;
|
|
296
|
+
}
|
|
297
|
+
return merged;
|
|
298
|
+
}
|
|
299
|
+
function toWorkspaceId(value) {
|
|
300
|
+
return value
|
|
301
|
+
.toLowerCase()
|
|
302
|
+
.replace(/[^a-z0-9]+/g, '-')
|
|
303
|
+
.replace(/^-+|-+$/g, '');
|
|
304
|
+
}
|
|
305
|
+
function loadWorkspaceDocument(targetDir) {
|
|
306
|
+
const workspacePath = path.join(targetDir, CONFIG_FILE_NAME);
|
|
307
|
+
if (!fs.existsSync(workspacePath)) {
|
|
308
|
+
const projectName = resolveBootstrapProjectName(targetDir);
|
|
309
|
+
const projectId = toWorkspaceId(projectName);
|
|
310
|
+
const workspace = {
|
|
311
|
+
...getDefaultWorkspaceConfig(),
|
|
312
|
+
id: projectId,
|
|
313
|
+
name: projectName,
|
|
314
|
+
memory_namespace: projectId,
|
|
315
|
+
event_namespace: projectId,
|
|
316
|
+
};
|
|
317
|
+
return { exists: false, workspace };
|
|
318
|
+
}
|
|
319
|
+
const content = fs.readFileSync(workspacePath, 'utf-8');
|
|
320
|
+
const workspace = asRecord(yaml.parse(content));
|
|
321
|
+
if (!workspace) {
|
|
322
|
+
throw new Error(`${INIT_ERROR_PREFIX} ${CONFIG_FILE_NAME} exists but is not a valid YAML object. ` +
|
|
323
|
+
`Fix ${CONFIG_FILE_NAME} and re-run init.`);
|
|
324
|
+
}
|
|
325
|
+
return { exists: true, workspace };
|
|
326
|
+
}
|
|
327
|
+
function upsertWorkspaceSoftwareDelivery(targetDir, softwareDeliveryConfig, result) {
|
|
328
|
+
const workspacePath = path.join(targetDir, CONFIG_FILE_NAME);
|
|
329
|
+
const { exists, workspace } = loadWorkspaceDocument(targetDir);
|
|
330
|
+
const existingSoftwareDelivery = asRecord(workspace[SOFTWARE_DELIVERY_KEY]) ?? {};
|
|
331
|
+
workspace[SOFTWARE_DELIVERY_KEY] = mergeConfigDefaults(softwareDeliveryConfig, existingSoftwareDelivery);
|
|
332
|
+
fs.writeFileSync(workspacePath, yaml.stringify(workspace), 'utf-8');
|
|
333
|
+
if (exists) {
|
|
334
|
+
result.overwritten = result.overwritten ?? [];
|
|
335
|
+
if (!result.overwritten.includes(CONFIG_FILE_NAME)) {
|
|
336
|
+
result.overwritten.push(CONFIG_FILE_NAME);
|
|
337
|
+
}
|
|
338
|
+
return;
|
|
339
|
+
}
|
|
340
|
+
result.created.push(CONFIG_FILE_NAME);
|
|
341
|
+
}
|
|
213
342
|
/**
|
|
214
|
-
*
|
|
343
|
+
* Build software_delivery configuration defaults
|
|
215
344
|
* WU-1067: Supports --preset option for config-driven gates
|
|
216
345
|
* WU-1307: Includes default lane definitions for onboarding
|
|
217
346
|
* WU-1364: Supports git config overrides (requireRemote)
|
|
218
347
|
* WU-1383: Adds enforcement hooks config for Claude client by default
|
|
219
348
|
* WU-1965: Detects installed tooling from package.json for config defaults
|
|
220
349
|
*/
|
|
221
|
-
function
|
|
222
|
-
// WU-1382: Add managed file header to prevent manual edits
|
|
223
|
-
const header = `# ============================================================================
|
|
224
|
-
# LUMENFLOW MANAGED FILE - DO NOT EDIT MANUALLY
|
|
225
|
-
# ============================================================================
|
|
226
|
-
# Generated by: lumenflow init
|
|
227
|
-
# Regenerate with: pnpm exec lumenflow init --force
|
|
228
|
-
#
|
|
229
|
-
# This file is managed by LumenFlow tooling. Manual edits may be overwritten.
|
|
230
|
-
# To customize, use the CLI commands or edit the appropriate source templates.
|
|
231
|
-
# ============================================================================
|
|
232
|
-
|
|
233
|
-
# LumenFlow Configuration
|
|
234
|
-
# Customize paths based on your project structure
|
|
235
|
-
|
|
236
|
-
`;
|
|
350
|
+
function buildSoftwareDeliveryConfig(gatePreset, gitConfigOverride, client, docsPaths, targetDir) {
|
|
237
351
|
const config = getDefaultConfig();
|
|
238
352
|
config.directories.agentsDir = LUMENFLOW_AGENTS_DIR;
|
|
239
353
|
// WU-1755: Override directory paths to match detected docs structure.
|
|
@@ -319,7 +433,7 @@ function generateLumenflowConfigYaml(gatePreset, gitConfigOverride, client, docs
|
|
|
319
433
|
},
|
|
320
434
|
};
|
|
321
435
|
}
|
|
322
|
-
return
|
|
436
|
+
return config;
|
|
323
437
|
}
|
|
324
438
|
/**
|
|
325
439
|
* Get current date in YYYY-MM-DD format
|
|
@@ -381,22 +495,29 @@ async function runClientIntegrations(targetDir, result) {
|
|
|
381
495
|
const configPath = path.join(targetDir, CONFIG_FILE_NAME);
|
|
382
496
|
if (!fs.existsSync(configPath))
|
|
383
497
|
return integrationFiles;
|
|
384
|
-
let
|
|
498
|
+
let softwareDeliveryConfig;
|
|
385
499
|
try {
|
|
386
500
|
const content = fs.readFileSync(configPath, 'utf-8');
|
|
387
|
-
|
|
501
|
+
const workspaceConfig = asRecord(yaml.parse(content));
|
|
502
|
+
softwareDeliveryConfig = workspaceConfig
|
|
503
|
+
? asRecord(workspaceConfig[SOFTWARE_DELIVERY_KEY])
|
|
504
|
+
: null;
|
|
388
505
|
}
|
|
389
506
|
catch {
|
|
390
507
|
return integrationFiles; // Config unreadable -- skip silently
|
|
391
508
|
}
|
|
392
|
-
if (!
|
|
509
|
+
if (!softwareDeliveryConfig)
|
|
393
510
|
return integrationFiles;
|
|
394
|
-
const agents =
|
|
395
|
-
const clients = agents?.
|
|
511
|
+
const agents = asRecord(softwareDeliveryConfig[SOFTWARE_DELIVERY_CONFIG_KEYS.AGENTS]);
|
|
512
|
+
const clients = asRecord(agents?.[SOFTWARE_DELIVERY_CONFIG_KEYS.CLIENTS]);
|
|
396
513
|
if (!clients)
|
|
397
514
|
return integrationFiles;
|
|
398
|
-
for (const [clientKey,
|
|
399
|
-
const
|
|
515
|
+
for (const [clientKey, unsafeClientConfig] of Object.entries(clients)) {
|
|
516
|
+
const clientConfig = asRecord(unsafeClientConfig);
|
|
517
|
+
if (!clientConfig) {
|
|
518
|
+
continue;
|
|
519
|
+
}
|
|
520
|
+
const enforcement = asRecord(clientConfig[SOFTWARE_DELIVERY_CONFIG_KEYS.ENFORCEMENT]);
|
|
400
521
|
if (!enforcement?.hooks)
|
|
401
522
|
continue;
|
|
402
523
|
const integration = CLIENT_INTEGRATIONS[clientKey];
|
|
@@ -504,19 +625,8 @@ export async function scaffoldProject(targetDir, options) {
|
|
|
504
625
|
DOCS_TASKS_PATH: docsPaths.tasks,
|
|
505
626
|
DOCS_ONBOARDING_PATH: docsPaths.onboarding,
|
|
506
627
|
};
|
|
507
|
-
//
|
|
508
|
-
|
|
509
|
-
// WU-1383: Includes enforcement hooks for Claude client
|
|
510
|
-
// Note: Config files don't use merge mode (always skip or force)
|
|
511
|
-
const configPath = path.join(targetDir, CONFIG_FILE_NAME);
|
|
512
|
-
// WU-1383: Warn if config already exists to discourage manual editing
|
|
513
|
-
if (fs.existsSync(configPath) && !options.force) {
|
|
514
|
-
result.warnings = result.warnings ?? [];
|
|
515
|
-
result.warnings.push(`${CONFIG_FILE_NAME} already exists. ` +
|
|
516
|
-
'To modify configuration, use CLI commands (e.g., pnpm lumenflow:init --force) ' +
|
|
517
|
-
'instead of manual editing.');
|
|
518
|
-
}
|
|
519
|
-
await createFile(configPath, generateLumenflowConfigYaml(options.gatePreset, gitConfigOverride, client, docsPaths, targetDir), options.force ? 'force' : 'skip', result, targetDir);
|
|
628
|
+
// Upsert workspace.yaml software_delivery defaults (WU-2006 hard cut)
|
|
629
|
+
upsertWorkspaceSoftwareDelivery(targetDir, buildSoftwareDeliveryConfig(options.gatePreset, gitConfigOverride, client, docsPaths, targetDir), result);
|
|
520
630
|
// WU-1171: Create AGENTS.md (universal entry point for all agents)
|
|
521
631
|
try {
|
|
522
632
|
const agentsTemplate = loadTemplate('core/AGENTS.md.template');
|
|
@@ -596,14 +706,8 @@ async function scaffoldGitignore(targetDir, options, result) {
|
|
|
596
706
|
// Merge mode or skip mode with existing file: append LumenFlow exclusions if not already present
|
|
597
707
|
const existingContent = fs.readFileSync(gitignorePath, 'utf-8');
|
|
598
708
|
const linesToAdd = [];
|
|
599
|
-
//
|
|
600
|
-
|
|
601
|
-
const requiredExclusions = [
|
|
602
|
-
{ pattern: 'node_modules', line: 'node_modules/' },
|
|
603
|
-
{ pattern: '.lumenflow/telemetry', line: '.lumenflow/telemetry/' },
|
|
604
|
-
{ pattern: 'worktrees', line: 'worktrees/' },
|
|
605
|
-
];
|
|
606
|
-
for (const { pattern, line } of requiredExclusions) {
|
|
709
|
+
// WU-1969: Use shared constant so merge path and full template cannot drift
|
|
710
|
+
for (const { pattern, line } of REQUIRED_GITIGNORE_EXCLUSIONS) {
|
|
607
711
|
if (!existingContent.includes(pattern)) {
|
|
608
712
|
linesToAdd.push(line);
|
|
609
713
|
}
|
|
@@ -970,6 +1074,56 @@ async function scaffoldClientFiles(targetDir, options, result, tokens, client) {
|
|
|
970
1074
|
await createFile(path.join(targetDir, '.aider.conf.yml'), AIDER_CONF_TEMPLATE, fileMode, result, targetDir);
|
|
971
1075
|
}
|
|
972
1076
|
}
|
|
1077
|
+
function resolveBootstrapProjectName(targetDir) {
|
|
1078
|
+
const basename = path.basename(path.resolve(targetDir)).trim();
|
|
1079
|
+
return basename.length > 0 ? basename : DEFAULT_PROJECT_NAME;
|
|
1080
|
+
}
|
|
1081
|
+
export async function runInitBootstrap(options) {
|
|
1082
|
+
if (options.skipBootstrap) {
|
|
1083
|
+
return {
|
|
1084
|
+
skipped: true,
|
|
1085
|
+
reason: BOOTSTRAP_SKIP_REASON_FLAG,
|
|
1086
|
+
workspaceGenerated: false,
|
|
1087
|
+
packInstalled: false,
|
|
1088
|
+
};
|
|
1089
|
+
}
|
|
1090
|
+
const workspacePath = path.join(options.targetDir, WORKSPACE_FILENAME);
|
|
1091
|
+
const hasExistingWorkspace = fs.existsSync(workspacePath);
|
|
1092
|
+
if (hasExistingWorkspace && !options.force) {
|
|
1093
|
+
return {
|
|
1094
|
+
skipped: true,
|
|
1095
|
+
reason: BOOTSTRAP_SKIP_REASON_EXISTING_WORKSPACE,
|
|
1096
|
+
workspaceGenerated: false,
|
|
1097
|
+
packInstalled: false,
|
|
1098
|
+
};
|
|
1099
|
+
}
|
|
1100
|
+
const onboardModule = await import('./onboard.js');
|
|
1101
|
+
const onboardResult = (await onboardModule.runOnboard({
|
|
1102
|
+
targetDir: options.targetDir,
|
|
1103
|
+
nonInteractive: true,
|
|
1104
|
+
projectName: resolveBootstrapProjectName(options.targetDir),
|
|
1105
|
+
domain: options.bootstrapDomain,
|
|
1106
|
+
force: options.force,
|
|
1107
|
+
skipPackInstall: options.skipBootstrapPackInstall,
|
|
1108
|
+
skipDashboard: true,
|
|
1109
|
+
fetchFn: options.fetchFn ?? globalThis.fetch,
|
|
1110
|
+
}));
|
|
1111
|
+
if (!onboardResult.success) {
|
|
1112
|
+
const failureReason = onboardResult.errors.join('; ') || 'unknown onboarding error';
|
|
1113
|
+
throw new Error(`${BOOTSTRAP_ERROR_PREFIX} ${failureReason}`);
|
|
1114
|
+
}
|
|
1115
|
+
if (!options.skipBootstrapPackInstall &&
|
|
1116
|
+
options.bootstrapDomain !== BOOTSTRAP_CUSTOM_DOMAIN &&
|
|
1117
|
+
onboardResult.packInstalled !== true) {
|
|
1118
|
+
throw new Error(`${BOOTSTRAP_ERROR_PREFIX} failed to install ${options.bootstrapDomain} pack with integrity metadata. ` +
|
|
1119
|
+
`Retry after fixing registry access or rerun with --skip-bootstrap-pack-install.`);
|
|
1120
|
+
}
|
|
1121
|
+
return {
|
|
1122
|
+
skipped: false,
|
|
1123
|
+
workspaceGenerated: onboardResult.workspaceGenerated === true,
|
|
1124
|
+
packInstalled: onboardResult.packInstalled === true,
|
|
1125
|
+
};
|
|
1126
|
+
}
|
|
973
1127
|
/**
|
|
974
1128
|
* CLI entry point
|
|
975
1129
|
* WU-1085: Updated to use parseInitOptions for proper --help support
|
|
@@ -978,8 +1132,14 @@ async function scaffoldClientFiles(targetDir, options, result, tokens, client) {
|
|
|
978
1132
|
*/
|
|
979
1133
|
export async function main() {
|
|
980
1134
|
// WU-1378: Check for subcommands before parsing init options
|
|
1135
|
+
const invokedBinary = path.basename(process.argv[1] ?? '', '.js');
|
|
981
1136
|
const subcommand = process.argv[2];
|
|
982
|
-
if (
|
|
1137
|
+
if (invokedBinary === CLOUD_CONNECT_BIN) {
|
|
1138
|
+
const { runCloudConnectCli } = await import('./onboard.js');
|
|
1139
|
+
await runCloudConnectCli();
|
|
1140
|
+
return;
|
|
1141
|
+
}
|
|
1142
|
+
if (subcommand === INIT_SUBCOMMANDS.COMMANDS) {
|
|
983
1143
|
// Route to commands subcommand
|
|
984
1144
|
const { main: commandsMain } = await import('./commands.js');
|
|
985
1145
|
// Remove 'commands' from argv so the subcommand parser sees clean args
|
|
@@ -987,6 +1147,21 @@ export async function main() {
|
|
|
987
1147
|
await commandsMain();
|
|
988
1148
|
return;
|
|
989
1149
|
}
|
|
1150
|
+
if (subcommand === LEGACY_SUBCOMMANDS.ONBOARD ||
|
|
1151
|
+
subcommand === LEGACY_SUBCOMMANDS.WORKSPACE_INIT_COLON ||
|
|
1152
|
+
subcommand === LEGACY_SUBCOMMANDS.WORKSPACE_INIT_DASH) {
|
|
1153
|
+
throw new Error(`${LEGACY_SUBCOMMAND_ERROR_PREFIX} "${subcommand}". ${LEGACY_SUBCOMMAND_GUIDANCE}. ${LEGACY_SUBCOMMAND_HELP_HINT}.`);
|
|
1154
|
+
}
|
|
1155
|
+
if (subcommand === INIT_SUBCOMMANDS.CLOUD) {
|
|
1156
|
+
const cloudSubcommand = process.argv[3];
|
|
1157
|
+
if (cloudSubcommand !== CLOUD_SUBCOMMANDS.CONNECT) {
|
|
1158
|
+
throw new Error(`${INIT_ERROR_PREFIX} Unknown cloud subcommand "${cloudSubcommand ?? ''}". ${INIT_CLOUD_CONNECT_HELP}`);
|
|
1159
|
+
}
|
|
1160
|
+
const { runCloudConnectCli } = await import('./onboard.js');
|
|
1161
|
+
process.argv.splice(2, 2);
|
|
1162
|
+
await runCloudConnectCli();
|
|
1163
|
+
return;
|
|
1164
|
+
}
|
|
990
1165
|
const opts = parseInitOptions();
|
|
991
1166
|
const targetDir = process.cwd();
|
|
992
1167
|
console.log('[lumenflow init] Scaffolding LumenFlow project...');
|
|
@@ -994,15 +1169,23 @@ export async function main() {
|
|
|
994
1169
|
console.log(` Framework: ${opts.framework ?? 'none'}`);
|
|
995
1170
|
console.log(` Client: ${opts.client ?? 'auto'}`);
|
|
996
1171
|
console.log(` Gate preset: ${opts.preset ?? 'none (manual config)'}`);
|
|
997
|
-
|
|
998
|
-
|
|
999
|
-
|
|
1000
|
-
|
|
1001
|
-
|
|
1002
|
-
|
|
1003
|
-
|
|
1004
|
-
|
|
1005
|
-
|
|
1172
|
+
console.log(` Bootstrap domain: ${opts.bootstrapDomain}`);
|
|
1173
|
+
console.log(` Bootstrap pack install: ${opts.skipBootstrapPackInstall ? 'skipped (--skip-bootstrap-pack-install)' : 'required'}`);
|
|
1174
|
+
// WU-1968: Removed separate checkPrerequisites() call here.
|
|
1175
|
+
// runDoctorForInit() (called after scaffolding) already checks prerequisites
|
|
1176
|
+
// and displays results, avoiding duplicate output.
|
|
1177
|
+
const bootstrapResult = await runInitBootstrap({
|
|
1178
|
+
targetDir,
|
|
1179
|
+
force: opts.force,
|
|
1180
|
+
bootstrapDomain: opts.bootstrapDomain,
|
|
1181
|
+
skipBootstrap: opts.skipBootstrap,
|
|
1182
|
+
skipBootstrapPackInstall: opts.skipBootstrapPackInstall,
|
|
1183
|
+
});
|
|
1184
|
+
if (bootstrapResult.skipped) {
|
|
1185
|
+
console.log(` Bootstrap: skipped (${bootstrapResult.reason})`);
|
|
1186
|
+
}
|
|
1187
|
+
else {
|
|
1188
|
+
console.log(` Bootstrap: workspace=${bootstrapResult.workspaceGenerated ? 'created' : 'unchanged'}, pack=${bootstrapResult.packInstalled ? 'installed' : 'skipped'}`);
|
|
1006
1189
|
}
|
|
1007
1190
|
const result = await scaffoldProject(targetDir, {
|
|
1008
1191
|
force: opts.force,
|
|
@@ -1051,7 +1234,7 @@ export async function main() {
|
|
|
1051
1234
|
// WU-1576: Show enforcement hooks status -- vendor-agnostic (UnsafeAny adapter that produced files)
|
|
1052
1235
|
console.log('\n[lumenflow init] Done! Next steps:');
|
|
1053
1236
|
console.log(' 1. Review AGENTS.md and LUMENFLOW.md for workflow documentation');
|
|
1054
|
-
console.log(` 2.
|
|
1237
|
+
console.log(` 2. Review ${CONFIG_FILE_NAME} ${SOFTWARE_DELIVERY_KEY} settings for project defaults`);
|
|
1055
1238
|
console.log('');
|
|
1056
1239
|
console.log(` ${buildInitLaneLifecycleMessage(LANE_LIFECYCLE_STATUS.UNCONFIGURED)}`);
|
|
1057
1240
|
if (result.integrationFiles && result.integrationFiles.length > 0) {
|
|
@@ -384,7 +384,7 @@ export function buildAddWuMicroWorktreeOptions(wuArg, initId) {
|
|
|
384
384
|
},
|
|
385
385
|
};
|
|
386
386
|
}
|
|
387
|
-
async function main() {
|
|
387
|
+
export async function main() {
|
|
388
388
|
const args = createWUParser({
|
|
389
389
|
name: 'initiative-add-wu',
|
|
390
390
|
description: 'Link one or more WUs to an initiative bidirectionally',
|
|
@@ -242,7 +242,7 @@ function printSummary(stats) {
|
|
|
242
242
|
/**
|
|
243
243
|
* Main function
|
|
244
244
|
*/
|
|
245
|
-
async function main() {
|
|
245
|
+
export async function main() {
|
|
246
246
|
const args = createWUParser({
|
|
247
247
|
name: 'initiative-bulk-assign-wus',
|
|
248
248
|
description: 'Bulk-assign orphaned WUs to initiatives based on lane prefix rules',
|
|
@@ -117,14 +117,14 @@ function createInitiativeYamlInWorktree(worktreePath, id, slug, title, options =
|
|
|
117
117
|
}
|
|
118
118
|
/**
|
|
119
119
|
* Resolve lane lifecycle classification for initiative:create without mutating
|
|
120
|
-
* .
|
|
120
|
+
* workspace.yaml.
|
|
121
121
|
*
|
|
122
122
|
* WU-1751: initiative:create guidance should be read-only.
|
|
123
123
|
*/
|
|
124
124
|
export function resolveLaneLifecycleForInitiativeCreate(projectRoot) {
|
|
125
125
|
return ensureLaneLifecycleForProject(projectRoot, { persist: false });
|
|
126
126
|
}
|
|
127
|
-
async function main() {
|
|
127
|
+
export async function main() {
|
|
128
128
|
const args = createWUParser({
|
|
129
129
|
name: 'initiative-create',
|
|
130
130
|
description: 'Create a new Initiative with micro-worktree isolation (race-safe)',
|
package/dist/initiative-edit.js
CHANGED
|
@@ -469,7 +469,7 @@ export function buildNoEditsMessage() {
|
|
|
469
469
|
/**
|
|
470
470
|
* Main entry point
|
|
471
471
|
*/
|
|
472
|
-
async function main() {
|
|
472
|
+
export async function main() {
|
|
473
473
|
const opts = parseArgs();
|
|
474
474
|
const { id } = opts;
|
|
475
475
|
console.log(`${PREFIX} Starting Initiative edit for ${id}`);
|
package/dist/initiative-list.js
CHANGED
|
@@ -73,7 +73,7 @@ function truncate(str, maxLen) {
|
|
|
73
73
|
return '';
|
|
74
74
|
return str.length > maxLen ? `${str.substring(0, maxLen - 3)}...` : str;
|
|
75
75
|
}
|
|
76
|
-
async function main() {
|
|
76
|
+
export async function main() {
|
|
77
77
|
const args = createWUParser({
|
|
78
78
|
name: 'initiative-list',
|
|
79
79
|
description: 'List all initiatives with progress percentages',
|
package/dist/initiative-plan.js
CHANGED
|
@@ -252,7 +252,7 @@ export function getCommitMessage(initId, planUri) {
|
|
|
252
252
|
const filename = planUri.replace(PLAN_URI_SCHEME, '');
|
|
253
253
|
return `docs: link plan ${filename} to ${initId.toLowerCase()}`;
|
|
254
254
|
}
|
|
255
|
-
async function main() {
|
|
255
|
+
export async function main() {
|
|
256
256
|
const args = createWUParser({
|
|
257
257
|
name: 'init-plan',
|
|
258
258
|
description: 'Link a plan file to an initiative',
|
|
@@ -377,6 +377,4 @@ import { runCLI } from './cli-entry-point.js';
|
|
|
377
377
|
if (import.meta.main) {
|
|
378
378
|
void runCLI(main);
|
|
379
379
|
}
|
|
380
|
-
// Export for testing
|
|
381
|
-
export { main };
|
|
382
380
|
//# sourceMappingURL=initiative-plan.js.map
|
|
@@ -40,11 +40,29 @@ function hasIncompletePhase(phases) {
|
|
|
40
40
|
return normalizeLifecycleStatus(phase.status) !== WU_STATUS.DONE;
|
|
41
41
|
});
|
|
42
42
|
}
|
|
43
|
-
|
|
43
|
+
function hasAllLinkedWUsDone(progress) {
|
|
44
|
+
if (!progress) {
|
|
45
|
+
return false;
|
|
46
|
+
}
|
|
47
|
+
return progress.total > 0 && progress.done === progress.total;
|
|
48
|
+
}
|
|
49
|
+
function hasIncompleteLinkedWUs(progress) {
|
|
50
|
+
if (!progress) {
|
|
51
|
+
return false;
|
|
52
|
+
}
|
|
53
|
+
return progress.total > 0 && progress.done < progress.total;
|
|
54
|
+
}
|
|
55
|
+
export function deriveInitiativeLifecycleStatus(status, phases, progress) {
|
|
44
56
|
const normalizedStatus = normalizeLifecycleStatus(status);
|
|
57
|
+
if (hasAllLinkedWUsDone(progress)) {
|
|
58
|
+
return WU_STATUS.DONE;
|
|
59
|
+
}
|
|
45
60
|
if (normalizedStatus === WU_STATUS.DONE && hasIncompletePhase(phases)) {
|
|
46
61
|
return WU_STATUS.IN_PROGRESS;
|
|
47
62
|
}
|
|
63
|
+
if (normalizedStatus === WU_STATUS.DONE && hasIncompleteLinkedWUs(progress)) {
|
|
64
|
+
return WU_STATUS.IN_PROGRESS;
|
|
65
|
+
}
|
|
48
66
|
return normalizedStatus || WU_STATUS.IN_PROGRESS;
|
|
49
67
|
}
|
|
50
68
|
function getWUBlockers(doc) {
|
|
@@ -54,6 +72,28 @@ function getWUBlockers(doc) {
|
|
|
54
72
|
}
|
|
55
73
|
return asStringArray(doc.dependencies);
|
|
56
74
|
}
|
|
75
|
+
function hasPhaseWUStatus(phaseWUs, status) {
|
|
76
|
+
return phaseWUs.some((wu) => normalizeLifecycleStatus(wu.doc.status) === status);
|
|
77
|
+
}
|
|
78
|
+
function areAllPhaseWUsDone(phaseWUs) {
|
|
79
|
+
return (phaseWUs.length > 0 &&
|
|
80
|
+
phaseWUs.every((wu) => normalizeLifecycleStatus(wu.doc.status) === WU_STATUS.DONE));
|
|
81
|
+
}
|
|
82
|
+
export function deriveInitiativePhaseStatus(status, phaseWUs) {
|
|
83
|
+
if (areAllPhaseWUsDone(phaseWUs)) {
|
|
84
|
+
return WU_STATUS.DONE;
|
|
85
|
+
}
|
|
86
|
+
if (hasPhaseWUStatus(phaseWUs, WU_STATUS.IN_PROGRESS)) {
|
|
87
|
+
return WU_STATUS.IN_PROGRESS;
|
|
88
|
+
}
|
|
89
|
+
if (hasPhaseWUStatus(phaseWUs, WU_STATUS.BLOCKED)) {
|
|
90
|
+
return WU_STATUS.BLOCKED;
|
|
91
|
+
}
|
|
92
|
+
if (hasPhaseWUStatus(phaseWUs, WU_STATUS.READY)) {
|
|
93
|
+
return WU_STATUS.READY;
|
|
94
|
+
}
|
|
95
|
+
return normalizeLifecycleStatus(status) || WU_STATUS.IN_PROGRESS;
|
|
96
|
+
}
|
|
57
97
|
function priorityRank(priority) {
|
|
58
98
|
const p = String(priority || '').toUpperCase();
|
|
59
99
|
const map = { P0: 0, P1: 1, P2: 2, P3: 3 };
|
|
@@ -75,7 +115,7 @@ function renderDetailed(initiative, useColor) {
|
|
|
75
115
|
const wuById = new Map(wus.map((wu) => [wu.id, wu]));
|
|
76
116
|
const phaseGroups = getInitiativePhases(id);
|
|
77
117
|
const phases = toInitiativePhases(doc);
|
|
78
|
-
const status = deriveInitiativeLifecycleStatus(doc.status, phases);
|
|
118
|
+
const status = deriveInitiativeLifecycleStatus(doc.status, phases, progress);
|
|
79
119
|
const docTitle = asString(doc.title);
|
|
80
120
|
const rawStatus = asString(doc.status);
|
|
81
121
|
const normalizedRawStatus = normalizeLifecycleStatus(rawStatus);
|
|
@@ -129,7 +169,7 @@ function renderDetailed(initiative, useColor) {
|
|
|
129
169
|
console.log('\nPhases:');
|
|
130
170
|
for (const phase of phases) {
|
|
131
171
|
const phaseWUs = phaseGroups.get(phase.id) || [];
|
|
132
|
-
const phaseStatus = formatStatus(
|
|
172
|
+
const phaseStatus = formatStatus(deriveInitiativePhaseStatus(phase.status, phaseWUs), useColor);
|
|
133
173
|
const phaseTitle = asString(phase.title) || `Phase ${phase.id}`;
|
|
134
174
|
console.log(` ${phase.id}. ${phaseTitle.padEnd(30)} [${phaseStatus}] ${phaseWUs.length} WUs`);
|
|
135
175
|
}
|
|
@@ -169,7 +209,7 @@ function renderJSON(initiative) {
|
|
|
169
209
|
const wus = getInitiativeWUs(id);
|
|
170
210
|
const phaseGroups = getInitiativePhases(id);
|
|
171
211
|
const phases = toInitiativePhases(doc);
|
|
172
|
-
const status = deriveInitiativeLifecycleStatus(doc.status, phases);
|
|
212
|
+
const status = deriveInitiativeLifecycleStatus(doc.status, phases, progress);
|
|
173
213
|
const output = {
|
|
174
214
|
id,
|
|
175
215
|
slug: asString(doc.slug),
|
|
@@ -191,10 +231,11 @@ function renderJSON(initiative) {
|
|
|
191
231
|
},
|
|
192
232
|
phases: phases.map((phase) => {
|
|
193
233
|
const phaseWUs = phaseGroups.get(phase.id) || [];
|
|
234
|
+
const phaseStatus = deriveInitiativePhaseStatus(phase.status, phaseWUs);
|
|
194
235
|
return {
|
|
195
236
|
id: phase.id,
|
|
196
237
|
title: asString(phase.title),
|
|
197
|
-
status:
|
|
238
|
+
status: phaseStatus,
|
|
198
239
|
wuCount: phaseWUs.length,
|
|
199
240
|
wus: phaseWUs.map((w) => ({
|
|
200
241
|
id: w.id,
|
|
@@ -258,7 +299,7 @@ function truncate(str, maxLen) {
|
|
|
258
299
|
function capitalizeFirst(str) {
|
|
259
300
|
return str.charAt(0).toUpperCase() + str.slice(1).replace(/_/g, ' ');
|
|
260
301
|
}
|
|
261
|
-
async function main() {
|
|
302
|
+
export async function main() {
|
|
262
303
|
const args = createWUParser({
|
|
263
304
|
name: 'initiative-status',
|
|
264
305
|
description: 'Show detailed initiative view with phases and WUs',
|