@automaton-labs/aib 0.0.7 → 0.0.8
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 -257
- package/config/agent-dx-policy.default.json +31 -0
- package/config/control-plane-client.default.json +3 -0
- package/dist/agent-dx/agent-dx.js +805 -0
- package/dist/agent-dx/presentation.js +32 -0
- package/dist/alias-advisor/analyze.js +982 -0
- package/dist/alias-advisor/exact-text-cost.js +74 -0
- package/dist/alias-advisor/lexical.js +240 -0
- package/dist/alias-advisor/model.js +2 -0
- package/dist/alias-advisor/path-identity.js +49 -0
- package/dist/alias-advisor/ranking.js +171 -0
- package/dist/alias-advisor/token-estimator.js +85 -0
- package/dist/bin/aib.js +5 -1
- package/dist/bin/cli.js +811 -4
- package/dist/commands/add-missing-imports-preview-cache.js +99 -2
- package/dist/commands/add-missing-imports.js +241 -2
- package/dist/commands/apply-module-plan.js +1319 -3
- package/dist/commands/background-command.js +378 -2
- package/dist/commands/captured-input.js +74 -1
- package/dist/commands/config-command.js +314 -2
- package/dist/commands/config-output.js +357 -10
- package/dist/commands/control-plane-command.js +183 -1
- package/dist/commands/declaration-command.js +1209 -7
- package/dist/commands/declaration-execution-cache.js +79 -1
- package/dist/commands/declaration-format.js +221 -1
- package/dist/commands/declaration-preview-cache.js +114 -2
- package/dist/commands/diagnostics-command.js +70 -3
- package/dist/commands/doctor.js +137 -3
- package/dist/commands/execution-command.js +117 -1
- package/dist/commands/exports-star-collapse-command.js +178 -0
- package/dist/commands/exports-star-command.js +252 -0
- package/dist/commands/exports-star-preview-cache.js +84 -0
- package/dist/commands/feedback-command.js +176 -3
- package/dist/commands/file-move-to-dir-execution-cache.js +92 -1
- package/dist/commands/file-move-to-dir-preview-cache.js +125 -2
- package/dist/commands/file-move-to-dir-worker.js +54 -0
- package/dist/commands/file-move-to-dir.js +1073 -5
- package/dist/commands/file-mutation-runtime.js +102 -1
- package/dist/commands/file-mutation-worker-apply.js +180 -0
- package/dist/commands/file-refactor-batch-execution-cache.js +90 -1
- package/dist/commands/file-refactor-batch-preview-cache.js +125 -2
- package/dist/commands/file-refactor-batch-worker.js +54 -0
- package/dist/commands/file-refactor-batch.js +1154 -5
- package/dist/commands/file-rename-execution-cache.js +92 -1
- package/dist/commands/file-rename-preview-cache.js +125 -2
- package/dist/commands/file-rename-worker.js +54 -0
- package/dist/commands/file-rename.js +1053 -5
- package/dist/commands/file-text-edit-executor.js +205 -0
- package/dist/commands/find-importers.js +52 -1
- package/dist/commands/find-unused-imports.js +55 -1
- package/dist/commands/generate-docs-command.js +244 -6
- package/dist/commands/help-command.js +460 -7
- package/dist/commands/import-specifier-policy.js +391 -0
- package/dist/commands/imports-command.js +68 -1
- package/dist/commands/imports-rebase.js +1138 -0
- package/dist/commands/init-skill-usage.js +92 -3
- package/dist/commands/init-workspace.js +30 -1
- package/dist/commands/inspect-alias-candidates.js +413 -0
- package/dist/commands/inspect-cycles.js +811 -5
- package/dist/commands/inspect-direct-usages.js +98 -0
- package/dist/commands/inspect-duplicates-format.js +229 -0
- package/dist/commands/inspect-format-primitives.js +127 -0
- package/dist/commands/inspect-format.js +1590 -18
- package/dist/commands/inspect-graph.js +1553 -9
- package/dist/commands/inspect-imports.js +339 -2
- package/dist/commands/inspect-mixed-format.js +524 -0
- package/dist/commands/inspect-module-plan-format.js +216 -0
- package/dist/commands/inspect-module-plan-serialization.js +402 -0
- package/dist/commands/inspect-reference-path-format.js +157 -0
- package/dist/commands/inspect-request-values.js +599 -0
- package/dist/commands/inspect-selector-kind.js +21 -0
- package/dist/commands/inspect-selector.js +50 -0
- package/dist/commands/inspect-symbol-format.js +90 -0
- package/dist/commands/inspect-topology.js +435 -0
- package/dist/commands/inspect-tree.js +827 -5
- package/dist/commands/inspect-usages-detail.js +793 -0
- package/dist/commands/inspect-usages-evidence.js +31 -0
- package/dist/commands/inspect-usages-format.js +367 -0
- package/dist/commands/inspect.js +1450 -16
- package/dist/commands/internal-command.js +64 -0
- package/dist/commands/json-file-input.js +60 -1
- package/dist/commands/module-plan-cache.js +156 -2
- package/dist/commands/module-plan-standalone.js +208 -0
- package/dist/commands/module-plan-timeout.js +77 -1
- package/dist/commands/move-preview-cache.js +101 -2
- package/dist/commands/mutate-aggregate-output.js +996 -0
- package/dist/commands/mutate-child-execution.js +374 -0
- package/dist/commands/mutate-command.js +1394 -0
- package/dist/commands/mutate-declaration-output.js +313 -0
- package/dist/commands/mutate-domain-adapters.js +638 -0
- package/dist/commands/mutate-execution-cache.js +114 -0
- package/dist/commands/mutate-execution-status.js +598 -0
- package/dist/commands/mutate-failure-output.js +531 -0
- package/dist/commands/mutate-file-view.js +151 -0
- package/dist/commands/mutate-object-output.js +91 -0
- package/dist/commands/mutate-output-values.js +97 -0
- package/dist/commands/mutate-preview-cache.js +86 -0
- package/dist/commands/mutate-response-replay.js +153 -0
- package/dist/commands/mutate-result-projection.js +818 -0
- package/dist/commands/mutation-eta.js +28 -0
- package/dist/commands/mutation-execution-cache.js +140 -3
- package/dist/commands/mutation-recovery-journal.js +195 -0
- package/dist/commands/normalize-imports.js +1120 -4
- package/dist/commands/object-pack-command.js +546 -0
- package/dist/commands/object-pack-preview-cache.js +88 -0
- package/dist/commands/observability-command.js +47 -3
- package/dist/commands/ota-command.js +403 -2
- package/dist/commands/print-config.js +10 -1
- package/dist/commands/quick-read.js +1113 -11
- package/dist/commands/refactor-batch-builder.js +265 -1
- package/dist/commands/refactor-batch-execution-cache.js +85 -1
- package/dist/commands/refactor-batch-preview-cache.js +96 -2
- package/dist/commands/refactor-batch.js +461 -4
- package/dist/commands/rename-entities.js +794 -4
- package/dist/commands/rename-execution-cache.js +49 -1
- package/dist/commands/rename-input.js +22 -1
- package/dist/commands/rename-polling-policy.js +68 -0
- package/dist/commands/rename-preview-cache.js +96 -2
- package/dist/commands/result-view.js +993 -7
- package/dist/commands/reveal-command.js +445 -5
- package/dist/commands/selector-suggestions.js +93 -0
- package/dist/commands/session-workspace.js +1836 -31
- package/dist/commands/shared.js +2 -1
- package/dist/commands/skills-command.js +315 -0
- package/dist/commands/sync-command.js +59 -2
- package/dist/commands/worker-command.js +173 -1
- package/dist/commands/workspace-cache.js +55 -1
- package/dist/config/defaults.js +26 -1
- package/dist/config/env-vars.js +77 -1
- package/dist/config/glob-match.js +44 -1
- package/dist/config/import-rules.js +165 -1
- package/dist/config/local-config.js +293 -3
- package/dist/config/mutation-comments.js +51 -1
- package/dist/config/path-aliases.js +165 -1
- package/dist/config/path-display.js +84 -1
- package/dist/config/product-storage.js +37 -1
- package/dist/config/request-env.js +21 -0
- package/dist/config/request-routing-context.js +23 -0
- package/dist/config/resolve-command-alias.js +74 -1
- package/dist/config/resolve.js +24 -1
- package/dist/config/tsconfig-discovery.js +113 -1
- package/dist/config/typescript-preferences.js +131 -0
- package/dist/config/workspace-root.js +310 -3
- package/dist/config/workspace-state.js +254 -1
- package/dist/content/content-bundle.js +88 -1
- package/dist/diagnostics/module-plan-timeline.js +75 -2
- package/dist/diagnostics/readiness-text.js +45 -8
- package/dist/dsl/aib-dsl.js +838 -1
- package/dist/dsl/declaration-dsl.js +264 -1
- package/dist/dsl/file-move-to-dir-dsl.js +123 -1
- package/dist/dsl/file-refactor-batch-dsl.js +203 -1
- package/dist/dsl/file-rename-dsl.js +135 -1
- package/dist/dsl/mutate-dsl.js +746 -0
- package/dist/help/bootstrap.bash.md +176 -341
- package/dist/help/bootstrap.md +175 -340
- package/dist/help/bootstrap.pwsh.md +176 -341
- package/dist/help/docs/basics.md +1 -1
- package/dist/help/docs/config-setup.import-normalize.md +65 -65
- package/dist/help/docs/config-setup.import-rules.md +6 -5
- package/dist/help/docs/first-setup.md +6 -5
- package/dist/help/docs/help-protocol.md +4 -3
- package/dist/help/docs/import.base.md +38 -0
- package/dist/help/docs/import.rebase.md +85 -0
- package/dist/help/docs/inspect.aliasCandidates.md +39 -0
- package/dist/help/docs/inspect.code.md +1 -7
- package/dist/help/docs/inspect.file.md +10 -19
- package/dist/help/docs/inspect.graph.md +3 -17
- package/dist/help/{dsl/docs/inspect.md → docs/inspect.shared.md} +13 -12
- package/dist/help/docs/modulePlan.md +24 -28
- package/dist/help/docs/move.md +19 -22
- package/dist/help/{dsl/topics/file.move.md → docs/moveToDir.md} +36 -34
- package/dist/help/docs/mutate.mixed.md +34 -0
- package/dist/help/docs/mutation.shared.md +55 -0
- package/dist/help/docs/patterns.md +3 -12
- package/dist/help/docs/qr.md +12 -6
- package/dist/help/docs/quick-map.md +36 -24
- package/dist/help/docs/recipe.file-layout.md +10 -10
- package/dist/help/docs/recipe.import-boundary.md +92 -0
- package/dist/help/docs/recipe.safe-artifact-probing.md +68 -0
- package/dist/help/docs/recipe.unfamiliar-area.md +64 -0
- package/dist/help/docs/recipes.md +20 -0
- package/dist/help/docs/rename.md +19 -27
- package/dist/help/docs/renameFile.md +36 -0
- package/dist/help/docs/rules.md +26 -0
- package/dist/help/dsl/bootstrap.bash.md +176 -341
- package/dist/help/dsl/bootstrap.md +175 -340
- package/dist/help/dsl/bootstrap.pwsh.md +176 -341
- package/dist/help/dsl/docs/basics.md +1 -1
- package/dist/help/dsl/docs/config-setup.import-normalize.md +65 -65
- package/dist/help/dsl/docs/config-setup.import-rules.md +6 -5
- package/dist/help/dsl/docs/first-setup.md +6 -5
- package/dist/help/dsl/docs/help-protocol.md +4 -3
- package/dist/help/dsl/docs/import.base.md +38 -0
- package/dist/help/dsl/docs/import.rebase.md +85 -0
- package/dist/help/dsl/docs/inspect.aliasCandidates.md +39 -0
- package/dist/help/dsl/docs/inspect.code.md +1 -7
- package/dist/help/dsl/docs/inspect.file.md +10 -19
- package/dist/help/dsl/docs/inspect.graph.md +3 -17
- package/dist/help/{docs/inspect.md → dsl/docs/inspect.shared.md} +13 -12
- package/dist/help/dsl/docs/modulePlan.md +24 -28
- package/dist/help/dsl/docs/move.md +19 -22
- package/dist/help/{topics/file.move.md → dsl/docs/moveToDir.md} +36 -34
- package/dist/help/dsl/docs/mutate.mixed.md +34 -0
- package/dist/help/dsl/docs/mutation.shared.md +55 -0
- package/dist/help/dsl/docs/patterns.md +3 -12
- package/dist/help/dsl/docs/qr.md +12 -6
- package/dist/help/dsl/docs/quick-map.md +36 -24
- package/dist/help/dsl/docs/recipe.file-layout.md +10 -10
- package/dist/help/dsl/docs/recipe.import-boundary.md +92 -0
- package/dist/help/dsl/docs/recipe.safe-artifact-probing.md +68 -0
- package/dist/help/dsl/docs/recipe.unfamiliar-area.md +64 -0
- package/dist/help/dsl/docs/recipes.md +20 -0
- package/dist/help/dsl/docs/rename.md +19 -27
- package/dist/help/dsl/docs/renameFile.md +36 -0
- package/dist/help/dsl/docs/rules.md +26 -0
- package/dist/help/dsl/full.md +175 -340
- package/dist/help/dsl/help-index.md +48 -43
- package/dist/help/dsl/snippets/agents.md +2 -2
- package/dist/help/dsl/tokens/qr.inline.examples.md +1 -1
- package/dist/help/dsl/topics/basics.md +1 -1
- package/dist/help/dsl/topics/config-setup.import-normalize.md +65 -65
- package/dist/help/dsl/topics/config-setup.import-rules.md +6 -5
- package/dist/help/dsl/topics/first-setup.md +6 -5
- package/dist/help/dsl/topics/help-protocol.md +4 -3
- package/dist/help/dsl/topics/import.base.md +36 -0
- package/dist/help/dsl/topics/import.rebase.md +83 -0
- package/dist/help/dsl/topics/inspect.aliasCandidates.md +37 -0
- package/dist/help/dsl/topics/inspect.code.md +1 -7
- package/dist/help/dsl/topics/inspect.file.md +10 -19
- package/dist/help/dsl/topics/inspect.graph.md +3 -17
- package/dist/help/dsl/topics/{inspect.md → inspect.shared.md} +13 -12
- package/dist/help/dsl/topics/modulePlan.md +21 -26
- package/dist/help/dsl/topics/move.md +17 -18
- package/dist/help/{docs/file.move.md → dsl/topics/moveToDir.md} +33 -35
- package/dist/help/dsl/topics/mutate.mixed.md +32 -0
- package/dist/help/dsl/topics/mutation.shared.md +53 -0
- package/dist/help/dsl/topics/patterns.md +3 -12
- package/dist/help/dsl/topics/qr.md +12 -6
- package/dist/help/dsl/topics/quick-map.md +36 -24
- package/dist/help/dsl/topics/recipe.file-layout.md +10 -10
- package/dist/help/dsl/topics/recipe.import-boundary.md +90 -0
- package/dist/help/dsl/topics/recipe.safe-artifact-probing.md +66 -0
- package/dist/help/dsl/topics/recipe.unfamiliar-area.md +62 -0
- package/dist/help/dsl/topics/recipes.md +18 -0
- package/dist/help/dsl/topics/rename.md +15 -15
- package/dist/help/dsl/topics/renameFile.md +34 -0
- package/dist/help/dsl/topics/rules.md +24 -0
- package/dist/help/full.md +175 -340
- package/dist/help/help-index.md +48 -43
- package/dist/help/help-meta.json +98 -48
- package/dist/help/index.md +52 -20
- package/dist/help/snippets/agents.md +2 -2
- package/dist/help/tokens/qr.inline.examples.md +1 -1
- package/dist/help/topics/basics.md +1 -1
- package/dist/help/topics/config-setup.import-normalize.md +65 -65
- package/dist/help/topics/config-setup.import-rules.md +6 -5
- package/dist/help/topics/first-setup.md +6 -5
- package/dist/help/topics/help-protocol.md +4 -3
- package/dist/help/topics/import.base.md +36 -0
- package/dist/help/topics/import.rebase.md +83 -0
- package/dist/help/topics/inspect.aliasCandidates.md +37 -0
- package/dist/help/topics/inspect.code.md +1 -7
- package/dist/help/topics/inspect.file.md +10 -19
- package/dist/help/topics/inspect.graph.md +3 -17
- package/dist/help/topics/{inspect.md → inspect.shared.md} +13 -12
- package/dist/help/topics/modulePlan.md +21 -26
- package/dist/help/topics/move.md +17 -18
- package/dist/help/{dsl/docs/file.move.md → topics/moveToDir.md} +33 -35
- package/dist/help/topics/mutate.mixed.md +32 -0
- package/dist/help/topics/mutation.shared.md +53 -0
- package/dist/help/topics/patterns.md +3 -12
- package/dist/help/topics/qr.md +12 -6
- package/dist/help/topics/quick-map.md +36 -24
- package/dist/help/topics/recipe.file-layout.md +10 -10
- package/dist/help/topics/recipe.import-boundary.md +90 -0
- package/dist/help/topics/recipe.safe-artifact-probing.md +66 -0
- package/dist/help/topics/recipe.unfamiliar-area.md +62 -0
- package/dist/help/topics/recipes.md +18 -0
- package/dist/help/topics/rename.md +15 -15
- package/dist/help/topics/renameFile.md +34 -0
- package/dist/help/topics/rules.md +24 -0
- package/dist/host/capabilities.js +56 -1
- package/dist/imports/standalone-import-analysis.js +602 -0
- package/dist/imports/standalone-import-model.js +2 -0
- package/dist/imports/standalone-import-process.js +66 -0
- package/dist/imports/standalone-import-worker.js +27 -0
- package/dist/imports/standalone-ts-project.js +147 -0
- package/dist/inspect/inspect-duplicates-service.js +526 -0
- package/dist/inspect/inspect-reverse-module-closure.js +338 -0
- package/dist/inspect/inspect-source-ranges.js +82 -0
- package/dist/inspect/inspect-source-shape.js +649 -0
- package/dist/inspect/standalone-inspect-analysis.js +319 -0
- package/dist/inspect/standalone-inspect-model.js +9 -0
- package/dist/inspect/standalone-inspect-process.js +55 -0
- package/dist/inspect/standalone-inspect-usages.js +274 -0
- package/dist/inspect/standalone-inspect-worker.js +13 -0
- package/dist/metrics/central-metrics.js +101 -2
- package/dist/mutation/concrete-edit-plan.js +157 -0
- package/dist/mutation/exports-star-collapse-preview.js +361 -0
- package/dist/mutation/exports-star-expand-apply.js +373 -0
- package/dist/mutation/exports-star-expand-preview.js +807 -0
- package/dist/mutation/file-impact-scan.js +182 -0
- package/dist/mutation/file-mutation-discovery.js +674 -0
- package/dist/mutation/file-mutation-eta.js +99 -0
- package/dist/mutation/file-mutation-standalone-apply.js +584 -0
- package/dist/mutation/file-mutation-standalone-planner.js +500 -0
- package/dist/mutation/file-mutation-tsserver-session.js +473 -0
- package/dist/mutation/mutation-estimate.js +45 -0
- package/dist/mutation/mutation-plan.js +467 -0
- package/dist/mutation/object-mutation-foundation.js +2 -0
- package/dist/mutation/object-mutation-partition.js +148 -0
- package/dist/mutation/object-pack-semantic-apply.js +507 -0
- package/dist/mutation/object-pack-semantic-preview.js +984 -0
- package/dist/mutation/object-unpack-semantic-preview.js +993 -0
- package/dist/mutation/package-manifest-impact.js +176 -0
- package/dist/mutation/rename-owner-worker-child.js +37 -0
- package/dist/mutation/rename-owner-worker.js +122 -0
- package/dist/mutation/runtime-cycle-query.js +66 -0
- package/dist/mutation/semantic-execution-progress.js +63 -0
- package/dist/mutation/semantic-export-index.js +474 -0
- package/dist/mutation/semantic-impact-scan.js +434 -0
- package/dist/mutation/semantic-model.js +2 -0
- package/dist/mutation/semantic-move-best-effort-planner.js +209 -0
- package/dist/mutation/semantic-move-config-worker-child.js +61 -0
- package/dist/mutation/semantic-move-config-worker.js +449 -0
- package/dist/mutation/semantic-move-declarations.js +94 -0
- package/dist/mutation/semantic-move-metrics.js +119 -0
- package/dist/mutation/semantic-move-model.js +2 -0
- package/dist/mutation/semantic-move-owner-authority.js +122 -0
- package/dist/mutation/semantic-move-owner-candidates.js +300 -0
- package/dist/mutation/semantic-move-owner-divergence-harness.js +474 -0
- package/dist/mutation/semantic-move-owner-divergence-runner.js +162 -0
- package/dist/mutation/semantic-move-plan-hash.js +56 -0
- package/dist/mutation/semantic-move-policy.js +360 -0
- package/dist/mutation/semantic-move-process.js +218 -0
- package/dist/mutation/semantic-move-provider-diagnostics.js +27 -0
- package/dist/mutation/semantic-move-standalone-engine.js +919 -0
- package/dist/mutation/semantic-move-standalone-planner.js +1553 -0
- package/dist/mutation/semantic-move-transaction.js +639 -0
- package/dist/mutation/semantic-mutation-engine.js +478 -0
- package/dist/mutation/semantic-mutation-runtime.js +521 -0
- package/dist/mutation/semantic-planner-retry.js +26 -0
- package/dist/mutation/semantic-program-roots.js +69 -0
- package/dist/mutation/semantic-rename-commonjs.js +229 -0
- package/dist/mutation/semantic-rename-config-worker-child.js +46 -0
- package/dist/mutation/semantic-rename-config-worker.js +498 -0
- package/dist/mutation/semantic-rename-locations.js +192 -0
- package/dist/mutation/semantic-rename-model.js +2 -0
- package/dist/mutation/semantic-rename-process.js +210 -0
- package/dist/mutation/semantic-rename-standalone-engine.js +302 -0
- package/dist/mutation/semantic-rename-standalone-planner.js +567 -0
- package/dist/mutation/semantic-rename-transaction.js +333 -0
- package/dist/mutation/semantic-unused-import-cleanup.js +248 -0
- package/dist/mutation/semantic-worker-retry.js +40 -0
- package/dist/mutation/semantic-workspace.js +804 -0
- package/dist/mutation/targeted-import-canonicalizer.js +359 -0
- package/dist/observability/config.js +206 -1
- package/dist/observability/context.js +59 -1
- package/dist/observability/failure-snapshot.js +124 -2
- package/dist/observability/recent.js +63 -2
- package/dist/payloads/read-stdin-json.js +212 -1
- package/dist/rg-wrapper/core.js +714 -6
- package/dist/rg-wrapper/options.js +125 -1
- package/dist/rtk-wrapper/core.js +144 -2
- package/dist/rtk-wrapper/git-safety.js +203 -0
- package/dist/rtk-wrapper/output-adapter.js +106 -0
- package/dist/runtime/buffered-process.js +114 -0
- package/dist/runtime/bundled-node.js +97 -1
- package/dist/runtime/command-lifecycle.js +2 -0
- package/dist/runtime/input-source.js +238 -1
- package/dist/runtime/node-cli-identity.js +37 -0
- package/dist/runtime/run-command.js +191 -1
- package/dist/selectors/parse-entities.js +84 -1
- package/dist/semantic/semantic-context-pool.js +830 -0
- package/dist/semantic/semantic-context-provider.js +416 -0
- package/dist/semantic/semantic-resident-admission.js +38 -0
- package/dist/semantic/semantic-worker-child.js +40 -0
- package/dist/semantic/semantic-worker-manager.js +460 -0
- package/dist/semantic/semantic-worker-protocol.js +2 -0
- package/dist/semantic/semantic-worker-runtime.js +38 -0
- package/dist/semantic/workspace-semantic-context-pools.js +136 -0
- package/dist/session/client.js +359 -1
- package/dist/session/daemon-state.js +185 -2
- package/dist/session/external-tool-coordinator.js +88 -0
- package/dist/session/external-tool-request.js +52 -0
- package/dist/session/lane-owner.js +116 -0
- package/dist/session/paths.js +71 -1
- package/dist/session/runtime-lifecycle.js +225 -0
- package/dist/session/runtime-shutdown.js +95 -0
- package/dist/session/server.js +1194 -7
- package/dist/session/session-health.js +27 -0
- package/dist/shared/agent-text.js +29 -1
- package/dist/shared/errors.js +496 -30
- package/dist/shared/event-loop.js +6 -1
- package/dist/shared/hints.js +37 -1
- package/dist/shared/metrics.js +43 -1
- package/dist/shared/presentation.js +69 -4
- package/dist/shared/stdin-examples.js +77 -1
- package/dist/shared/stdout.js +6 -2
- package/dist/shared/types.js +23 -1
- package/dist/tool-runtime/runtime-tools.js +120 -1
- package/dist/topology/availability.js +663 -0
- package/dist/topology/cache.js +130 -0
- package/dist/topology/candidates.js +372 -0
- package/dist/topology/core.js +903 -0
- package/dist/topology/dependency-snapshot.js +189 -0
- package/dist/topology/model.js +2 -0
- package/dist/topology/scope.js +100 -0
- package/dist/topology/ts-oracle-batch.js +529 -0
- package/dist/topology/ts-oracle-host.js +69 -0
- package/dist/topology/ts-oracle-model.js +2 -0
- package/dist/topology/ts-oracle.js +224 -0
- package/dist/topology/tsconfig-loader.js +105 -0
- package/dist/topology/workspace-project-index.js +542 -0
- package/dist/tracing/config.js +192 -2
- package/dist/tracing/failure-summary.js +100 -0
- package/dist/tracing/trace.js +318 -5
- package/dist/tsc-wrapper/core.js +697 -0
- package/dist/workers/control-plane/aib-control-plane-worker.cjs +32 -32
- package/dist/workers/control-plane/client-config.default.json +3 -3
- package/dist/workers/lexical-worker-child.js +27 -0
- package/dist/workers/lexical-worker-manager.js +394 -0
- package/dist/workers/lexical-worker-protocol.js +2 -0
- package/dist/workers/lexical-worker-runtime.js +25 -0
- package/dist/workers/owned-one-shot-process.js +115 -0
- package/dist/workers/product-storage.js +23 -1
- package/dist/workers/registry.js +241 -1
- package/package.json +8 -13
- package/scripts/postinstall.cjs +29 -29
- package/scripts/provision-runtime.cjs +411 -459
- package/dist/client/http-client.js +0 -1
- package/dist/client/transport-options.js +0 -1
- package/dist/client/websocket-client.js +0 -1
- package/dist/commands/entity-resolution.js +0 -1
- package/dist/commands/file-command.js +0 -1
- package/dist/commands/host-command.js +0 -1
- package/dist/commands/inspect-symbol-query.js +0 -1
- package/dist/commands/list-instances.js +0 -1
- package/dist/commands/module-plan-command.js +0 -1
- package/dist/commands/move-command.js +0 -1
- package/dist/commands/move-to-file.js +0 -2
- package/dist/commands/ping.js +0 -1
- package/dist/commands/refactor-command.js +0 -1
- package/dist/commands/rename-command.js +0 -1
- package/dist/commands/runtime-command.js +0 -4
- package/dist/commands/runtime-info.js +0 -1
- package/dist/commands/validate-module-plan.js +0 -2
- package/dist/compatibility/policy.js +0 -1
- package/dist/config/auto-start-ide.js +0 -1
- package/dist/discovery/registry.js +0 -1
- package/dist/discovery/select-instance.js +0 -1
- package/dist/help/docs/file.rename.md +0 -35
- package/dist/help/docs/mutation.md +0 -60
- package/dist/help/docs/refactor.batch.md +0 -44
- package/dist/help/dsl/docs/file.rename.md +0 -35
- package/dist/help/dsl/docs/mutation.md +0 -60
- package/dist/help/dsl/docs/refactor.batch.md +0 -44
- package/dist/help/dsl/topics/file.rename.md +0 -33
- package/dist/help/dsl/topics/mutation.md +0 -58
- package/dist/help/dsl/topics/refactor.batch.md +0 -33
- package/dist/help/topics/file.rename.md +0 -33
- package/dist/help/topics/mutation.md +0 -58
- package/dist/help/topics/refactor.batch.md +0 -33
- package/dist/ide-launch/common.cjs +0 -162
- package/dist/managed-host/extension-vsix-resolver.js +0 -1
- package/dist/managed-host/manage-serve-web-host.cjs +0 -141
- package/dist/managed-host/serve-web-autostart.js +0 -1
- package/dist/managed-host/serve-web-host.cjs +0 -2115
- package/dist/runtime/managed-runtime-provisioning.js +0 -1
- package/dist/shared/diagnostic-catalog.js +0 -1
- package/dist/shared/diagnostics.js +0 -1
- package/dist/shared/operations.js +0 -1
- package/dist/shared/protocol.js +0 -1
- package/dist/shared/routes.js +0 -1
- package/extension/vscode-refactor-bridge-extension.vsix +0 -0
- package/runtimes/launcher/linux-x64/aib +0 -0
- package/runtimes/launcher/win-x64/aib.exe +0 -0
|
@@ -1,5 +1,1073 @@
|
|
|
1
|
-
"use strict";
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
1
|
+
"use strict";
|
|
2
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
3
|
+
if (k2 === undefined) k2 = k;
|
|
4
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
5
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
6
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
7
|
+
}
|
|
8
|
+
Object.defineProperty(o, k2, desc);
|
|
9
|
+
}) : (function(o, m, k, k2) {
|
|
10
|
+
if (k2 === undefined) k2 = k;
|
|
11
|
+
o[k2] = m[k];
|
|
12
|
+
}));
|
|
13
|
+
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
|
14
|
+
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
|
15
|
+
}) : function(o, v) {
|
|
16
|
+
o["default"] = v;
|
|
17
|
+
});
|
|
18
|
+
var __importStar = (this && this.__importStar) || (function () {
|
|
19
|
+
var ownKeys = function(o) {
|
|
20
|
+
ownKeys = Object.getOwnPropertyNames || function (o) {
|
|
21
|
+
var ar = [];
|
|
22
|
+
for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
|
|
23
|
+
return ar;
|
|
24
|
+
};
|
|
25
|
+
return ownKeys(o);
|
|
26
|
+
};
|
|
27
|
+
return function (mod) {
|
|
28
|
+
if (mod && mod.__esModule) return mod;
|
|
29
|
+
var result = {};
|
|
30
|
+
if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
|
|
31
|
+
__setModuleDefault(result, mod);
|
|
32
|
+
return result;
|
|
33
|
+
};
|
|
34
|
+
})();
|
|
35
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
36
|
+
exports.runFileMoveToDir = runFileMoveToDir;
|
|
37
|
+
exports.runFileMoveToDirExecutionWorker = runFileMoveToDirExecutionWorker;
|
|
38
|
+
exports.readCachedFileMoveToDirExecution = readCachedFileMoveToDirExecution;
|
|
39
|
+
const fs = __importStar(require("node:fs"));
|
|
40
|
+
const path = __importStar(require("node:path"));
|
|
41
|
+
const node_child_process_1 = require("node:child_process");
|
|
42
|
+
const zod_1 = require("zod");
|
|
43
|
+
const env_vars_1 = require("../config/env-vars");
|
|
44
|
+
const agent_text_1 = require("../shared/agent-text");
|
|
45
|
+
const errors_1 = require("../shared/errors");
|
|
46
|
+
const inspect_cycles_1 = require("./inspect-cycles");
|
|
47
|
+
const mutation_eta_1 = require("./mutation-eta");
|
|
48
|
+
const file_move_to_dir_preview_cache_1 = require("./file-move-to-dir-preview-cache");
|
|
49
|
+
const file_move_to_dir_execution_cache_1 = require("./file-move-to-dir-execution-cache");
|
|
50
|
+
const file_mutation_runtime_1 = require("./file-mutation-runtime");
|
|
51
|
+
const mutation_execution_cache_1 = require("./mutation-execution-cache");
|
|
52
|
+
const mutate_child_execution_1 = require("./mutate-child-execution");
|
|
53
|
+
const file_mutation_worker_apply_1 = require("./file-mutation-worker-apply");
|
|
54
|
+
const file_impact_scan_1 = require("../mutation/file-impact-scan");
|
|
55
|
+
const runtime_lifecycle_1 = require("../session/runtime-lifecycle");
|
|
56
|
+
const FileMoveToDirPayloadSchema = zod_1.z.object({
|
|
57
|
+
base: zod_1.z.string().min(1),
|
|
58
|
+
moves: zod_1.z.array(zod_1.z.object({
|
|
59
|
+
targetDir: zod_1.z.string().min(1),
|
|
60
|
+
files: zod_1.z.array(zod_1.z.string().min(1)).min(1)
|
|
61
|
+
})).min(1),
|
|
62
|
+
execute: zod_1.z.boolean().optional()
|
|
63
|
+
});
|
|
64
|
+
async function runFileMoveToDir(cwd, rawPayload, options = {}, restArgs = []) {
|
|
65
|
+
const runtimeOptions = readFileMoveToDirRuntimeOptions();
|
|
66
|
+
const action = restArgs[0] ?? "preview";
|
|
67
|
+
if (action === "help" || action === "--help") {
|
|
68
|
+
return fileMoveToDirHelp();
|
|
69
|
+
}
|
|
70
|
+
if (action === "apply") {
|
|
71
|
+
const previewId = restArgs[1];
|
|
72
|
+
if (!previewId || previewId.startsWith("--")) {
|
|
73
|
+
throw new errors_1.CliError("FILE_MOVE_PREVIEW_ID_REQUIRED", "file move toDir apply expects a preview id.", {
|
|
74
|
+
usage: "aib file move toDir apply <previewId>"
|
|
75
|
+
});
|
|
76
|
+
}
|
|
77
|
+
return applyFileMoveToDirPreview(cwd, previewId, options, runtimeOptions);
|
|
78
|
+
}
|
|
79
|
+
if (action !== "preview" && action !== "execute" && action !== "validate") {
|
|
80
|
+
throw new errors_1.CliError("UNKNOWN_FILE_MOVE_TO_DIR_COMMAND", `Unknown file move toDir command: ${action}`, {
|
|
81
|
+
availableCommands: ["preview", "apply", "execute", "validate", "help"]
|
|
82
|
+
});
|
|
83
|
+
}
|
|
84
|
+
const payload = FileMoveToDirPayloadSchema.parse(rawPayload);
|
|
85
|
+
if (action === "execute" && readFileMoveToDirSyncWaitMs() > 0) {
|
|
86
|
+
return runFileMoveToDirPayloadWithExecution(cwd, {
|
|
87
|
+
...payload,
|
|
88
|
+
execute: true
|
|
89
|
+
}, options, "execute", readFileMoveToDirSyncWaitMs(), runtimeOptions);
|
|
90
|
+
}
|
|
91
|
+
return runFileMoveToDirPayload(cwd, {
|
|
92
|
+
...payload,
|
|
93
|
+
execute: action === "execute"
|
|
94
|
+
}, options, action, runtimeOptions);
|
|
95
|
+
}
|
|
96
|
+
async function applyFileMoveToDirPreview(cwd, previewId, options, runtimeOptions) {
|
|
97
|
+
const record = (0, file_move_to_dir_preview_cache_1.readFileMoveToDirPreviewRecord)(cwd, previewId);
|
|
98
|
+
(0, file_move_to_dir_preview_cache_1.validateFileMoveStates)(record);
|
|
99
|
+
const payload = FileMoveToDirPayloadSchema.parse({
|
|
100
|
+
...record.normalizedPayload,
|
|
101
|
+
execute: true
|
|
102
|
+
});
|
|
103
|
+
const syncWaitMs = readFileMoveToDirSyncWaitMs();
|
|
104
|
+
if (syncWaitMs > 0) {
|
|
105
|
+
return runFileMoveToDirPayloadWithExecution(cwd, payload, options, "apply", syncWaitMs, runtimeOptions, previewId);
|
|
106
|
+
}
|
|
107
|
+
const result = await runFileMoveToDirPayload(cwd, payload, options, "apply", runtimeOptions, previewId);
|
|
108
|
+
return result.ok === false
|
|
109
|
+
? (0, agent_text_1.attachAgentText)({ ...result, next: "Fix the file move request and rerun preview." }, formatFileMoveToDirAgentText({ ...result, next: "Fix the file move request and rerun preview." }))
|
|
110
|
+
: result;
|
|
111
|
+
}
|
|
112
|
+
async function runFileMoveToDirPayloadWithExecution(cwd, payload, options, action, syncWaitMs, runtimeOptions, previewIdFromApply) {
|
|
113
|
+
const normalized = normalizePayload(cwd, payload, true);
|
|
114
|
+
const executionId = (0, file_move_to_dir_execution_cache_1.buildFileMoveToDirExecutionId)();
|
|
115
|
+
const operation = `move.toDir.${action}`;
|
|
116
|
+
const etaEstimate = (0, file_mutation_runtime_1.estimateFileMutationEta)(buildFileMutationEtaInput(cwd, normalized.operations));
|
|
117
|
+
const estimatedDurationMs = etaEstimate.selectedMs;
|
|
118
|
+
const status = (0, file_move_to_dir_execution_cache_1.createFileMoveToDirExecutionStatus)(cwd, executionId, operation, buildPlannedMoves(cwd, normalized.operations));
|
|
119
|
+
(0, file_move_to_dir_execution_cache_1.writeFileMoveToDirExecutionStatus)(cwd, status);
|
|
120
|
+
const startedAtMs = Date.now();
|
|
121
|
+
const backgroundEnv = captureFileMoveToDirBackgroundEnv();
|
|
122
|
+
const workerInputPath = writeFileMoveToDirWorkerInput(cwd, executionId, {
|
|
123
|
+
schemaVersion: 1,
|
|
124
|
+
cwd,
|
|
125
|
+
payload,
|
|
126
|
+
normalized,
|
|
127
|
+
options: serializeResolveTargetInstanceOptions(options),
|
|
128
|
+
action,
|
|
129
|
+
runtimeOptions,
|
|
130
|
+
executionId,
|
|
131
|
+
status,
|
|
132
|
+
previewIdFromApply: previewIdFromApply ?? null
|
|
133
|
+
});
|
|
134
|
+
const workerPid = startFileMoveToDirWorkerProcess(cwd, workerInputPath, backgroundEnv);
|
|
135
|
+
if (workerPid === null) {
|
|
136
|
+
return failFileMoveToDirWorkerStart(cwd, status, "FILE_MOVE_TO_DIR_WORKER_START_FAILED", "File move worker did not publish a process id.");
|
|
137
|
+
}
|
|
138
|
+
const publicationFailure = await (0, mutate_child_execution_1.awaitFileMutationWorkerPublication)({
|
|
139
|
+
cwd,
|
|
140
|
+
executionId,
|
|
141
|
+
kind: "move.toDir",
|
|
142
|
+
operation,
|
|
143
|
+
workerPid
|
|
144
|
+
});
|
|
145
|
+
if (publicationFailure) {
|
|
146
|
+
return publicationFailure;
|
|
147
|
+
}
|
|
148
|
+
const result = await waitForFileMoveToDirWorkerResult(cwd, executionId, syncWaitMs);
|
|
149
|
+
if (result) {
|
|
150
|
+
return result;
|
|
151
|
+
}
|
|
152
|
+
const finalStatus = (0, file_move_to_dir_execution_cache_1.tryReadFileMoveToDirExecutionStatus)(cwd, executionId);
|
|
153
|
+
if (finalStatus && finalStatus.status !== "running") {
|
|
154
|
+
return isObject(finalStatus.result)
|
|
155
|
+
? finalStatus.result
|
|
156
|
+
: readCachedFileMoveToDirExecution(cwd, executionId);
|
|
157
|
+
}
|
|
158
|
+
return buildFileMoveToDirStillRunningResponse(cwd, executionId, operation, workerPid, estimatedDurationMs, Date.now() - startedAtMs, etaEstimate);
|
|
159
|
+
}
|
|
160
|
+
async function runFileMoveToDirExecutionWorker(input) {
|
|
161
|
+
const status = input.status;
|
|
162
|
+
status.workerPid = process.pid;
|
|
163
|
+
(0, file_move_to_dir_execution_cache_1.writeFileMoveToDirExecutionStatus)(input.cwd, status);
|
|
164
|
+
try {
|
|
165
|
+
const result = await executeFileMoveToDirOperations(input.cwd, input.normalized, input.action, input.options, input.runtimeOptions, input.executionId, status, input.previewIdFromApply ?? undefined);
|
|
166
|
+
const rows = readFileMoveToDirRows(result);
|
|
167
|
+
status.status = result.ok === false ? "failed" : "completed";
|
|
168
|
+
status.phase = "completed";
|
|
169
|
+
status.completedRows = result.ok === false ? rows.filter((row) => row.ok !== false).length : status.rowCount;
|
|
170
|
+
status.failedRows = result.ok === false ? rows.filter((row) => row.ok === false).length : 0;
|
|
171
|
+
status.notRunRows = result.ok === false ? Math.max(0, status.rowCount - rows.length) : 0;
|
|
172
|
+
status.filesWritten = readStringArray(result.filesWritten);
|
|
173
|
+
status.touchedFiles = readStringArray(result.touchedFiles);
|
|
174
|
+
status.moves = Array.isArray(result.moves) ? result.moves.filter(isObject) : [];
|
|
175
|
+
status.rows = rows;
|
|
176
|
+
if (isObject(result.postMutation)) {
|
|
177
|
+
status.postMutation = result.postMutation;
|
|
178
|
+
}
|
|
179
|
+
status.result = result;
|
|
180
|
+
if (result.ok === false) {
|
|
181
|
+
status.error = readString(result.code) ?? readFirstFailedCode(rows) ?? "FILE_MOVE_TO_DIR_FAILED";
|
|
182
|
+
}
|
|
183
|
+
(0, file_move_to_dir_execution_cache_1.writeFileMoveToDirExecutionStatus)(input.cwd, status);
|
|
184
|
+
return result;
|
|
185
|
+
}
|
|
186
|
+
catch (error) {
|
|
187
|
+
status.status = "failed";
|
|
188
|
+
status.phase = "completed";
|
|
189
|
+
status.failedRows = Math.max(1, status.failedRows);
|
|
190
|
+
status.notRunRows = Math.max(0, status.rowCount - status.completedRows - status.failedRows);
|
|
191
|
+
status.error = error instanceof Error ? error.message : String(error);
|
|
192
|
+
(0, file_move_to_dir_execution_cache_1.writeFileMoveToDirExecutionStatus)(input.cwd, status);
|
|
193
|
+
throw error;
|
|
194
|
+
}
|
|
195
|
+
}
|
|
196
|
+
function writeFileMoveToDirWorkerInput(cwd, executionId, input) {
|
|
197
|
+
const filePath = path.join(fileMoveToDirWorkerDir(cwd, executionId), "worker-input.json");
|
|
198
|
+
fs.mkdirSync(path.dirname(filePath), { recursive: true });
|
|
199
|
+
const tmpPath = `${filePath}.${process.pid}.${Date.now()}.tmp`;
|
|
200
|
+
fs.writeFileSync(tmpPath, `${JSON.stringify(input, null, 2)}\n`);
|
|
201
|
+
fs.renameSync(tmpPath, filePath);
|
|
202
|
+
return filePath;
|
|
203
|
+
}
|
|
204
|
+
function fileMoveToDirWorkerDir(cwd, executionId) {
|
|
205
|
+
return path.join(cwd, ".tmp", "aib-file-move-to-dir-workers", executionId.replace(/[^a-z0-9_-]+/gi, "-"));
|
|
206
|
+
}
|
|
207
|
+
function startFileMoveToDirWorkerProcess(cwd, inputPath, envPatch) {
|
|
208
|
+
const env = { ...process.env };
|
|
209
|
+
for (const [key, value] of Object.entries(envPatch)) {
|
|
210
|
+
if (value === undefined) {
|
|
211
|
+
delete env[key];
|
|
212
|
+
}
|
|
213
|
+
else {
|
|
214
|
+
env[key] = value;
|
|
215
|
+
}
|
|
216
|
+
}
|
|
217
|
+
const child = (0, node_child_process_1.spawn)(process.execPath, [path.join(__dirname, "file-move-to-dir-worker.js"), inputPath], {
|
|
218
|
+
cwd,
|
|
219
|
+
env,
|
|
220
|
+
detached: true,
|
|
221
|
+
stdio: "ignore",
|
|
222
|
+
windowsHide: true
|
|
223
|
+
});
|
|
224
|
+
child.on("error", () => undefined);
|
|
225
|
+
(0, runtime_lifecycle_1.trackSessionOwnedProcess)(child, "file-move-worker");
|
|
226
|
+
child.unref();
|
|
227
|
+
return child.pid ?? null;
|
|
228
|
+
}
|
|
229
|
+
async function waitForFileMoveToDirWorkerResult(cwd, executionId, syncWaitMs) {
|
|
230
|
+
if (syncWaitMs <= 0) {
|
|
231
|
+
return null;
|
|
232
|
+
}
|
|
233
|
+
const deadline = Date.now() + syncWaitMs;
|
|
234
|
+
while (Date.now() < deadline) {
|
|
235
|
+
const status = (0, file_move_to_dir_execution_cache_1.tryReadFileMoveToDirExecutionStatus)(cwd, executionId);
|
|
236
|
+
if (status && isFinalFileMoveToDirWorkerStatus(status)) {
|
|
237
|
+
return isObject(status.result)
|
|
238
|
+
? status.result
|
|
239
|
+
: readCachedFileMoveToDirExecution(cwd, executionId);
|
|
240
|
+
}
|
|
241
|
+
await new Promise((resolve) => setTimeout(resolve, 100));
|
|
242
|
+
}
|
|
243
|
+
const finalStatus = (0, file_move_to_dir_execution_cache_1.tryReadFileMoveToDirExecutionStatus)(cwd, executionId);
|
|
244
|
+
if (finalStatus && isFinalFileMoveToDirWorkerStatus(finalStatus)) {
|
|
245
|
+
return isObject(finalStatus.result)
|
|
246
|
+
? finalStatus.result
|
|
247
|
+
: readCachedFileMoveToDirExecution(cwd, executionId);
|
|
248
|
+
}
|
|
249
|
+
return null;
|
|
250
|
+
}
|
|
251
|
+
function isFinalFileMoveToDirWorkerStatus(status) {
|
|
252
|
+
return isObject(status.result) || status.phase === "completed";
|
|
253
|
+
}
|
|
254
|
+
function serializeResolveTargetInstanceOptions(options) {
|
|
255
|
+
return {
|
|
256
|
+
...(options.metricsEnabled !== undefined ? { metricsEnabled: options.metricsEnabled } : {}),
|
|
257
|
+
...(options.importRules ? { importRules: options.importRules } : {}),
|
|
258
|
+
...(options.mutationComments ? { mutationComments: options.mutationComments } : {})
|
|
259
|
+
};
|
|
260
|
+
}
|
|
261
|
+
async function runFileMoveToDirPayload(cwd, payload, options, action, runtimeOptions, previewIdFromApply, executionId, normalizedFromExecution) {
|
|
262
|
+
await (0, file_mutation_runtime_1.maybeDelayFileMutationForTest)(process.env[env_vars_1.CLI_ENV.testFileMoveToDirDelayMs]);
|
|
263
|
+
const normalized = normalizedFromExecution ?? normalizePayload(cwd, payload, action === "execute" || action === "apply");
|
|
264
|
+
const result = normalized.execute
|
|
265
|
+
? await executeFileMoveToDirOperations(cwd, normalized, action === "apply" ? "apply" : "execute", options, runtimeOptions, executionId, undefined, previewIdFromApply)
|
|
266
|
+
: buildLocalFileMoveToDirPreviewResult(normalized.operations);
|
|
267
|
+
const response = compactFileMoveToDirResponse(cwd, result, normalized, action, previewIdFromApply, executionId);
|
|
268
|
+
if ((action === "preview" || action === "validate") && response.ok !== false) {
|
|
269
|
+
const previewId = (0, file_move_to_dir_preview_cache_1.buildFileMoveToDirPreviewId)(normalized.normalizedPayload);
|
|
270
|
+
const states = (0, file_move_to_dir_preview_cache_1.readFileMoveStates)(normalized.operations);
|
|
271
|
+
const previewHash = (0, file_move_to_dir_preview_cache_1.buildFileMoveToDirPreviewHash)(normalized.normalizedPayload, states, response);
|
|
272
|
+
(0, file_move_to_dir_preview_cache_1.writeFileMoveToDirPreviewRecord)(cwd, {
|
|
273
|
+
previewId,
|
|
274
|
+
previewHash,
|
|
275
|
+
createdAt: new Date().toISOString(),
|
|
276
|
+
cwd: path.resolve(cwd),
|
|
277
|
+
normalizedPayload: normalized.normalizedPayload,
|
|
278
|
+
states,
|
|
279
|
+
previewResult: response
|
|
280
|
+
});
|
|
281
|
+
response.previewId = previewId;
|
|
282
|
+
response.next = `aib file move toDir apply ${previewId}`;
|
|
283
|
+
}
|
|
284
|
+
return (0, agent_text_1.attachAgentText)(response, formatFileMoveToDirAgentText(response));
|
|
285
|
+
}
|
|
286
|
+
async function executeFileMoveToDirOperations(cwd, normalized, action, options, runtimeOptions, executionId, status, previewIdFromApply) {
|
|
287
|
+
const rawRows = [];
|
|
288
|
+
const filesWritten = new Set();
|
|
289
|
+
const touchedFiles = new Set();
|
|
290
|
+
const importSnapshotBefore = [];
|
|
291
|
+
const preMutationCycles = runPostMutationCyclesSnapshot(cwd, normalized.operations.map((operation) => operation.sourceFile));
|
|
292
|
+
let cleanup = [];
|
|
293
|
+
let postMutation = null;
|
|
294
|
+
for (const operation of normalized.operations) {
|
|
295
|
+
if (status) {
|
|
296
|
+
status.phase = "movingFile";
|
|
297
|
+
status.status = "running";
|
|
298
|
+
persistFileMoveToDirExecutionProgress(cwd, status, rawRows, filesWritten, touchedFiles);
|
|
299
|
+
await yieldToEventLoop();
|
|
300
|
+
}
|
|
301
|
+
const rowResult = await (0, file_mutation_worker_apply_1.executeWorkerOwnedFileMutationRow)(cwd, operation, options, runtimeOptions);
|
|
302
|
+
const row = Array.isArray(rowResult.rows) && isObject(rowResult.rows[0])
|
|
303
|
+
? rowResult.rows[0]
|
|
304
|
+
: localFailureRow(operation, "FILE_MOVE_TO_DIR_FAILED", "Extension did not return a file move row.");
|
|
305
|
+
rawRows.push(row);
|
|
306
|
+
for (const savedFile of collectStringArray(row.savedFiles)) {
|
|
307
|
+
filesWritten.add(path.normalize(savedFile));
|
|
308
|
+
}
|
|
309
|
+
for (const touchedFile of collectStringArray(row.touchedFiles)) {
|
|
310
|
+
touchedFiles.add(path.normalize(touchedFile));
|
|
311
|
+
}
|
|
312
|
+
for (const snapshot of collectImportSnapshots(row.importSnapshotBefore)) {
|
|
313
|
+
importSnapshotBefore.push(snapshot);
|
|
314
|
+
}
|
|
315
|
+
for (const cleanupRow of collectImportSnapshots(row.cleanup)) {
|
|
316
|
+
cleanup.push(cleanupRow);
|
|
317
|
+
}
|
|
318
|
+
if (status) {
|
|
319
|
+
persistFileMoveToDirExecutionProgress(cwd, status, rawRows, filesWritten, touchedFiles);
|
|
320
|
+
await yieldToEventLoop();
|
|
321
|
+
}
|
|
322
|
+
if (row.ok === false) {
|
|
323
|
+
break;
|
|
324
|
+
}
|
|
325
|
+
await (0, file_mutation_runtime_1.delayFileMutationForTest)(runtimeOptions.testRowDelayMs);
|
|
326
|
+
}
|
|
327
|
+
const rowsOk = rawRows.every((row) => row.ok !== false) && rawRows.length === normalized.operations.length;
|
|
328
|
+
const cleanupOk = cleanup.every((row) => row.ok !== false);
|
|
329
|
+
if (rowsOk && cleanupOk) {
|
|
330
|
+
if (status) {
|
|
331
|
+
status.phase = "postMutation.cycles";
|
|
332
|
+
persistFileMoveToDirExecutionProgress(cwd, status, rawRows, filesWritten, touchedFiles);
|
|
333
|
+
await yieldToEventLoop();
|
|
334
|
+
}
|
|
335
|
+
await maybeDelayPostMutationCycles(runtimeOptions.testPostMutationCyclesDelayMs);
|
|
336
|
+
const postMutationFocusFiles = uniqueStrings([...Array.from(touchedFiles), ...Array.from(filesWritten)]);
|
|
337
|
+
const postMutationCycles = runPostMutationCyclesSnapshot(cwd, postMutationFocusFiles);
|
|
338
|
+
postMutation = {
|
|
339
|
+
cycles: diffPostMutationCycles(preMutationCycles, postMutationCycles, new Set(formatCycleFocusFiles(cwd, postMutationFocusFiles)))
|
|
340
|
+
};
|
|
341
|
+
}
|
|
342
|
+
const rawResult = compactObject({
|
|
343
|
+
...(!rowsOk || !cleanupOk ? { ok: false } : {}),
|
|
344
|
+
operation: "fileMutation",
|
|
345
|
+
execute: true,
|
|
346
|
+
rowCount: normalized.operations.length,
|
|
347
|
+
appliedCount: rawRows.filter((row) => row.applied === true).length,
|
|
348
|
+
savedFiles: Array.from(filesWritten),
|
|
349
|
+
touchedFiles: Array.from(touchedFiles),
|
|
350
|
+
cleanup,
|
|
351
|
+
rows: rawRows,
|
|
352
|
+
postMutation
|
|
353
|
+
});
|
|
354
|
+
const response = compactFileMoveToDirResponse(cwd, rawResult, normalized, action, previewIdFromApply, executionId);
|
|
355
|
+
return (0, agent_text_1.attachAgentText)(response, formatFileMoveToDirAgentText(response));
|
|
356
|
+
}
|
|
357
|
+
function persistFileMoveToDirExecutionProgress(cwd, status, rawRows, filesWritten, touchedFiles) {
|
|
358
|
+
const compactRows = rawRows.map((row) => compactRow(cwd, row));
|
|
359
|
+
status.rows = compactRows;
|
|
360
|
+
status.completedRows = compactRows.filter((row) => row.ok !== false).length;
|
|
361
|
+
status.failedRows = compactRows.filter((row) => row.ok === false).length;
|
|
362
|
+
status.notRunRows = status.failedRows > 0 ? Math.max(0, status.rowCount - compactRows.length) : 0;
|
|
363
|
+
status.filesWritten = Array.from(filesWritten).sort((left, right) => left.localeCompare(right)).map((file) => formatRelativePath(cwd, file));
|
|
364
|
+
status.touchedFiles = Array.from(touchedFiles).sort((left, right) => left.localeCompare(right)).map((file) => formatRelativePath(cwd, file));
|
|
365
|
+
if (status.failedRows > 0) {
|
|
366
|
+
status.status = "failed";
|
|
367
|
+
status.error = readFirstFailedCode(compactRows) ?? "FILE_MOVE_TO_DIR_FAILED";
|
|
368
|
+
}
|
|
369
|
+
(0, file_move_to_dir_execution_cache_1.writeFileMoveToDirExecutionStatus)(cwd, status);
|
|
370
|
+
}
|
|
371
|
+
function readCachedFileMoveToDirExecution(cwd, executionId) {
|
|
372
|
+
const status = (0, file_move_to_dir_execution_cache_1.readFileMoveToDirExecutionStatus)(cwd, executionId);
|
|
373
|
+
const response = {
|
|
374
|
+
operation: "execution.status",
|
|
375
|
+
executionId: status.executionId,
|
|
376
|
+
status: status.status,
|
|
377
|
+
phase: status.phase,
|
|
378
|
+
summary: buildFileMoveToDirExecutionSummary(status),
|
|
379
|
+
progress: `${status.completedRows}/${status.rowCount}`,
|
|
380
|
+
filesWritten: status.filesWritten,
|
|
381
|
+
touchedFiles: status.touchedFiles,
|
|
382
|
+
...(status.postMutation ? { postMutation: status.postMutation } : {}),
|
|
383
|
+
updatedAt: status.updatedAt,
|
|
384
|
+
...(status.error ? { error: status.error } : {})
|
|
385
|
+
};
|
|
386
|
+
return (0, agent_text_1.attachAgentText)(response, formatFileMoveToDirExecutionStatusText(status));
|
|
387
|
+
}
|
|
388
|
+
function buildFileMoveToDirStillRunningResponse(cwd, executionId, operation, workerPid, estimatedDurationMs, elapsedMs, estimate = null) {
|
|
389
|
+
const status = (0, file_move_to_dir_execution_cache_1.readFileMoveToDirExecutionStatus)(cwd, executionId);
|
|
390
|
+
const estimatedRemainingMs = Math.max(0, estimatedDurationMs - elapsedMs);
|
|
391
|
+
const eta = (0, mutation_eta_1.buildMutationEtaHint)(status.executionId, estimatedRemainingMs);
|
|
392
|
+
const response = {
|
|
393
|
+
operation: "execution.status",
|
|
394
|
+
executionId: status.executionId,
|
|
395
|
+
childExecutionKind: "move.toDir",
|
|
396
|
+
childOperation: operation,
|
|
397
|
+
childCacheNamespace: file_move_to_dir_execution_cache_1.FILE_MOVE_TO_DIR_EXECUTION_NAMESPACE,
|
|
398
|
+
childWorkerPid: workerPid,
|
|
399
|
+
status: status.status,
|
|
400
|
+
phase: status.phase,
|
|
401
|
+
summary: buildFileMoveToDirExecutionSummary(status),
|
|
402
|
+
progress: `${status.completedRows}/${status.rowCount}`,
|
|
403
|
+
filesWritten: status.filesWritten,
|
|
404
|
+
touchedFiles: status.touchedFiles,
|
|
405
|
+
...(status.postMutation ? { postMutation: status.postMutation } : {}),
|
|
406
|
+
updatedAt: status.updatedAt,
|
|
407
|
+
...(estimate ? { eta: estimate } : {}),
|
|
408
|
+
estimatedRemainingMs: eta.estimatedRemainingMs,
|
|
409
|
+
suggestedFirstCheckMs: eta.suggestedFirstCheckMs,
|
|
410
|
+
next: eta.next
|
|
411
|
+
};
|
|
412
|
+
return (0, agent_text_1.attachAgentText)(response, formatFileMoveToDirStillRunningText(operation, status, eta));
|
|
413
|
+
}
|
|
414
|
+
function failFileMoveToDirWorkerStart(cwd, status, code, error) {
|
|
415
|
+
const result = {
|
|
416
|
+
ok: false,
|
|
417
|
+
operation: status.operation,
|
|
418
|
+
executionId: status.executionId,
|
|
419
|
+
code,
|
|
420
|
+
error,
|
|
421
|
+
filesWritten: [],
|
|
422
|
+
filesTouched: []
|
|
423
|
+
};
|
|
424
|
+
status.status = "failed";
|
|
425
|
+
status.phase = "completed";
|
|
426
|
+
status.failedRows = Math.max(1, status.failedRows);
|
|
427
|
+
status.notRunRows = Math.max(0, status.rowCount - status.completedRows - status.failedRows);
|
|
428
|
+
status.error = code;
|
|
429
|
+
status.result = result;
|
|
430
|
+
(0, file_move_to_dir_execution_cache_1.writeFileMoveToDirExecutionStatus)(cwd, status);
|
|
431
|
+
return result;
|
|
432
|
+
}
|
|
433
|
+
function formatFileMoveToDirStillRunningText(operation, status, eta) {
|
|
434
|
+
return [
|
|
435
|
+
`${operation} ${status.executionId}`,
|
|
436
|
+
buildFileMoveToDirExecutionSummary(status),
|
|
437
|
+
formatFileMoveToDirPhaseLine(status),
|
|
438
|
+
...(0, mutation_eta_1.formatMutationEtaLines)(eta)
|
|
439
|
+
].join("\n");
|
|
440
|
+
}
|
|
441
|
+
function formatFileMoveToDirExecutionStatusText(status) {
|
|
442
|
+
const lines = [
|
|
443
|
+
buildFileMoveToDirExecutionSummary(status)
|
|
444
|
+
];
|
|
445
|
+
if (status.status === "running") {
|
|
446
|
+
lines.push(formatFileMoveToDirPhaseLine(status));
|
|
447
|
+
return lines.join("\n");
|
|
448
|
+
}
|
|
449
|
+
appendExecutionMoveLines(lines, status);
|
|
450
|
+
const failedRows = status.rows.filter((row) => row.ok === false);
|
|
451
|
+
const firstFailed = failedRows[0];
|
|
452
|
+
if (firstFailed) {
|
|
453
|
+
const code = readString(firstFailed.code) ?? status.error ?? "FILE_MOVE_TO_DIR_FAILED";
|
|
454
|
+
lines.push(`code: ${code}`);
|
|
455
|
+
if (typeof firstFailed.error === "string") {
|
|
456
|
+
lines.push(firstFailed.error);
|
|
457
|
+
}
|
|
458
|
+
if (typeof firstFailed.rollback === "string") {
|
|
459
|
+
lines.push(`rollback: ${firstFailed.rollback}`);
|
|
460
|
+
}
|
|
461
|
+
if (typeof firstFailed.hint === "string") {
|
|
462
|
+
lines.push(`hint: ${firstFailed.hint}`);
|
|
463
|
+
}
|
|
464
|
+
lines.push("failed:");
|
|
465
|
+
for (const row of failedRows) {
|
|
466
|
+
lines.push(`${readString(row.source) ?? "source"} -> ${readString(row.target) ?? "target"}`);
|
|
467
|
+
}
|
|
468
|
+
}
|
|
469
|
+
else if (status.error) {
|
|
470
|
+
lines.push(status.error);
|
|
471
|
+
}
|
|
472
|
+
appendExecutionNotRunLines(lines, status);
|
|
473
|
+
if (status.filesWritten.length > 0) {
|
|
474
|
+
appendFilesWrittenLines(lines, status.filesWritten, status.plannedMoves.map((move) => move.target));
|
|
475
|
+
}
|
|
476
|
+
if (isObject(status.postMutation) && isObject(status.postMutation.cycles)) {
|
|
477
|
+
appendPostMutationCyclesText(lines, status.postMutation.cycles);
|
|
478
|
+
}
|
|
479
|
+
if (status.status === "failed") {
|
|
480
|
+
lines.push("next: Fix failed move row and rerun move.toDir preview.");
|
|
481
|
+
}
|
|
482
|
+
return lines.join("\n");
|
|
483
|
+
}
|
|
484
|
+
function formatFileMoveToDirPhaseLine(status) {
|
|
485
|
+
if (status.phase === "postProcessImports") {
|
|
486
|
+
return "updating imports";
|
|
487
|
+
}
|
|
488
|
+
if (status.phase === "postMutation.cycles") {
|
|
489
|
+
return "checking cycles";
|
|
490
|
+
}
|
|
491
|
+
return "moving files";
|
|
492
|
+
}
|
|
493
|
+
function buildFileMoveToDirExecutionSummary(status) {
|
|
494
|
+
const percent = Math.floor((Math.max(0, status.completedRows) / Math.max(1, status.rowCount)) * 100);
|
|
495
|
+
if (status.status === "completed") {
|
|
496
|
+
return `completed, ${status.completedRows}/${status.rowCount} rows, ${percent}% files, ${status.filesWritten.length} files written`;
|
|
497
|
+
}
|
|
498
|
+
if (status.status === "failed") {
|
|
499
|
+
const parts = [
|
|
500
|
+
`failed, ${status.completedRows}/${status.rowCount} rows, ${percent}% files`,
|
|
501
|
+
`${status.failedRows} failed`
|
|
502
|
+
];
|
|
503
|
+
if (status.notRunRows > 0) {
|
|
504
|
+
parts.push(`${status.notRunRows} not run`);
|
|
505
|
+
}
|
|
506
|
+
parts.push(`${status.filesWritten.length} files written`);
|
|
507
|
+
return parts.join(", ");
|
|
508
|
+
}
|
|
509
|
+
return `in progress, ${status.completedRows}/${status.rowCount} rows, ${percent}% files`;
|
|
510
|
+
}
|
|
511
|
+
function normalizePayload(cwd, payload, execute) {
|
|
512
|
+
const baseDir = resolveInsideCwd(cwd, payload.base);
|
|
513
|
+
const operations = [];
|
|
514
|
+
const seenTargets = new Set();
|
|
515
|
+
for (const move of payload.moves) {
|
|
516
|
+
const targetDir = resolveTargetDir(baseDir, move.targetDir);
|
|
517
|
+
assertInsideCwd(cwd, targetDir, "FILE_MOVE_TARGET_OUTSIDE_CWD");
|
|
518
|
+
for (const source of move.files) {
|
|
519
|
+
const sourceFile = resolveSourceFile(cwd, baseDir, source);
|
|
520
|
+
assertInsideCwd(cwd, sourceFile, "FILE_MOVE_SOURCE_OUTSIDE_CWD");
|
|
521
|
+
const targetFile = path.normalize(path.resolve(targetDir, path.basename(sourceFile)));
|
|
522
|
+
assertInsideCwd(cwd, targetFile, "FILE_MOVE_TARGET_OUTSIDE_CWD");
|
|
523
|
+
const targetKey = normalizeKey(targetFile);
|
|
524
|
+
if (seenTargets.has(targetKey)) {
|
|
525
|
+
throw new errors_1.CliError("FILE_MOVE_DUPLICATE_TARGET", "Several file moves resolve to the same target.", {
|
|
526
|
+
targetFile: formatRelativePath(cwd, targetFile)
|
|
527
|
+
});
|
|
528
|
+
}
|
|
529
|
+
seenTargets.add(targetKey);
|
|
530
|
+
operations.push({
|
|
531
|
+
id: `move-${operations.length + 1}`,
|
|
532
|
+
kind: "fileMoveToDir",
|
|
533
|
+
sourceFile,
|
|
534
|
+
targetDir,
|
|
535
|
+
targetFile,
|
|
536
|
+
execute
|
|
537
|
+
});
|
|
538
|
+
}
|
|
539
|
+
}
|
|
540
|
+
if (operations.length === 0) {
|
|
541
|
+
throw new errors_1.CliError("FILE_MOVE_ROWS_REQUIRED", "file move toDir expects at least one file.");
|
|
542
|
+
}
|
|
543
|
+
return {
|
|
544
|
+
execute,
|
|
545
|
+
baseDir,
|
|
546
|
+
operations,
|
|
547
|
+
normalizedPayload: {
|
|
548
|
+
base: baseDir,
|
|
549
|
+
moves: normalizedPayloadGroups(operations),
|
|
550
|
+
execute
|
|
551
|
+
}
|
|
552
|
+
};
|
|
553
|
+
}
|
|
554
|
+
function buildLocalFileMoveToDirPreviewResult(operations) {
|
|
555
|
+
const rows = [];
|
|
556
|
+
for (const operation of operations) {
|
|
557
|
+
if (rows.some((row) => row.ok === false)) {
|
|
558
|
+
break;
|
|
559
|
+
}
|
|
560
|
+
rows.push(validateLocalMoveOperation(operation));
|
|
561
|
+
}
|
|
562
|
+
const ok = rows.every((row) => row.ok !== false) && rows.length === operations.length;
|
|
563
|
+
return {
|
|
564
|
+
...(ok ? {} : { ok: false }),
|
|
565
|
+
operation: "fileMutation",
|
|
566
|
+
execute: false,
|
|
567
|
+
rowCount: operations.length,
|
|
568
|
+
appliedCount: 0,
|
|
569
|
+
savedFiles: [],
|
|
570
|
+
rows
|
|
571
|
+
};
|
|
572
|
+
}
|
|
573
|
+
function validateLocalMoveOperation(operation) {
|
|
574
|
+
if (operation.kind !== "fileMoveToDir") {
|
|
575
|
+
return localFailureRow(operation, "FILE_MUTATION_KIND_UNSUPPORTED", `Unsupported file mutation kind: ${operation.kind}`);
|
|
576
|
+
}
|
|
577
|
+
if (!fs.existsSync(operation.sourceFile)) {
|
|
578
|
+
return localFailureRow(operation, "FILE_MOVE_SOURCE_NOT_FOUND", "Source file does not exist.");
|
|
579
|
+
}
|
|
580
|
+
try {
|
|
581
|
+
const stat = fs.statSync(operation.sourceFile);
|
|
582
|
+
if (!stat.isFile()) {
|
|
583
|
+
return localFailureRow(operation, "FILE_MOVE_SOURCE_DIRECTORY_UNSUPPORTED", "file move toDir v1 supports files only, not directories.");
|
|
584
|
+
}
|
|
585
|
+
}
|
|
586
|
+
catch (error) {
|
|
587
|
+
return localFailureRow(operation, "FILE_MOVE_SOURCE_STAT_FAILED", error instanceof Error ? error.message : String(error));
|
|
588
|
+
}
|
|
589
|
+
if (fs.existsSync(operation.targetFile)) {
|
|
590
|
+
return localFailureRow(operation, "FILE_MOVE_TARGET_EXISTS", "Target file already exists.", "Pick another target directory/name or remove the target collision.");
|
|
591
|
+
}
|
|
592
|
+
if (isCssLikeAsset(operation.sourceFile)) {
|
|
593
|
+
return localFailureRow(operation, "FILE_MOVE_SOURCE_ASSET_UNSUPPORTED", "CSS/SCSS files cannot be moved with file move toDir v1.");
|
|
594
|
+
}
|
|
595
|
+
return {
|
|
596
|
+
id: operation.id,
|
|
597
|
+
ok: true,
|
|
598
|
+
sourceFile: operation.sourceFile,
|
|
599
|
+
targetFile: operation.targetFile,
|
|
600
|
+
applied: false
|
|
601
|
+
};
|
|
602
|
+
}
|
|
603
|
+
function localFailureRow(operation, code, error, hint) {
|
|
604
|
+
return {
|
|
605
|
+
id: operation.id,
|
|
606
|
+
ok: false,
|
|
607
|
+
sourceFile: operation.sourceFile,
|
|
608
|
+
targetFile: operation.targetFile,
|
|
609
|
+
applied: false,
|
|
610
|
+
code,
|
|
611
|
+
error,
|
|
612
|
+
...(hint ? { hint } : {})
|
|
613
|
+
};
|
|
614
|
+
}
|
|
615
|
+
function isCssLikeAsset(filePath) {
|
|
616
|
+
return [".css", ".scss"].includes(path.extname(filePath).toLowerCase());
|
|
617
|
+
}
|
|
618
|
+
function normalizedPayloadGroups(operations) {
|
|
619
|
+
const groups = new Map();
|
|
620
|
+
for (const operation of operations) {
|
|
621
|
+
const current = groups.get(operation.targetDir) ?? { targetDir: operation.targetDir, files: [] };
|
|
622
|
+
current.files.push(operation.sourceFile);
|
|
623
|
+
groups.set(operation.targetDir, current);
|
|
624
|
+
}
|
|
625
|
+
return Array.from(groups.values());
|
|
626
|
+
}
|
|
627
|
+
function resolveSourceFile(cwd, baseDir, rawPath) {
|
|
628
|
+
const trimmed = rawPath.trim();
|
|
629
|
+
if (path.isAbsolute(trimmed)) {
|
|
630
|
+
return path.normalize(trimmed);
|
|
631
|
+
}
|
|
632
|
+
const baseRelative = path.normalize(path.resolve(baseDir, trimmed));
|
|
633
|
+
if (fs.existsSync(baseRelative)) {
|
|
634
|
+
return baseRelative;
|
|
635
|
+
}
|
|
636
|
+
const cwdRelative = path.normalize(path.resolve(cwd, trimmed));
|
|
637
|
+
if (fs.existsSync(cwdRelative)) {
|
|
638
|
+
return cwdRelative;
|
|
639
|
+
}
|
|
640
|
+
return baseRelative;
|
|
641
|
+
}
|
|
642
|
+
function resolveTargetDir(baseDir, rawPath) {
|
|
643
|
+
const trimmed = rawPath.trim();
|
|
644
|
+
return path.normalize(path.isAbsolute(trimmed) ? trimmed : path.resolve(baseDir, trimmed));
|
|
645
|
+
}
|
|
646
|
+
function resolveInsideCwd(cwd, rawPath) {
|
|
647
|
+
const resolved = path.normalize(path.isAbsolute(rawPath) ? rawPath : path.resolve(cwd, rawPath));
|
|
648
|
+
assertInsideCwd(cwd, resolved, "FILE_MOVE_PATH_OUTSIDE_CWD");
|
|
649
|
+
return resolved;
|
|
650
|
+
}
|
|
651
|
+
function assertInsideCwd(cwd, filePath, code) {
|
|
652
|
+
const root = path.resolve(cwd);
|
|
653
|
+
const relative = path.relative(root, filePath);
|
|
654
|
+
if (relative === "" || (!relative.startsWith("..") && !path.isAbsolute(relative))) {
|
|
655
|
+
return;
|
|
656
|
+
}
|
|
657
|
+
throw new errors_1.CliError(code, "File move paths must stay inside the current workspace.", {
|
|
658
|
+
cwd: root,
|
|
659
|
+
filePath
|
|
660
|
+
});
|
|
661
|
+
}
|
|
662
|
+
function compactFileMoveToDirResponse(cwd, raw, normalized, action, previewIdFromApply, executionId) {
|
|
663
|
+
const rows = Array.isArray(raw.rows)
|
|
664
|
+
? raw.rows.filter(isObject).map((row) => compactRow(cwd, row))
|
|
665
|
+
: [];
|
|
666
|
+
const ok = raw.ok !== false && rows.every((row) => row.ok !== false);
|
|
667
|
+
const movedFiles = collectRows(rows, "target");
|
|
668
|
+
const filesWritten = collectExistingFiles(cwd, collectStringArray(raw.savedFiles)).map((file) => formatRelativePath(cwd, file));
|
|
669
|
+
const dirsToCreate = countDirsToCreate(normalized.operations);
|
|
670
|
+
const operation = action === "apply"
|
|
671
|
+
? "move.toDir.apply"
|
|
672
|
+
: normalized.execute
|
|
673
|
+
? "move.toDir.execute"
|
|
674
|
+
: "move.toDir.preview";
|
|
675
|
+
const response = compactObject({
|
|
676
|
+
...(ok ? {} : { ok: false }),
|
|
677
|
+
operation,
|
|
678
|
+
executionId: executionId ?? null,
|
|
679
|
+
base: formatRelativePath(cwd, normalized.baseDir),
|
|
680
|
+
operationCount: normalized.operations.length,
|
|
681
|
+
summary: ok
|
|
682
|
+
? normalized.execute
|
|
683
|
+
? `${normalized.operations.length} ${plural(normalized.operations.length, "file", "files")} moved, ${filesWritten.length} ${plural(filesWritten.length, "file", "files")} written`
|
|
684
|
+
: `${normalized.operations.length} ${plural(normalized.operations.length, "file", "files")}, ${countTargetDirs(normalized.operations)} target ${plural(countTargetDirs(normalized.operations), "dir", "dirs")} ready`
|
|
685
|
+
: buildFailureSummary(rows, normalized.operations.length, normalized.execute || action === "apply"),
|
|
686
|
+
dirsToCreate,
|
|
687
|
+
moves: groupMoves(cwd, normalized.operations),
|
|
688
|
+
...(normalized.execute || action === "apply" ? { filesWritten, filesMoved: movedFiles } : {}),
|
|
689
|
+
...(isObject(raw.postMutation) ? { postMutation: raw.postMutation } : {}),
|
|
690
|
+
rows: ok ? null : rows,
|
|
691
|
+
previewId: previewIdFromApply ?? null
|
|
692
|
+
});
|
|
693
|
+
return response;
|
|
694
|
+
}
|
|
695
|
+
function compactRow(cwd, row) {
|
|
696
|
+
return compactObject({
|
|
697
|
+
id: readString(row.id),
|
|
698
|
+
ok: row.ok !== false,
|
|
699
|
+
source: formatRelativePath(cwd, readString(row.sourceFile) ?? ""),
|
|
700
|
+
target: formatRelativePath(cwd, readString(row.targetFile) ?? ""),
|
|
701
|
+
applied: typeof row.applied === "boolean" ? row.applied : null,
|
|
702
|
+
rollback: readString(row.rollback),
|
|
703
|
+
savedFiles: compactList(collectStringArray(row.savedFiles).map((file) => formatRelativePath(cwd, file)), 5),
|
|
704
|
+
code: readString(row.code),
|
|
705
|
+
error: readString(row.error),
|
|
706
|
+
hint: readString(row.hint)
|
|
707
|
+
});
|
|
708
|
+
}
|
|
709
|
+
function groupMoves(cwd, operations) {
|
|
710
|
+
const groups = new Map();
|
|
711
|
+
for (const operation of operations) {
|
|
712
|
+
const targetDir = formatRelativePath(cwd, operation.targetDir);
|
|
713
|
+
groups.set(targetDir, [...(groups.get(targetDir) ?? []), formatRelativePath(cwd, operation.sourceFile)]);
|
|
714
|
+
}
|
|
715
|
+
return Array.from(groups.entries()).map(([targetDir, files]) => ({
|
|
716
|
+
targetDir,
|
|
717
|
+
files
|
|
718
|
+
}));
|
|
719
|
+
}
|
|
720
|
+
function buildFailureSummary(rows, total, executed) {
|
|
721
|
+
const failed = rows.filter((row) => row.ok === false).length;
|
|
722
|
+
const notRun = Math.max(0, total - rows.length);
|
|
723
|
+
if (!executed) {
|
|
724
|
+
const checked = Math.min(total, rows.length);
|
|
725
|
+
return `${total} ${plural(total, "file", "files")}, validation blocked at row ${checked}`;
|
|
726
|
+
}
|
|
727
|
+
return `${total} ${plural(total, "file", "files")}, ${failed} failed${notRun > 0 ? `, ${notRun} not run` : ""}`;
|
|
728
|
+
}
|
|
729
|
+
function buildPlannedMoves(cwd, operations) {
|
|
730
|
+
return operations.map((operation) => ({
|
|
731
|
+
source: formatRelativePath(cwd, operation.sourceFile),
|
|
732
|
+
target: formatRelativePath(cwd, operation.targetFile),
|
|
733
|
+
targetDir: formatRelativePath(cwd, operation.targetDir)
|
|
734
|
+
}));
|
|
735
|
+
}
|
|
736
|
+
function readFileMoveToDirRows(result) {
|
|
737
|
+
return Array.isArray(result.rows) ? result.rows.filter(isObject) : [];
|
|
738
|
+
}
|
|
739
|
+
function buildFileMutationEtaInput(cwd, operations) {
|
|
740
|
+
const targetDirs = new Set(operations.map((operation) => operation.targetDir));
|
|
741
|
+
let dirsToCreate = 0;
|
|
742
|
+
for (const targetDir of targetDirs) {
|
|
743
|
+
if (!fs.existsSync(targetDir)) {
|
|
744
|
+
dirsToCreate += 1;
|
|
745
|
+
}
|
|
746
|
+
}
|
|
747
|
+
const impact = (0, file_impact_scan_1.estimateFileMutationImpact)(cwd, operations.map((operation) => operation.sourceFile));
|
|
748
|
+
return {
|
|
749
|
+
rowCount: operations.length,
|
|
750
|
+
targetDirCount: targetDirs.size,
|
|
751
|
+
dirsToCreate,
|
|
752
|
+
importingFileCount: impact.importingFileCount,
|
|
753
|
+
importStatementCount: impact.importStatementCount,
|
|
754
|
+
barrelExportCount: impact.barrelExportCount,
|
|
755
|
+
sourceFileCount: impact.sourceFileCount,
|
|
756
|
+
existingSourceFileCount: impact.existingSourceFileCount,
|
|
757
|
+
scanTruncated: impact.truncated
|
|
758
|
+
};
|
|
759
|
+
}
|
|
760
|
+
function readFirstFailedCode(rows) {
|
|
761
|
+
const failed = rows.find((row) => row.ok === false);
|
|
762
|
+
return failed ? readString(failed.code) : null;
|
|
763
|
+
}
|
|
764
|
+
function appendExecutionMoveLines(lines, status) {
|
|
765
|
+
const completedSources = new Set(status.rows.filter((row) => row.ok !== false).map((row) => readString(row.source)).filter((value) => Boolean(value)));
|
|
766
|
+
const movesByTarget = new Map();
|
|
767
|
+
for (const move of status.plannedMoves) {
|
|
768
|
+
if (status.status !== "completed" && !completedSources.has(move.source)) {
|
|
769
|
+
continue;
|
|
770
|
+
}
|
|
771
|
+
movesByTarget.set(move.targetDir, [...(movesByTarget.get(move.targetDir) ?? []), move.source]);
|
|
772
|
+
}
|
|
773
|
+
if (movesByTarget.size === 0) {
|
|
774
|
+
return;
|
|
775
|
+
}
|
|
776
|
+
lines.push("moves:");
|
|
777
|
+
for (const [targetDir, sources] of movesByTarget) {
|
|
778
|
+
lines.push(`${targetDir}: ${sources.join(", ")}`);
|
|
779
|
+
}
|
|
780
|
+
}
|
|
781
|
+
function appendExecutionNotRunLines(lines, status) {
|
|
782
|
+
if (status.notRunRows <= 0) {
|
|
783
|
+
return;
|
|
784
|
+
}
|
|
785
|
+
const seenSources = new Set(status.rows.map((row) => readString(row.source)).filter((value) => Boolean(value)));
|
|
786
|
+
const notRun = status.plannedMoves.filter((move) => !seenSources.has(move.source));
|
|
787
|
+
if (notRun.length === 0) {
|
|
788
|
+
return;
|
|
789
|
+
}
|
|
790
|
+
lines.push("not run:");
|
|
791
|
+
for (const move of notRun) {
|
|
792
|
+
lines.push(move.source);
|
|
793
|
+
}
|
|
794
|
+
}
|
|
795
|
+
function readFileMoveToDirSyncWaitMs() {
|
|
796
|
+
return (0, mutation_execution_cache_1.readMutationSyncWaitMs)(process.env[env_vars_1.CLI_ENV.fileMoveToDirSyncWaitMs], 120_000);
|
|
797
|
+
}
|
|
798
|
+
function readFileMoveToDirRuntimeOptions() {
|
|
799
|
+
return {
|
|
800
|
+
postProcessImports: (0, file_mutation_runtime_1.isFileMutationImportPostProcessEnabled)(),
|
|
801
|
+
testFailRequiredImportUpdate: readString(process.env[env_vars_1.CLI_ENV.testFileMoveToDirFailImports]),
|
|
802
|
+
testRowDelayMs: (0, file_mutation_runtime_1.readFileMutationTestDelayMs)(process.env[env_vars_1.CLI_ENV.testFileMoveToDirRowDelayMs], 60_000),
|
|
803
|
+
testImportPostProcessDelayMs: (0, file_mutation_runtime_1.readFileMutationTestDelayMs)(process.env[env_vars_1.CLI_ENV.testFileMoveToDirImportsDelayMs], 60_000),
|
|
804
|
+
testPostMutationCyclesDelayMs: (0, file_mutation_runtime_1.readFileMutationTestDelayMs)(process.env[env_vars_1.CLI_ENV.testPostMutationCyclesDelayMs], 60_000)
|
|
805
|
+
};
|
|
806
|
+
}
|
|
807
|
+
function captureFileMoveToDirBackgroundEnv() {
|
|
808
|
+
return (0, file_mutation_runtime_1.captureFileMutationBackgroundEnv)([
|
|
809
|
+
env_vars_1.CLI_ENV.testFileMoveToDirDelayMs,
|
|
810
|
+
env_vars_1.CLI_ENV.testFileMoveToDirRowDelayMs,
|
|
811
|
+
env_vars_1.CLI_ENV.testFileMoveToDirImportsDelayMs,
|
|
812
|
+
env_vars_1.CLI_ENV.testFileMoveToDirFailImports
|
|
813
|
+
]);
|
|
814
|
+
}
|
|
815
|
+
function formatFileMoveToDirAgentText(response) {
|
|
816
|
+
const operation = readString(response.operation);
|
|
817
|
+
if (!operation?.startsWith("move.toDir.")) {
|
|
818
|
+
return null;
|
|
819
|
+
}
|
|
820
|
+
const lines = [];
|
|
821
|
+
const previewId = readString(response.previewId);
|
|
822
|
+
const executionId = readString(response.executionId);
|
|
823
|
+
lines.push(response.ok === false
|
|
824
|
+
? `${operation} failed`
|
|
825
|
+
: previewId && operation === "move.toDir.preview"
|
|
826
|
+
? `${operation} ${previewId}`
|
|
827
|
+
: executionId && (operation === "move.toDir.apply" || operation === "move.toDir.execute")
|
|
828
|
+
? `${operation} ${executionId}`
|
|
829
|
+
: operation);
|
|
830
|
+
if (typeof response.summary === "string") {
|
|
831
|
+
lines.push(response.summary);
|
|
832
|
+
}
|
|
833
|
+
if (operation === "move.toDir.preview" && readNumber(response.dirsToCreate) > 0) {
|
|
834
|
+
lines.push(`${readNumber(response.dirsToCreate)} ${plural(readNumber(response.dirsToCreate), "dir", "dirs")} will be created`);
|
|
835
|
+
}
|
|
836
|
+
const moves = Array.isArray(response.moves) ? response.moves.filter(isObject) : [];
|
|
837
|
+
if (moves.length > 0 && response.ok !== false) {
|
|
838
|
+
lines.push("moves:");
|
|
839
|
+
for (const move of moves) {
|
|
840
|
+
const targetDir = readString(move.targetDir);
|
|
841
|
+
const files = Array.isArray(move.files) ? move.files.filter((file) => typeof file === "string") : [];
|
|
842
|
+
if (targetDir && files.length > 0) {
|
|
843
|
+
lines.push(`${targetDir}: ${files.join(", ")}`);
|
|
844
|
+
}
|
|
845
|
+
}
|
|
846
|
+
}
|
|
847
|
+
appendFailureLines(lines, response);
|
|
848
|
+
const filesWritten = Array.isArray(response.filesWritten) ? response.filesWritten : [];
|
|
849
|
+
if (filesWritten.length > 0) {
|
|
850
|
+
appendFilesWrittenLines(lines, filesWritten, Array.isArray(response.filesMoved) ? response.filesMoved : []);
|
|
851
|
+
}
|
|
852
|
+
if (isObject(response.postMutation) && isObject(response.postMutation.cycles)) {
|
|
853
|
+
appendPostMutationCyclesText(lines, response.postMutation.cycles);
|
|
854
|
+
}
|
|
855
|
+
if (typeof response.next === "string") {
|
|
856
|
+
lines.push(`next: ${response.next}`);
|
|
857
|
+
}
|
|
858
|
+
return lines.join("\n");
|
|
859
|
+
}
|
|
860
|
+
function appendFailureLines(lines, response) {
|
|
861
|
+
if (response.ok !== false || !Array.isArray(response.rows)) {
|
|
862
|
+
return;
|
|
863
|
+
}
|
|
864
|
+
const failed = response.rows.filter(isObject).find((row) => row.ok === false);
|
|
865
|
+
if (!failed) {
|
|
866
|
+
return;
|
|
867
|
+
}
|
|
868
|
+
lines.push("failed:");
|
|
869
|
+
lines.push(`${readString(failed.source) ?? "source"} -> ${readString(failed.target) ?? "target"}`);
|
|
870
|
+
lines.push(`code: ${readString(failed.code) ?? "FILE_MOVE_TO_DIR_FAILED"}`);
|
|
871
|
+
if (typeof failed.error === "string") {
|
|
872
|
+
lines.push(failed.error);
|
|
873
|
+
}
|
|
874
|
+
if (typeof failed.rollback === "string") {
|
|
875
|
+
lines.push(`rollback: ${failed.rollback}`);
|
|
876
|
+
}
|
|
877
|
+
if (typeof failed.hint === "string") {
|
|
878
|
+
lines.push(`hint: ${failed.hint}`);
|
|
879
|
+
}
|
|
880
|
+
}
|
|
881
|
+
function fileMoveToDirHelp() {
|
|
882
|
+
return {
|
|
883
|
+
ok: true,
|
|
884
|
+
command: "file move toDir",
|
|
885
|
+
usage: "aib file move toDir preview --stdin | aib file move toDir execute --stdin | aib file move toDir apply <previewId>",
|
|
886
|
+
dsl: [
|
|
887
|
+
"@base packages/agent-project-tooling/src",
|
|
888
|
+
"moveToDir workspace-runner:",
|
|
889
|
+
" workspace-runner-cli.ts",
|
|
890
|
+
" workspace-runner-command-hints.ts"
|
|
891
|
+
],
|
|
892
|
+
notes: [
|
|
893
|
+
"preview validates planned file moves without writing.",
|
|
894
|
+
"execute moves files and updates TypeScript imports.",
|
|
895
|
+
"apply uses the cached preview id and refuses stale source/target state."
|
|
896
|
+
]
|
|
897
|
+
};
|
|
898
|
+
}
|
|
899
|
+
function collectRows(rows, field) {
|
|
900
|
+
return rows.map((row) => readString(row[field])).filter((value) => Boolean(value));
|
|
901
|
+
}
|
|
902
|
+
function collectStringArray(value) {
|
|
903
|
+
return Array.isArray(value) ? value.filter((item) => typeof item === "string") : [];
|
|
904
|
+
}
|
|
905
|
+
function collectImportSnapshots(value) {
|
|
906
|
+
return Array.isArray(value) ? value.filter(isObject) : [];
|
|
907
|
+
}
|
|
908
|
+
function runPostMutationCyclesSnapshot(cwd, files) {
|
|
909
|
+
const existingFiles = formatCycleFocusFiles(cwd, files).filter((file) => fs.existsSync(resolveCliFilePath(cwd, file)));
|
|
910
|
+
if (existingFiles.length === 0) {
|
|
911
|
+
return {
|
|
912
|
+
op: "cycles",
|
|
913
|
+
componentCount: 0,
|
|
914
|
+
components: []
|
|
915
|
+
};
|
|
916
|
+
}
|
|
917
|
+
const args = ["cycles"];
|
|
918
|
+
for (const file of existingFiles) {
|
|
919
|
+
args.push("--files", file);
|
|
920
|
+
}
|
|
921
|
+
args.push("--detail", "imports", "--limit", "50");
|
|
922
|
+
return (0, inspect_cycles_1.runInspectCycles)(cwd, args, undefined);
|
|
923
|
+
}
|
|
924
|
+
function diffPostMutationCycles(prePayload, postPayload, touchedFiles) {
|
|
925
|
+
const preKeys = new Set(readCycleComponents(prePayload).map(cycleComponentKey));
|
|
926
|
+
const newOrChanged = readCycleComponents(postPayload).filter((component) => readStringArray(component.files).some((file) => touchedFiles.has(file)) &&
|
|
927
|
+
!preKeys.has(cycleComponentKey(component)));
|
|
928
|
+
return {
|
|
929
|
+
status: newOrChanged.length > 0 ? "new-or-changed" : "none",
|
|
930
|
+
detail: "imports",
|
|
931
|
+
newOrChangedCount: newOrChanged.length,
|
|
932
|
+
preComponentCount: readNumber(prePayload.componentCount),
|
|
933
|
+
postComponentCount: readNumber(postPayload.componentCount),
|
|
934
|
+
components: newOrChanged
|
|
935
|
+
};
|
|
936
|
+
}
|
|
937
|
+
function readCycleComponents(payload) {
|
|
938
|
+
return (Array.isArray(payload.components) ? payload.components : [])
|
|
939
|
+
.filter(isObject)
|
|
940
|
+
.map((component) => ({
|
|
941
|
+
kind: readString(component.kind) ?? "mixed",
|
|
942
|
+
files: readStringArray(component.files).sort(),
|
|
943
|
+
chain: readString(component.chain) ?? "",
|
|
944
|
+
...(isObject(component.cycle) ? { cycle: component.cycle } : {}),
|
|
945
|
+
imports: readCycleImports(component)
|
|
946
|
+
}));
|
|
947
|
+
}
|
|
948
|
+
function readCycleImports(component) {
|
|
949
|
+
const cycle = isObject(component.cycle) ? component.cycle : {};
|
|
950
|
+
return readStringArray(cycle.imports);
|
|
951
|
+
}
|
|
952
|
+
function cycleComponentKey(component) {
|
|
953
|
+
return `${readString(component.kind) ?? "mixed"}:${readStringArray(component.files).sort().join("|")}`;
|
|
954
|
+
}
|
|
955
|
+
function formatCycleFocusFiles(cwd, files) {
|
|
956
|
+
return uniqueStrings(files.map((file) => formatRelativePath(cwd, resolveCliFilePath(cwd, file))));
|
|
957
|
+
}
|
|
958
|
+
function resolveCliFilePath(cwd, file) {
|
|
959
|
+
return path.normalize(path.isAbsolute(file) ? file : path.resolve(cwd, file));
|
|
960
|
+
}
|
|
961
|
+
function readStringArray(value) {
|
|
962
|
+
return collectStringArray(value);
|
|
963
|
+
}
|
|
964
|
+
function collectExistingFiles(cwd, files) {
|
|
965
|
+
return files.filter((file) => {
|
|
966
|
+
const resolved = path.isAbsolute(file) ? file : path.resolve(cwd, file);
|
|
967
|
+
return fs.existsSync(resolved);
|
|
968
|
+
});
|
|
969
|
+
}
|
|
970
|
+
function countTargetDirs(operations) {
|
|
971
|
+
return new Set(operations.map((operation) => normalizeKey(operation.targetDir))).size;
|
|
972
|
+
}
|
|
973
|
+
function countDirsToCreate(operations) {
|
|
974
|
+
const targetDirs = new Map();
|
|
975
|
+
for (const operation of operations) {
|
|
976
|
+
targetDirs.set(normalizeKey(operation.targetDir), operation.targetDir);
|
|
977
|
+
}
|
|
978
|
+
return Array.from(targetDirs.values()).filter((targetDir) => !fs.existsSync(targetDir)).length;
|
|
979
|
+
}
|
|
980
|
+
function compactList(items, limit) {
|
|
981
|
+
const unique = Array.from(new Set(items)).sort((left, right) => left.localeCompare(right));
|
|
982
|
+
const visible = unique.slice(0, limit);
|
|
983
|
+
const hidden = unique.length - visible.length;
|
|
984
|
+
return hidden > 0 ? [...visible, `+ ${hidden} more`] : visible;
|
|
985
|
+
}
|
|
986
|
+
function formatInlineList(values, limit) {
|
|
987
|
+
const visible = values.slice(0, limit);
|
|
988
|
+
const hidden = values.length - visible.length;
|
|
989
|
+
return hidden > 0 ? `${visible.join(", ")}, + ${hidden} more` : visible.join(", ");
|
|
990
|
+
}
|
|
991
|
+
function appendFilesWrittenLines(lines, values, movedTargets) {
|
|
992
|
+
const files = values.filter((value) => typeof value === "string");
|
|
993
|
+
if (files.length === 0) {
|
|
994
|
+
return;
|
|
995
|
+
}
|
|
996
|
+
const moved = new Set(movedTargets.filter((value) => typeof value === "string"));
|
|
997
|
+
const movedFiles = files.filter((file) => moved.has(file));
|
|
998
|
+
const referenceFiles = files.filter((file) => !moved.has(file));
|
|
999
|
+
const visibleReferenceFiles = referenceFiles.slice(0, 8);
|
|
1000
|
+
const hiddenReferenceFiles = referenceFiles.length - visibleReferenceFiles.length;
|
|
1001
|
+
lines.push("filesWritten:");
|
|
1002
|
+
for (const file of [...movedFiles, ...visibleReferenceFiles]) {
|
|
1003
|
+
lines.push(file);
|
|
1004
|
+
}
|
|
1005
|
+
if (hiddenReferenceFiles > 0) {
|
|
1006
|
+
lines.push(`+ ${hiddenReferenceFiles} reference ${plural(hiddenReferenceFiles, "file", "files")}`);
|
|
1007
|
+
}
|
|
1008
|
+
}
|
|
1009
|
+
function appendPostMutationCyclesText(lines, cycles) {
|
|
1010
|
+
lines.push("cycles:");
|
|
1011
|
+
const count = readNumber(cycles.newOrChangedCount);
|
|
1012
|
+
if (count === 0) {
|
|
1013
|
+
lines.push("no new/changed cycles involving touched files");
|
|
1014
|
+
return;
|
|
1015
|
+
}
|
|
1016
|
+
const components = Array.isArray(cycles.components) ? cycles.components.filter(isObject) : [];
|
|
1017
|
+
lines.push(formatPostMutationCycleSummary(count, components));
|
|
1018
|
+
components.forEach((component, index) => {
|
|
1019
|
+
(0, inspect_cycles_1.appendCycleComponentText)(lines, component, {
|
|
1020
|
+
detail: "imports",
|
|
1021
|
+
prefix: components.length === 1 ? "" : `${index + 1}. `,
|
|
1022
|
+
indent: components.length === 1 ? "" : " "
|
|
1023
|
+
});
|
|
1024
|
+
});
|
|
1025
|
+
}
|
|
1026
|
+
function formatPostMutationCycleSummary(count, components) {
|
|
1027
|
+
const kinds = components.map((component) => readString(component.kind) ?? "mixed");
|
|
1028
|
+
const uniqueKinds = Array.from(new Set(kinds));
|
|
1029
|
+
const kindText = uniqueKinds.length === 1 ? `${uniqueKinds[0]} ` : "";
|
|
1030
|
+
return `${count} new/changed ${kindText}${count === 1 ? "cycle" : "cycles"} involving touched files`;
|
|
1031
|
+
}
|
|
1032
|
+
function plural(count, one, many) {
|
|
1033
|
+
return count === 1 ? one : many;
|
|
1034
|
+
}
|
|
1035
|
+
function readString(value) {
|
|
1036
|
+
return typeof value === "string" && value.length > 0 ? value : null;
|
|
1037
|
+
}
|
|
1038
|
+
function readNumber(value) {
|
|
1039
|
+
return typeof value === "number" && Number.isFinite(value) ? value : 0;
|
|
1040
|
+
}
|
|
1041
|
+
function compactObject(input) {
|
|
1042
|
+
return Object.fromEntries(Object.entries(input).filter(([, value]) => {
|
|
1043
|
+
if (value === null || value === undefined) {
|
|
1044
|
+
return false;
|
|
1045
|
+
}
|
|
1046
|
+
return !(Array.isArray(value) && value.length === 0);
|
|
1047
|
+
}));
|
|
1048
|
+
}
|
|
1049
|
+
function isObject(value) {
|
|
1050
|
+
return Boolean(value) && typeof value === "object" && !Array.isArray(value);
|
|
1051
|
+
}
|
|
1052
|
+
function normalizeKey(filePath) {
|
|
1053
|
+
const normalized = path.normalize(filePath);
|
|
1054
|
+
return process.platform === "win32" ? normalized.toLowerCase() : normalized;
|
|
1055
|
+
}
|
|
1056
|
+
function uniqueStrings(values) {
|
|
1057
|
+
return Array.from(new Set(values));
|
|
1058
|
+
}
|
|
1059
|
+
function yieldToEventLoop() {
|
|
1060
|
+
return new Promise((resolve) => setImmediate(resolve));
|
|
1061
|
+
}
|
|
1062
|
+
async function maybeDelayPostMutationCycles(delayMs) {
|
|
1063
|
+
if (delayMs <= 0) {
|
|
1064
|
+
return;
|
|
1065
|
+
}
|
|
1066
|
+
await new Promise((resolve) => setTimeout(resolve, delayMs));
|
|
1067
|
+
}
|
|
1068
|
+
function formatRelativePath(cwd, filePath) {
|
|
1069
|
+
if (!filePath) {
|
|
1070
|
+
return "";
|
|
1071
|
+
}
|
|
1072
|
+
return path.relative(cwd, filePath).replace(/\\/g, "/");
|
|
1073
|
+
}
|