@ashlr/hub 2.2.0
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/CHANGELOG.md +1158 -0
- package/LICENSE +21 -0
- package/README.md +833 -0
- package/bin/ashlr +8 -0
- package/dist/api/core.d.ts +28 -0
- package/dist/api/core.js +42 -0
- package/dist/api/core.js.map +1 -0
- package/dist/api/index.d.ts +9 -0
- package/dist/api/index.js +9 -0
- package/dist/api/index.js.map +1 -0
- package/dist/api/plugin.d.ts +12 -0
- package/dist/api/plugin.js +13 -0
- package/dist/api/plugin.js.map +1 -0
- package/dist/api/types.d.ts +9 -0
- package/dist/api/types.js +9 -0
- package/dist/api/types.js.map +1 -0
- package/dist/cli/args.d.ts +20 -0
- package/dist/cli/args.js +23 -0
- package/dist/cli/args.js.map +1 -0
- package/dist/cli/ask.d.ts +22 -0
- package/dist/cli/ask.js +240 -0
- package/dist/cli/ask.js.map +1 -0
- package/dist/cli/audit.d.ts +26 -0
- package/dist/cli/audit.js +199 -0
- package/dist/cli/audit.js.map +1 -0
- package/dist/cli/backlog.d.ts +26 -0
- package/dist/cli/backlog.js +322 -0
- package/dist/cli/backlog.js.map +1 -0
- package/dist/cli/completions.d.ts +18 -0
- package/dist/cli/completions.js +156 -0
- package/dist/cli/completions.js.map +1 -0
- package/dist/cli/daemon.d.ts +31 -0
- package/dist/cli/daemon.js +334 -0
- package/dist/cli/daemon.js.map +1 -0
- package/dist/cli/demo-sandbox.d.ts +78 -0
- package/dist/cli/demo-sandbox.js +227 -0
- package/dist/cli/demo-sandbox.js.map +1 -0
- package/dist/cli/demo.d.ts +76 -0
- package/dist/cli/demo.js +285 -0
- package/dist/cli/demo.js.map +1 -0
- package/dist/cli/digest.d.ts +46 -0
- package/dist/cli/digest.js +352 -0
- package/dist/cli/digest.js.map +1 -0
- package/dist/cli/doctor-init.d.ts +28 -0
- package/dist/cli/doctor-init.js +335 -0
- package/dist/cli/doctor-init.js.map +1 -0
- package/dist/cli/genome.d.ts +62 -0
- package/dist/cli/genome.js +1061 -0
- package/dist/cli/genome.js.map +1 -0
- package/dist/cli/gh.d.ts +27 -0
- package/dist/cli/gh.js +322 -0
- package/dist/cli/gh.js.map +1 -0
- package/dist/cli/goals.d.ts +55 -0
- package/dist/cli/goals.js +667 -0
- package/dist/cli/goals.js.map +1 -0
- package/dist/cli/health.d.ts +56 -0
- package/dist/cli/health.js +407 -0
- package/dist/cli/health.js.map +1 -0
- package/dist/cli/help.d.ts +51 -0
- package/dist/cli/help.js +436 -0
- package/dist/cli/help.js.map +1 -0
- package/dist/cli/inbox.d.ts +28 -0
- package/dist/cli/inbox.js +589 -0
- package/dist/cli/inbox.js.map +1 -0
- package/dist/cli/index.d.ts +41 -0
- package/dist/cli/index.js +1208 -0
- package/dist/cli/index.js.map +1 -0
- package/dist/cli/knowledge.d.ts +33 -0
- package/dist/cli/knowledge.js +575 -0
- package/dist/cli/knowledge.js.map +1 -0
- package/dist/cli/mcp.d.ts +26 -0
- package/dist/cli/mcp.js +487 -0
- package/dist/cli/mcp.js.map +1 -0
- package/dist/cli/models.d.ts +26 -0
- package/dist/cli/models.js +435 -0
- package/dist/cli/models.js.map +1 -0
- package/dist/cli/new.d.ts +32 -0
- package/dist/cli/new.js +565 -0
- package/dist/cli/new.js.map +1 -0
- package/dist/cli/notify.d.ts +20 -0
- package/dist/cli/notify.js +188 -0
- package/dist/cli/notify.js.map +1 -0
- package/dist/cli/onboard.d.ts +85 -0
- package/dist/cli/onboard.js +305 -0
- package/dist/cli/onboard.js.map +1 -0
- package/dist/cli/open.d.ts +38 -0
- package/dist/cli/open.js +86 -0
- package/dist/cli/open.js.map +1 -0
- package/dist/cli/orient.d.ts +14 -0
- package/dist/cli/orient.js +110 -0
- package/dist/cli/orient.js.map +1 -0
- package/dist/cli/picker.d.ts +21 -0
- package/dist/cli/picker.js +177 -0
- package/dist/cli/picker.js.map +1 -0
- package/dist/cli/plugins.d.ts +21 -0
- package/dist/cli/plugins.js +394 -0
- package/dist/cli/plugins.js.map +1 -0
- package/dist/cli/preflight.d.ts +29 -0
- package/dist/cli/preflight.js +131 -0
- package/dist/cli/preflight.js.map +1 -0
- package/dist/cli/pulse.d.ts +26 -0
- package/dist/cli/pulse.js +482 -0
- package/dist/cli/pulse.js.map +1 -0
- package/dist/cli/reflect.d.ts +42 -0
- package/dist/cli/reflect.js +381 -0
- package/dist/cli/reflect.js.map +1 -0
- package/dist/cli/run.d.ts +29 -0
- package/dist/cli/run.js +687 -0
- package/dist/cli/run.js.map +1 -0
- package/dist/cli/sandbox.d.ts +20 -0
- package/dist/cli/sandbox.js +345 -0
- package/dist/cli/sandbox.js.map +1 -0
- package/dist/cli/seams.d.ts +41 -0
- package/dist/cli/seams.js +167 -0
- package/dist/cli/seams.js.map +1 -0
- package/dist/cli/serve.d.ts +25 -0
- package/dist/cli/serve.js +249 -0
- package/dist/cli/serve.js.map +1 -0
- package/dist/cli/ship.d.ts +33 -0
- package/dist/cli/ship.js +433 -0
- package/dist/cli/ship.js.map +1 -0
- package/dist/cli/spec.d.ts +19 -0
- package/dist/cli/spec.js +478 -0
- package/dist/cli/spec.js.map +1 -0
- package/dist/cli/swarm.d.ts +42 -0
- package/dist/cli/swarm.js +1365 -0
- package/dist/cli/swarm.js.map +1 -0
- package/dist/cli/telemetry.d.ts +26 -0
- package/dist/cli/telemetry.js +364 -0
- package/dist/cli/telemetry.js.map +1 -0
- package/dist/cli/tui.d.ts +17 -0
- package/dist/cli/tui.js +52 -0
- package/dist/cli/tui.js.map +1 -0
- package/dist/cli/ui.d.ts +53 -0
- package/dist/cli/ui.js +66 -0
- package/dist/cli/ui.js.map +1 -0
- package/dist/cli/update.d.ts +38 -0
- package/dist/cli/update.js +682 -0
- package/dist/cli/update.js.map +1 -0
- package/dist/cli/vercel.d.ts +20 -0
- package/dist/cli/vercel.js +193 -0
- package/dist/cli/vercel.js.map +1 -0
- package/dist/cli/verify-safety.d.ts +96 -0
- package/dist/cli/verify-safety.js +509 -0
- package/dist/cli/verify-safety.js.map +1 -0
- package/dist/cli/wire.d.ts +22 -0
- package/dist/cli/wire.js +205 -0
- package/dist/cli/wire.js.map +1 -0
- package/dist/core/classify.d.ts +51 -0
- package/dist/core/classify.js +450 -0
- package/dist/core/classify.js.map +1 -0
- package/dist/core/config.d.ts +63 -0
- package/dist/core/config.js +474 -0
- package/dist/core/config.js.map +1 -0
- package/dist/core/daemon/loop.d.ts +74 -0
- package/dist/core/daemon/loop.js +618 -0
- package/dist/core/daemon/loop.js.map +1 -0
- package/dist/core/daemon/state.d.ts +66 -0
- package/dist/core/daemon/state.js +197 -0
- package/dist/core/daemon/state.js.map +1 -0
- package/dist/core/dashboard.d.ts +40 -0
- package/dist/core/dashboard.js +463 -0
- package/dist/core/dashboard.js.map +1 -0
- package/dist/core/digest/build.d.ts +51 -0
- package/dist/core/digest/build.js +230 -0
- package/dist/core/digest/build.js.map +1 -0
- package/dist/core/digest/deliver.d.ts +47 -0
- package/dist/core/digest/deliver.js +230 -0
- package/dist/core/digest/deliver.js.map +1 -0
- package/dist/core/digest/store.d.ts +57 -0
- package/dist/core/digest/store.js +223 -0
- package/dist/core/digest/store.js.map +1 -0
- package/dist/core/doctor-fix.d.ts +21 -0
- package/dist/core/doctor-fix.js +440 -0
- package/dist/core/doctor-fix.js.map +1 -0
- package/dist/core/doctor.d.ts +18 -0
- package/dist/core/doctor.js +806 -0
- package/dist/core/doctor.js.map +1 -0
- package/dist/core/env-bridge.d.ts +64 -0
- package/dist/core/env-bridge.js +103 -0
- package/dist/core/env-bridge.js.map +1 -0
- package/dist/core/genome/capture.d.ts +49 -0
- package/dist/core/genome/capture.js +352 -0
- package/dist/core/genome/capture.js.map +1 -0
- package/dist/core/genome/consolidate.d.ts +38 -0
- package/dist/core/genome/consolidate.js +426 -0
- package/dist/core/genome/consolidate.js.map +1 -0
- package/dist/core/genome/export.d.ts +29 -0
- package/dist/core/genome/export.js +102 -0
- package/dist/core/genome/export.js.map +1 -0
- package/dist/core/genome/playbook.d.ts +33 -0
- package/dist/core/genome/playbook.js +320 -0
- package/dist/core/genome/playbook.js.map +1 -0
- package/dist/core/genome/recall.d.ts +45 -0
- package/dist/core/genome/recall.js +293 -0
- package/dist/core/genome/recall.js.map +1 -0
- package/dist/core/genome/store.d.ts +62 -0
- package/dist/core/genome/store.js +711 -0
- package/dist/core/genome/store.js.map +1 -0
- package/dist/core/git.d.ts +34 -0
- package/dist/core/git.js +115 -0
- package/dist/core/git.js.map +1 -0
- package/dist/core/goals/advance.d.ts +82 -0
- package/dist/core/goals/advance.js +263 -0
- package/dist/core/goals/advance.js.map +1 -0
- package/dist/core/goals/planner.d.ts +58 -0
- package/dist/core/goals/planner.js +233 -0
- package/dist/core/goals/planner.js.map +1 -0
- package/dist/core/goals/store.d.ts +128 -0
- package/dist/core/goals/store.js +442 -0
- package/dist/core/goals/store.js.map +1 -0
- package/dist/core/inbox/apply.d.ts +36 -0
- package/dist/core/inbox/apply.js +407 -0
- package/dist/core/inbox/apply.js.map +1 -0
- package/dist/core/inbox/notify-proposal.d.ts +13 -0
- package/dist/core/inbox/notify-proposal.js +21 -0
- package/dist/core/inbox/notify-proposal.js.map +1 -0
- package/dist/core/inbox/store.d.ts +67 -0
- package/dist/core/inbox/store.js +258 -0
- package/dist/core/inbox/store.js.map +1 -0
- package/dist/core/index-engine.d.ts +62 -0
- package/dist/core/index-engine.js +486 -0
- package/dist/core/index-engine.js.map +1 -0
- package/dist/core/integrations/desktop-notify.d.ts +18 -0
- package/dist/core/integrations/desktop-notify.js +42 -0
- package/dist/core/integrations/desktop-notify.js.map +1 -0
- package/dist/core/integrations/editors.d.ts +50 -0
- package/dist/core/integrations/editors.js +216 -0
- package/dist/core/integrations/editors.js.map +1 -0
- package/dist/core/integrations/github.d.ts +66 -0
- package/dist/core/integrations/github.js +332 -0
- package/dist/core/integrations/github.js.map +1 -0
- package/dist/core/integrations/identity.d.ts +29 -0
- package/dist/core/integrations/identity.js +359 -0
- package/dist/core/integrations/identity.js.map +1 -0
- package/dist/core/integrations/notify.d.ts +23 -0
- package/dist/core/integrations/notify.js +96 -0
- package/dist/core/integrations/notify.js.map +1 -0
- package/dist/core/integrations/vercel.d.ts +37 -0
- package/dist/core/integrations/vercel.js +192 -0
- package/dist/core/integrations/vercel.js.map +1 -0
- package/dist/core/knowledge/ask.d.ts +34 -0
- package/dist/core/knowledge/ask.js +325 -0
- package/dist/core/knowledge/ask.js.map +1 -0
- package/dist/core/knowledge/graph.d.ts +51 -0
- package/dist/core/knowledge/graph.js +564 -0
- package/dist/core/knowledge/graph.js.map +1 -0
- package/dist/core/knowledge/index.d.ts +74 -0
- package/dist/core/knowledge/index.js +586 -0
- package/dist/core/knowledge/index.js.map +1 -0
- package/dist/core/learn/playbooks.d.ts +84 -0
- package/dist/core/learn/playbooks.js +241 -0
- package/dist/core/learn/playbooks.js.map +1 -0
- package/dist/core/learn/reflect.d.ts +87 -0
- package/dist/core/learn/reflect.js +435 -0
- package/dist/core/learn/reflect.js.map +1 -0
- package/dist/core/learn/store.d.ts +51 -0
- package/dist/core/learn/store.js +165 -0
- package/dist/core/learn/store.js.map +1 -0
- package/dist/core/learn/tuning.d.ts +48 -0
- package/dist/core/learn/tuning.js +201 -0
- package/dist/core/learn/tuning.js.map +1 -0
- package/dist/core/lifecycle/scaffold.d.ts +43 -0
- package/dist/core/lifecycle/scaffold.js +260 -0
- package/dist/core/lifecycle/scaffold.js.map +1 -0
- package/dist/core/lifecycle/ship.d.ts +48 -0
- package/dist/core/lifecycle/ship.js +513 -0
- package/dist/core/lifecycle/ship.js.map +1 -0
- package/dist/core/lifecycle/templates.d.ts +20 -0
- package/dist/core/lifecycle/templates.js +605 -0
- package/dist/core/lifecycle/templates.js.map +1 -0
- package/dist/core/mcp-gateway.d.ts +59 -0
- package/dist/core/mcp-gateway.js +385 -0
- package/dist/core/mcp-gateway.js.map +1 -0
- package/dist/core/mcp-native.d.ts +53 -0
- package/dist/core/mcp-native.js +507 -0
- package/dist/core/mcp-native.js.map +1 -0
- package/dist/core/mcp-registry.d.ts +36 -0
- package/dist/core/mcp-registry.js +180 -0
- package/dist/core/mcp-registry.js.map +1 -0
- package/dist/core/observability/budget-alert.d.ts +18 -0
- package/dist/core/observability/budget-alert.js +90 -0
- package/dist/core/observability/budget-alert.js.map +1 -0
- package/dist/core/observability/estimate.d.ts +27 -0
- package/dist/core/observability/estimate.js +188 -0
- package/dist/core/observability/estimate.js.map +1 -0
- package/dist/core/observability/forecast.d.ts +19 -0
- package/dist/core/observability/forecast.js +101 -0
- package/dist/core/observability/forecast.js.map +1 -0
- package/dist/core/observability/governance.d.ts +28 -0
- package/dist/core/observability/governance.js +101 -0
- package/dist/core/observability/governance.js.map +1 -0
- package/dist/core/observability/otlp.d.ts +88 -0
- package/dist/core/observability/otlp.js +217 -0
- package/dist/core/observability/otlp.js.map +1 -0
- package/dist/core/observability/rollup.d.ts +35 -0
- package/dist/core/observability/rollup.js +311 -0
- package/dist/core/observability/rollup.js.map +1 -0
- package/dist/core/observability/telemetry-sink.d.ts +63 -0
- package/dist/core/observability/telemetry-sink.js +350 -0
- package/dist/core/observability/telemetry-sink.js.map +1 -0
- package/dist/core/observability/usage-source.d.ts +60 -0
- package/dist/core/observability/usage-source.js +347 -0
- package/dist/core/observability/usage-source.js.map +1 -0
- package/dist/core/onboard.d.ts +27 -0
- package/dist/core/onboard.js +288 -0
- package/dist/core/onboard.js.map +1 -0
- package/dist/core/orient.d.ts +23 -0
- package/dist/core/orient.js +135 -0
- package/dist/core/orient.js.map +1 -0
- package/dist/core/phantom.d.ts +23 -0
- package/dist/core/phantom.js +279 -0
- package/dist/core/phantom.js.map +1 -0
- package/dist/core/plugins/host-api.d.ts +29 -0
- package/dist/core/plugins/host-api.js +113 -0
- package/dist/core/plugins/host-api.js.map +1 -0
- package/dist/core/plugins/integrity.d.ts +36 -0
- package/dist/core/plugins/integrity.js +73 -0
- package/dist/core/plugins/integrity.js.map +1 -0
- package/dist/core/plugins/manifest.d.ts +31 -0
- package/dist/core/plugins/manifest.js +316 -0
- package/dist/core/plugins/manifest.js.map +1 -0
- package/dist/core/plugins/registry.d.ts +87 -0
- package/dist/core/plugins/registry.js +415 -0
- package/dist/core/plugins/registry.js.map +1 -0
- package/dist/core/plugins/types.d.ts +182 -0
- package/dist/core/plugins/types.js +40 -0
- package/dist/core/plugins/types.js.map +1 -0
- package/dist/core/plugins/wrappers.d.ts +40 -0
- package/dist/core/plugins/wrappers.js +229 -0
- package/dist/core/plugins/wrappers.js.map +1 -0
- package/dist/core/portfolio/backlog.d.ts +40 -0
- package/dist/core/portfolio/backlog.js +177 -0
- package/dist/core/portfolio/backlog.js.map +1 -0
- package/dist/core/portfolio/scanners.d.ts +21 -0
- package/dist/core/portfolio/scanners.js +600 -0
- package/dist/core/portfolio/scanners.js.map +1 -0
- package/dist/core/providers.d.ts +34 -0
- package/dist/core/providers.js +250 -0
- package/dist/core/providers.js.map +1 -0
- package/dist/core/quality/conventions.d.ts +35 -0
- package/dist/core/quality/conventions.js +267 -0
- package/dist/core/quality/conventions.js.map +1 -0
- package/dist/core/quality/fixes.d.ts +56 -0
- package/dist/core/quality/fixes.js +209 -0
- package/dist/core/quality/fixes.js.map +1 -0
- package/dist/core/quality/health.d.ts +69 -0
- package/dist/core/quality/health.js +350 -0
- package/dist/core/quality/health.js.map +1 -0
- package/dist/core/quality/store.d.ts +56 -0
- package/dist/core/quality/store.js +195 -0
- package/dist/core/quality/store.js.map +1 -0
- package/dist/core/readiness.d.ts +112 -0
- package/dist/core/readiness.js +431 -0
- package/dist/core/readiness.js.map +1 -0
- package/dist/core/run/agent-loop.d.ts +40 -0
- package/dist/core/run/agent-loop.js +291 -0
- package/dist/core/run/agent-loop.js.map +1 -0
- package/dist/core/run/budget.d.ts +47 -0
- package/dist/core/run/budget.js +113 -0
- package/dist/core/run/budget.js.map +1 -0
- package/dist/core/run/engines.d.ts +75 -0
- package/dist/core/run/engines.js +199 -0
- package/dist/core/run/engines.js.map +1 -0
- package/dist/core/run/model-manager.d.ts +64 -0
- package/dist/core/run/model-manager.js +339 -0
- package/dist/core/run/model-manager.js.map +1 -0
- package/dist/core/run/orchestrator.d.ts +100 -0
- package/dist/core/run/orchestrator.js +1515 -0
- package/dist/core/run/orchestrator.js.map +1 -0
- package/dist/core/run/provider-client.d.ts +46 -0
- package/dist/core/run/provider-client.js +796 -0
- package/dist/core/run/provider-client.js.map +1 -0
- package/dist/core/run/retry.d.ts +19 -0
- package/dist/core/run/retry.js +68 -0
- package/dist/core/run/retry.js.map +1 -0
- package/dist/core/run/router.d.ts +50 -0
- package/dist/core/run/router.js +257 -0
- package/dist/core/run/router.js.map +1 -0
- package/dist/core/run/self-heal.d.ts +52 -0
- package/dist/core/run/self-heal.js +181 -0
- package/dist/core/run/self-heal.js.map +1 -0
- package/dist/core/run/streaming.d.ts +31 -0
- package/dist/core/run/streaming.js +122 -0
- package/dist/core/run/streaming.js.map +1 -0
- package/dist/core/run/verify.d.ts +30 -0
- package/dist/core/run/verify.js +204 -0
- package/dist/core/run/verify.js.map +1 -0
- package/dist/core/sandbox/audit.d.ts +31 -0
- package/dist/core/sandbox/audit.js +169 -0
- package/dist/core/sandbox/audit.js.map +1 -0
- package/dist/core/sandbox/policy.d.ts +61 -0
- package/dist/core/sandbox/policy.js +211 -0
- package/dist/core/sandbox/policy.js.map +1 -0
- package/dist/core/sandbox/worktree.d.ts +175 -0
- package/dist/core/sandbox/worktree.js +673 -0
- package/dist/core/sandbox/worktree.js.map +1 -0
- package/dist/core/seams/backlog.d.ts +47 -0
- package/dist/core/seams/backlog.js +47 -0
- package/dist/core/seams/backlog.js.map +1 -0
- package/dist/core/seams/daemon-coordinator.d.ts +72 -0
- package/dist/core/seams/daemon-coordinator.js +76 -0
- package/dist/core/seams/daemon-coordinator.js.map +1 -0
- package/dist/core/seams/genome.d.ts +45 -0
- package/dist/core/seams/genome.js +53 -0
- package/dist/core/seams/genome.js.map +1 -0
- package/dist/core/seams/identity.d.ts +40 -0
- package/dist/core/seams/identity.js +44 -0
- package/dist/core/seams/identity.js.map +1 -0
- package/dist/core/seams/inbox.d.ts +60 -0
- package/dist/core/seams/inbox.js +66 -0
- package/dist/core/seams/inbox.js.map +1 -0
- package/dist/core/seams/index.d.ts +20 -0
- package/dist/core/seams/index.js +21 -0
- package/dist/core/seams/index.js.map +1 -0
- package/dist/core/seams/portfolio.d.ts +50 -0
- package/dist/core/seams/portfolio.js +61 -0
- package/dist/core/seams/portfolio.js.map +1 -0
- package/dist/core/seams/registry.d.ts +42 -0
- package/dist/core/seams/registry.js +128 -0
- package/dist/core/seams/registry.js.map +1 -0
- package/dist/core/seams/run-swarm.d.ts +66 -0
- package/dist/core/seams/run-swarm.js +74 -0
- package/dist/core/seams/run-swarm.js.map +1 -0
- package/dist/core/seams/types.d.ts +123 -0
- package/dist/core/seams/types.js +35 -0
- package/dist/core/seams/types.js.map +1 -0
- package/dist/core/spec/spec-store.d.ts +62 -0
- package/dist/core/spec/spec-store.js +359 -0
- package/dist/core/spec/spec-store.js.map +1 -0
- package/dist/core/swarm/gate.d.ts +45 -0
- package/dist/core/swarm/gate.js +114 -0
- package/dist/core/swarm/gate.js.map +1 -0
- package/dist/core/swarm/planner.d.ts +32 -0
- package/dist/core/swarm/planner.js +293 -0
- package/dist/core/swarm/planner.js.map +1 -0
- package/dist/core/swarm/rollback.d.ts +56 -0
- package/dist/core/swarm/rollback.js +266 -0
- package/dist/core/swarm/rollback.js.map +1 -0
- package/dist/core/swarm/runner.d.ts +62 -0
- package/dist/core/swarm/runner.js +1263 -0
- package/dist/core/swarm/runner.js.map +1 -0
- package/dist/core/swarm/sign.d.ts +71 -0
- package/dist/core/swarm/sign.js +362 -0
- package/dist/core/swarm/sign.js.map +1 -0
- package/dist/core/swarm/store.d.ts +52 -0
- package/dist/core/swarm/store.js +195 -0
- package/dist/core/swarm/store.js.map +1 -0
- package/dist/core/tidy.d.ts +32 -0
- package/dist/core/tidy.js +354 -0
- package/dist/core/tidy.js.map +1 -0
- package/dist/core/tools-registry.d.ts +16 -0
- package/dist/core/tools-registry.js +308 -0
- package/dist/core/tools-registry.js.map +1 -0
- package/dist/core/types.d.ts +2545 -0
- package/dist/core/types.js +9 -0
- package/dist/core/types.js.map +1 -0
- package/dist/core/web/api.d.ts +53 -0
- package/dist/core/web/api.js +698 -0
- package/dist/core/web/api.js.map +1 -0
- package/dist/core/web/public/app.js +1906 -0
- package/dist/core/web/public/index.html +721 -0
- package/dist/core/web/public/styles.css +2007 -0
- package/dist/core/web/server.d.ts +18 -0
- package/dist/core/web/server.js +122 -0
- package/dist/core/web/server.js.map +1 -0
- package/dist/core/web/static.d.ts +18 -0
- package/dist/core/web/static.js +122 -0
- package/dist/core/web/static.js.map +1 -0
- package/dist/tui/app.d.ts +33 -0
- package/dist/tui/app.js +350 -0
- package/dist/tui/app.js.map +1 -0
- package/dist/tui/render.d.ts +20 -0
- package/dist/tui/render.js +558 -0
- package/dist/tui/render.js.map +1 -0
- package/package.json +80 -0
- package/schema/config.schema.json +223 -0
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* consolidate.ts — Genome consolidation for M16.
|
|
3
|
+
*
|
|
4
|
+
* Merges near-duplicate hub entries (same project + normalized goal/title +
|
|
5
|
+
* high token-overlap) into single canonical entries that preserve provenance:
|
|
6
|
+
* - mergedCount (how many source entries were folded in)
|
|
7
|
+
* - firstTs / lastTs (time span)
|
|
8
|
+
* - union of all tags
|
|
9
|
+
* - longest/most-informative text retained
|
|
10
|
+
*
|
|
11
|
+
* GUARDRAILS:
|
|
12
|
+
* - Writes a TIMESTAMPED BACKUP of hub.jsonl FIRST — no mutation before
|
|
13
|
+
* the backup succeeds.
|
|
14
|
+
* - NEVER drops information silently: merged entries retain their key content
|
|
15
|
+
* via longest-text selection + tag union.
|
|
16
|
+
* - Bounded: caps the comparison work to prevent O(n²) blow-up on huge stores.
|
|
17
|
+
* - Never throws — all I/O is wrapped defensively.
|
|
18
|
+
* - Append-only semantics preserved elsewhere; this is the ONE controlled
|
|
19
|
+
* rewrite of the hub store, and it is always backup-gated.
|
|
20
|
+
*/
|
|
21
|
+
import type { AshlrConfig, ConsolidationResult } from '../types.js';
|
|
22
|
+
/**
|
|
23
|
+
* Consolidate near-duplicate entries in hub.jsonl.
|
|
24
|
+
*
|
|
25
|
+
* Steps:
|
|
26
|
+
* 1. Read hub.jsonl entries.
|
|
27
|
+
* 2. Write a timestamped backup (FIRST — before any mutation).
|
|
28
|
+
* 3. Group entries: same [project × normalized-title] bucket first (cheap),
|
|
29
|
+
* then token-overlap within each bucket (Jaccard ≥ OVERLAP_THRESHOLD).
|
|
30
|
+
* 4. Merge each group into a single canonical entry (longest text + union
|
|
31
|
+
* tags + provenance fields: mergedCount, firstTs, lastTs).
|
|
32
|
+
* 5. Rewrite hub.jsonl with merged + un-merged entries.
|
|
33
|
+
* 6. Return { before, after, merged, backupPath }.
|
|
34
|
+
*
|
|
35
|
+
* Returns merged:0 / before===after when nothing to merge (backup still written).
|
|
36
|
+
* Never throws.
|
|
37
|
+
*/
|
|
38
|
+
export declare function consolidateGenome(_cfg: AshlrConfig): Promise<ConsolidationResult>;
|
|
@@ -0,0 +1,426 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* consolidate.ts — Genome consolidation for M16.
|
|
3
|
+
*
|
|
4
|
+
* Merges near-duplicate hub entries (same project + normalized goal/title +
|
|
5
|
+
* high token-overlap) into single canonical entries that preserve provenance:
|
|
6
|
+
* - mergedCount (how many source entries were folded in)
|
|
7
|
+
* - firstTs / lastTs (time span)
|
|
8
|
+
* - union of all tags
|
|
9
|
+
* - longest/most-informative text retained
|
|
10
|
+
*
|
|
11
|
+
* GUARDRAILS:
|
|
12
|
+
* - Writes a TIMESTAMPED BACKUP of hub.jsonl FIRST — no mutation before
|
|
13
|
+
* the backup succeeds.
|
|
14
|
+
* - NEVER drops information silently: merged entries retain their key content
|
|
15
|
+
* via longest-text selection + tag union.
|
|
16
|
+
* - Bounded: caps the comparison work to prevent O(n²) blow-up on huge stores.
|
|
17
|
+
* - Never throws — all I/O is wrapped defensively.
|
|
18
|
+
* - Append-only semantics preserved elsewhere; this is the ONE controlled
|
|
19
|
+
* rewrite of the hub store, and it is always backup-gated.
|
|
20
|
+
*/
|
|
21
|
+
import fs from 'node:fs';
|
|
22
|
+
import { hubStorePath } from './store.js';
|
|
23
|
+
// ---------------------------------------------------------------------------
|
|
24
|
+
// Constants
|
|
25
|
+
// ---------------------------------------------------------------------------
|
|
26
|
+
/** Maximum number of entries to load from hub.jsonl for consolidation. */
|
|
27
|
+
const CONSOLIDATE_MAX_ENTRIES = 2000;
|
|
28
|
+
/**
|
|
29
|
+
* Token-overlap (Jaccard) ratio threshold above which two entries are
|
|
30
|
+
* considered near-duplicates. 0.5 = 50% shared tokens.
|
|
31
|
+
*/
|
|
32
|
+
const OVERLAP_THRESHOLD = 0.5;
|
|
33
|
+
/**
|
|
34
|
+
* Maximum number of pairwise comparisons to cap O(n²) work.
|
|
35
|
+
* At 2000 entries, naïve pairs = 2M; we short-circuit at this budget.
|
|
36
|
+
*/
|
|
37
|
+
const MAX_COMPARISONS = 200_000;
|
|
38
|
+
// ---------------------------------------------------------------------------
|
|
39
|
+
// Tokenization (reuse the same approach as recall.ts for consistency)
|
|
40
|
+
// ---------------------------------------------------------------------------
|
|
41
|
+
/** Tokenize text: lowercase, split on non-alphanumeric, drop empties. */
|
|
42
|
+
function tokenize(text) {
|
|
43
|
+
return text
|
|
44
|
+
.toLowerCase()
|
|
45
|
+
.split(/[^a-z0-9]+/)
|
|
46
|
+
.filter((t) => t.length > 1); // drop single-char tokens to reduce noise
|
|
47
|
+
}
|
|
48
|
+
/** Build a Set of tokens from concatenated title + text for an entry. */
|
|
49
|
+
function entryTokenSet(entry) {
|
|
50
|
+
return new Set(tokenize(`${entry.title} ${entry.text}`));
|
|
51
|
+
}
|
|
52
|
+
/**
|
|
53
|
+
* Jaccard similarity between two token sets.
|
|
54
|
+
* Returns 0..1 (0 = disjoint, 1 = identical token sets).
|
|
55
|
+
*/
|
|
56
|
+
function jaccardSimilarity(a, b) {
|
|
57
|
+
if (a.size === 0 && b.size === 0)
|
|
58
|
+
return 1; // both empty = identical
|
|
59
|
+
if (a.size === 0 || b.size === 0)
|
|
60
|
+
return 0;
|
|
61
|
+
let intersectionSize = 0;
|
|
62
|
+
// Iterate smaller set for efficiency
|
|
63
|
+
const [smaller, larger] = a.size <= b.size ? [a, b] : [b, a];
|
|
64
|
+
for (const token of smaller) {
|
|
65
|
+
if (larger.has(token))
|
|
66
|
+
intersectionSize++;
|
|
67
|
+
}
|
|
68
|
+
const unionSize = a.size + b.size - intersectionSize;
|
|
69
|
+
return unionSize === 0 ? 0 : intersectionSize / unionSize;
|
|
70
|
+
}
|
|
71
|
+
// ---------------------------------------------------------------------------
|
|
72
|
+
// Normalization helpers
|
|
73
|
+
// ---------------------------------------------------------------------------
|
|
74
|
+
/**
|
|
75
|
+
* Normalize a title/goal string for grouping:
|
|
76
|
+
* lowercase, collapse whitespace, strip common filler words.
|
|
77
|
+
*/
|
|
78
|
+
function normalizeTitle(title) {
|
|
79
|
+
return title
|
|
80
|
+
.toLowerCase()
|
|
81
|
+
.replace(/[^a-z0-9\s]+/g, ' ')
|
|
82
|
+
.replace(/\s+/g, ' ')
|
|
83
|
+
.trim();
|
|
84
|
+
}
|
|
85
|
+
/** Normalize project key (null → '' for grouping). */
|
|
86
|
+
function projectKey(project) {
|
|
87
|
+
return (project ?? '').toLowerCase().trim();
|
|
88
|
+
}
|
|
89
|
+
// ---------------------------------------------------------------------------
|
|
90
|
+
// Hub JSONL I/O helpers
|
|
91
|
+
// ---------------------------------------------------------------------------
|
|
92
|
+
/** JSON.parse that returns null on any error. */
|
|
93
|
+
function safeParseJson(text) {
|
|
94
|
+
try {
|
|
95
|
+
return JSON.parse(text);
|
|
96
|
+
}
|
|
97
|
+
catch {
|
|
98
|
+
return null;
|
|
99
|
+
}
|
|
100
|
+
}
|
|
101
|
+
/**
|
|
102
|
+
* Load hub entries directly from hub.jsonl.
|
|
103
|
+
*
|
|
104
|
+
* Parses and field-validates up to CONSOLIDATE_MAX_ENTRIES objects for merging.
|
|
105
|
+
* Every other non-empty line (parse failures, missing-field lines, and any
|
|
106
|
+
* lines beyond the merge cap) is captured verbatim in `preservedLines` so the
|
|
107
|
+
* caller can round-trip them back into the rewritten store without loss.
|
|
108
|
+
*/
|
|
109
|
+
function loadHubRaw(storePath) {
|
|
110
|
+
const entries = [];
|
|
111
|
+
const preservedLines = [];
|
|
112
|
+
try {
|
|
113
|
+
if (!fs.existsSync(storePath))
|
|
114
|
+
return { entries, preservedLines };
|
|
115
|
+
const raw = fs.readFileSync(storePath, 'utf8');
|
|
116
|
+
for (const line of raw.split('\n')) {
|
|
117
|
+
const trimmed = line.trim();
|
|
118
|
+
if (!trimmed)
|
|
119
|
+
continue;
|
|
120
|
+
// Beyond the merge cap: preserve verbatim, do NOT parse/merge.
|
|
121
|
+
if (entries.length >= CONSOLIDATE_MAX_ENTRIES) {
|
|
122
|
+
preservedLines.push(trimmed);
|
|
123
|
+
continue;
|
|
124
|
+
}
|
|
125
|
+
const parsed = safeParseJson(trimmed);
|
|
126
|
+
if (typeof parsed !== 'object' || parsed === null) {
|
|
127
|
+
// Unparseable (or non-object) line — preserve verbatim.
|
|
128
|
+
preservedLines.push(trimmed);
|
|
129
|
+
continue;
|
|
130
|
+
}
|
|
131
|
+
const obj = parsed;
|
|
132
|
+
// Must have minimum required fields to take part in merging.
|
|
133
|
+
if (typeof obj['id'] !== 'string' ||
|
|
134
|
+
typeof obj['title'] !== 'string' ||
|
|
135
|
+
typeof obj['text'] !== 'string' ||
|
|
136
|
+
typeof obj['ts'] !== 'string') {
|
|
137
|
+
// Valid JSON but unknown/partial schema — preserve verbatim.
|
|
138
|
+
preservedLines.push(trimmed);
|
|
139
|
+
continue;
|
|
140
|
+
}
|
|
141
|
+
entries.push(obj);
|
|
142
|
+
}
|
|
143
|
+
}
|
|
144
|
+
catch {
|
|
145
|
+
// Return whatever was accumulated so far.
|
|
146
|
+
}
|
|
147
|
+
return { entries, preservedLines };
|
|
148
|
+
}
|
|
149
|
+
/** Cast a raw hub object to GenomeEntry (defensively). */
|
|
150
|
+
function rawToEntry(obj) {
|
|
151
|
+
return {
|
|
152
|
+
id: obj['id'],
|
|
153
|
+
project: typeof obj['project'] === 'string' ? obj['project'] : null,
|
|
154
|
+
source: 'hub',
|
|
155
|
+
title: obj['title'],
|
|
156
|
+
text: obj['text'],
|
|
157
|
+
tags: Array.isArray(obj['tags'])
|
|
158
|
+
? obj['tags'].filter((t) => typeof t === 'string')
|
|
159
|
+
: [],
|
|
160
|
+
ts: obj['ts'],
|
|
161
|
+
};
|
|
162
|
+
}
|
|
163
|
+
/**
|
|
164
|
+
* Merge a group of raw hub objects into one canonical MergedHubEntry.
|
|
165
|
+
*
|
|
166
|
+
* Strategy:
|
|
167
|
+
* - Canonical entry = member with the LONGEST text (most informative).
|
|
168
|
+
* - tags = union of all member tags, sorted and deduped.
|
|
169
|
+
* - firstTs = earliest ts across members.
|
|
170
|
+
* - lastTs = latest ts across members.
|
|
171
|
+
* - mergedCount = total members in this group.
|
|
172
|
+
* - id, title, project, source carried from the canonical member.
|
|
173
|
+
*/
|
|
174
|
+
function mergeGroup(group) {
|
|
175
|
+
// Pick the longest-text member as the canonical base.
|
|
176
|
+
let canonical = group[0];
|
|
177
|
+
let maxLen = typeof canonical['text'] === 'string' ? canonical['text'].length : 0;
|
|
178
|
+
for (let i = 1; i < group.length; i++) {
|
|
179
|
+
const len = typeof group[i]['text'] === 'string' ? group[i]['text'].length : 0;
|
|
180
|
+
if (len > maxLen) {
|
|
181
|
+
maxLen = len;
|
|
182
|
+
canonical = group[i];
|
|
183
|
+
}
|
|
184
|
+
}
|
|
185
|
+
// Collect union tags
|
|
186
|
+
const tagSet = new Set();
|
|
187
|
+
for (const member of group) {
|
|
188
|
+
if (Array.isArray(member['tags'])) {
|
|
189
|
+
for (const t of member['tags']) {
|
|
190
|
+
if (typeof t === 'string' && t.trim())
|
|
191
|
+
tagSet.add(t.trim());
|
|
192
|
+
}
|
|
193
|
+
}
|
|
194
|
+
}
|
|
195
|
+
// Collect timestamps
|
|
196
|
+
const timestamps = group
|
|
197
|
+
.map((m) => (typeof m['ts'] === 'string' ? m['ts'] : ''))
|
|
198
|
+
.filter(Boolean)
|
|
199
|
+
.sort();
|
|
200
|
+
const firstTs = timestamps[0] ?? canonical['ts'];
|
|
201
|
+
const lastTs = timestamps[timestamps.length - 1] ?? canonical['ts'];
|
|
202
|
+
const tags = Array.from(tagSet).sort();
|
|
203
|
+
return {
|
|
204
|
+
// Spread all fields from canonical first so no extended fields are lost.
|
|
205
|
+
...canonical,
|
|
206
|
+
// Then overwrite with our computed/merged values.
|
|
207
|
+
id: canonical['id'],
|
|
208
|
+
project: typeof canonical['project'] === 'string' ? canonical['project'] : null,
|
|
209
|
+
source: 'hub',
|
|
210
|
+
title: canonical['title'],
|
|
211
|
+
text: canonical['text'],
|
|
212
|
+
tags,
|
|
213
|
+
ts: lastTs, // canonical ts = most recent (for sort/display purposes)
|
|
214
|
+
mergedCount: group.length,
|
|
215
|
+
firstTs,
|
|
216
|
+
lastTs,
|
|
217
|
+
};
|
|
218
|
+
}
|
|
219
|
+
// ---------------------------------------------------------------------------
|
|
220
|
+
// Union-Find for grouping
|
|
221
|
+
// ---------------------------------------------------------------------------
|
|
222
|
+
/** Simple Union-Find to cluster near-duplicate entries. */
|
|
223
|
+
class UnionFind {
|
|
224
|
+
parent;
|
|
225
|
+
rank;
|
|
226
|
+
constructor(n) {
|
|
227
|
+
this.parent = Array.from({ length: n }, (_, i) => i);
|
|
228
|
+
this.rank = new Array(n).fill(0);
|
|
229
|
+
}
|
|
230
|
+
find(x) {
|
|
231
|
+
while (this.parent[x] !== x) {
|
|
232
|
+
this.parent[x] = this.parent[this.parent[x]]; // path compression
|
|
233
|
+
x = this.parent[x];
|
|
234
|
+
}
|
|
235
|
+
return x;
|
|
236
|
+
}
|
|
237
|
+
union(x, y) {
|
|
238
|
+
const rx = this.find(x);
|
|
239
|
+
const ry = this.find(y);
|
|
240
|
+
if (rx === ry)
|
|
241
|
+
return;
|
|
242
|
+
if (this.rank[rx] < this.rank[ry]) {
|
|
243
|
+
this.parent[rx] = ry;
|
|
244
|
+
}
|
|
245
|
+
else if (this.rank[rx] > this.rank[ry]) {
|
|
246
|
+
this.parent[ry] = rx;
|
|
247
|
+
}
|
|
248
|
+
else {
|
|
249
|
+
this.parent[ry] = rx;
|
|
250
|
+
this.rank[rx]++;
|
|
251
|
+
}
|
|
252
|
+
}
|
|
253
|
+
}
|
|
254
|
+
// ---------------------------------------------------------------------------
|
|
255
|
+
// Main export
|
|
256
|
+
// ---------------------------------------------------------------------------
|
|
257
|
+
/**
|
|
258
|
+
* Consolidate near-duplicate entries in hub.jsonl.
|
|
259
|
+
*
|
|
260
|
+
* Steps:
|
|
261
|
+
* 1. Read hub.jsonl entries.
|
|
262
|
+
* 2. Write a timestamped backup (FIRST — before any mutation).
|
|
263
|
+
* 3. Group entries: same [project × normalized-title] bucket first (cheap),
|
|
264
|
+
* then token-overlap within each bucket (Jaccard ≥ OVERLAP_THRESHOLD).
|
|
265
|
+
* 4. Merge each group into a single canonical entry (longest text + union
|
|
266
|
+
* tags + provenance fields: mergedCount, firstTs, lastTs).
|
|
267
|
+
* 5. Rewrite hub.jsonl with merged + un-merged entries.
|
|
268
|
+
* 6. Return { before, after, merged, backupPath }.
|
|
269
|
+
*
|
|
270
|
+
* Returns merged:0 / before===after when nothing to merge (backup still written).
|
|
271
|
+
* Never throws.
|
|
272
|
+
*/
|
|
273
|
+
export async function consolidateGenome(_cfg) {
|
|
274
|
+
const storePath = hubStorePath();
|
|
275
|
+
// ISO-safe timestamp for the backup suffix (colons replaced with dashes)
|
|
276
|
+
const tsSuffix = new Date().toISOString().replace(/[:.]/g, '-');
|
|
277
|
+
const backupPath = `${storePath}.bak-${tsSuffix}`;
|
|
278
|
+
// Fallback result in case of early error
|
|
279
|
+
const fallback = (before) => ({
|
|
280
|
+
before,
|
|
281
|
+
after: before,
|
|
282
|
+
merged: 0,
|
|
283
|
+
backupPath,
|
|
284
|
+
});
|
|
285
|
+
let rawEntries = [];
|
|
286
|
+
let preservedLines = [];
|
|
287
|
+
try {
|
|
288
|
+
const loaded = loadHubRaw(storePath);
|
|
289
|
+
rawEntries = loaded.entries;
|
|
290
|
+
preservedLines = loaded.preservedLines;
|
|
291
|
+
}
|
|
292
|
+
catch {
|
|
293
|
+
return fallback(0);
|
|
294
|
+
}
|
|
295
|
+
// `before` counts EVERY non-empty line in the store (mergeable entries plus
|
|
296
|
+
// preserved lines), so the rewrite can never report fewer lines than existed.
|
|
297
|
+
const before = rawEntries.length + preservedLines.length;
|
|
298
|
+
// Step 2: Write backup FIRST before any mutation.
|
|
299
|
+
// If the store doesn't exist yet, there is nothing to back up or consolidate.
|
|
300
|
+
if (before === 0) {
|
|
301
|
+
return { before: 0, after: 0, merged: 0, backupPath };
|
|
302
|
+
}
|
|
303
|
+
try {
|
|
304
|
+
// Read raw bytes to preserve any lines we skipped during parsing (malformed, etc.)
|
|
305
|
+
const rawBytes = fs.existsSync(storePath) ? fs.readFileSync(storePath) : Buffer.alloc(0);
|
|
306
|
+
fs.writeFileSync(backupPath, rawBytes);
|
|
307
|
+
}
|
|
308
|
+
catch {
|
|
309
|
+
// Cannot write backup — abort to protect NO DATA LOSS guarantee.
|
|
310
|
+
return fallback(before);
|
|
311
|
+
}
|
|
312
|
+
// Step 3: Build groups via Union-Find.
|
|
313
|
+
// Phase A: cheap bucket by [projectKey × normalizedTitle]
|
|
314
|
+
const buckets = new Map();
|
|
315
|
+
for (let i = 0; i < rawEntries.length; i++) {
|
|
316
|
+
const entry = rawEntries[i];
|
|
317
|
+
const proj = projectKey(typeof entry['project'] === 'string' ? entry['project'] : null);
|
|
318
|
+
const title = normalizeTitle(typeof entry['title'] === 'string' ? entry['title'] : '');
|
|
319
|
+
const bucketKey = `${proj}\x00${title}`;
|
|
320
|
+
const bucket = buckets.get(bucketKey);
|
|
321
|
+
if (bucket) {
|
|
322
|
+
bucket.push(i);
|
|
323
|
+
}
|
|
324
|
+
else {
|
|
325
|
+
buckets.set(bucketKey, [i]);
|
|
326
|
+
}
|
|
327
|
+
}
|
|
328
|
+
// Phase B: token-overlap within each bucket (bounded comparisons)
|
|
329
|
+
const uf = new UnionFind(rawEntries.length);
|
|
330
|
+
// Pre-compute token sets once
|
|
331
|
+
const tokenSets = rawEntries.map((obj) => {
|
|
332
|
+
try {
|
|
333
|
+
return entryTokenSet(rawToEntry(obj));
|
|
334
|
+
}
|
|
335
|
+
catch {
|
|
336
|
+
return null;
|
|
337
|
+
}
|
|
338
|
+
});
|
|
339
|
+
let comparisons = 0;
|
|
340
|
+
for (const indices of buckets.values()) {
|
|
341
|
+
if (indices.length < 2)
|
|
342
|
+
continue; // singleton bucket — nothing to compare
|
|
343
|
+
for (let a = 0; a < indices.length - 1; a++) {
|
|
344
|
+
for (let b = a + 1; b < indices.length; b++) {
|
|
345
|
+
if (comparisons >= MAX_COMPARISONS)
|
|
346
|
+
break;
|
|
347
|
+
comparisons++;
|
|
348
|
+
const ia = indices[a];
|
|
349
|
+
const ib = indices[b];
|
|
350
|
+
const sa = tokenSets[ia];
|
|
351
|
+
const sb = tokenSets[ib];
|
|
352
|
+
if (!sa || !sb)
|
|
353
|
+
continue;
|
|
354
|
+
const sim = jaccardSimilarity(sa, sb);
|
|
355
|
+
if (sim >= OVERLAP_THRESHOLD) {
|
|
356
|
+
uf.union(ia, ib);
|
|
357
|
+
}
|
|
358
|
+
}
|
|
359
|
+
if (comparisons >= MAX_COMPARISONS)
|
|
360
|
+
break;
|
|
361
|
+
}
|
|
362
|
+
}
|
|
363
|
+
// Step 4: Collect groups by their Union-Find root.
|
|
364
|
+
const groups = new Map();
|
|
365
|
+
for (let i = 0; i < rawEntries.length; i++) {
|
|
366
|
+
const root = uf.find(i);
|
|
367
|
+
const group = groups.get(root);
|
|
368
|
+
if (group) {
|
|
369
|
+
group.push(i);
|
|
370
|
+
}
|
|
371
|
+
else {
|
|
372
|
+
groups.set(root, [i]);
|
|
373
|
+
}
|
|
374
|
+
}
|
|
375
|
+
// Step 5: Build output entries.
|
|
376
|
+
const outputEntries = [];
|
|
377
|
+
let mergedCount = 0;
|
|
378
|
+
for (const [, memberIndices] of groups) {
|
|
379
|
+
if (memberIndices.length === 1) {
|
|
380
|
+
// No merge needed — preserve as-is (do NOT overwrite with MergedHubEntry shape).
|
|
381
|
+
outputEntries.push(rawEntries[memberIndices[0]]);
|
|
382
|
+
}
|
|
383
|
+
else {
|
|
384
|
+
// Multiple entries in this group — merge them.
|
|
385
|
+
const group = memberIndices.map((i) => rawEntries[i]);
|
|
386
|
+
const merged = mergeGroup(group);
|
|
387
|
+
outputEntries.push(merged);
|
|
388
|
+
// mergedCount tracks how many entries were folded AWAY (group.length - 1 survivals = 1).
|
|
389
|
+
mergedCount += group.length - 1;
|
|
390
|
+
}
|
|
391
|
+
}
|
|
392
|
+
// `after` counts the merged/unmerged entries PLUS every preserved line that
|
|
393
|
+
// was carried through untouched — so the rewritten store never has fewer
|
|
394
|
+
// lines than `before` minus the entries actually folded away by merging.
|
|
395
|
+
const after = outputEntries.length + preservedLines.length;
|
|
396
|
+
// Step 6: Rewrite hub.jsonl with merged entries.
|
|
397
|
+
// Preserve insertion order (sort by ts ascending so the file is chronological).
|
|
398
|
+
outputEntries.sort((a, b) => {
|
|
399
|
+
const ta = typeof a['ts'] === 'string' ? a['ts'] : '';
|
|
400
|
+
const tb = typeof b['ts'] === 'string' ? b['ts'] : '';
|
|
401
|
+
if (ta < tb)
|
|
402
|
+
return -1;
|
|
403
|
+
if (ta > tb)
|
|
404
|
+
return 1;
|
|
405
|
+
return 0;
|
|
406
|
+
});
|
|
407
|
+
try {
|
|
408
|
+
// Re-emit preserved (un-parseable / unknown-schema / over-cap) lines
|
|
409
|
+
// verbatim so consolidation never removes a line it could not merge.
|
|
410
|
+
const mergedLines = outputEntries.map((e) => JSON.stringify(e));
|
|
411
|
+
const allLines = [...mergedLines, ...preservedLines];
|
|
412
|
+
const lines = allLines.join('\n') + '\n';
|
|
413
|
+
// Write to a temp file first, then atomically rename to avoid partial-write corruption.
|
|
414
|
+
const tmpPath = `${storePath}.tmp-${tsSuffix}`;
|
|
415
|
+
fs.writeFileSync(tmpPath, lines, 'utf8');
|
|
416
|
+
fs.renameSync(tmpPath, storePath);
|
|
417
|
+
}
|
|
418
|
+
catch {
|
|
419
|
+
// Rewrite failed — the backup is intact; hub.jsonl is unchanged (or may
|
|
420
|
+
// be partially written to the temp path which is separate).
|
|
421
|
+
// Return a result indicating no change so callers know consolidation didn't apply.
|
|
422
|
+
return fallback(before);
|
|
423
|
+
}
|
|
424
|
+
return { before, after, merged: mergedCount, backupPath };
|
|
425
|
+
}
|
|
426
|
+
//# sourceMappingURL=consolidate.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"consolidate.js","sourceRoot":"","sources":["../../../src/core/genome/consolidate.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* export.ts — Genome export for M16 (no lock-in).
|
|
3
|
+
*
|
|
4
|
+
* Loads the full aggregated genome and writes it to a destination file as
|
|
5
|
+
* either portable JSON (array of GenomeEntry) or Markdown (one section per
|
|
6
|
+
* entry). READ-ONLY on the genome — never mutates hub.jsonl or any source.
|
|
7
|
+
*
|
|
8
|
+
* GUARDRAILS:
|
|
9
|
+
* - Read-only: genome sources are never modified.
|
|
10
|
+
* - Never throws: all errors are caught; ok:false returned on failure.
|
|
11
|
+
* - No lock-in: JSON output is a plain array; Markdown is human-readable.
|
|
12
|
+
* - Local-only: no network calls; no new runtime deps.
|
|
13
|
+
*/
|
|
14
|
+
import type { AshlrConfig } from '../types.js';
|
|
15
|
+
/**
|
|
16
|
+
* Export the full aggregated genome to `dest` in the requested format.
|
|
17
|
+
*
|
|
18
|
+
* - `'json'`: pretty-printed JSON array of GenomeEntry objects.
|
|
19
|
+
* - `'md'`: Markdown document with one section per entry.
|
|
20
|
+
*
|
|
21
|
+
* Creates the destination directory if it does not exist.
|
|
22
|
+
* Returns `{ ok: true, count, path }` on success.
|
|
23
|
+
* Returns `{ ok: false, count: 0, path: dest }` on any error — never throws.
|
|
24
|
+
*/
|
|
25
|
+
export declare function exportGenome(cfg: AshlrConfig, dest: string, format: 'json' | 'md'): {
|
|
26
|
+
ok: boolean;
|
|
27
|
+
count: number;
|
|
28
|
+
path: string;
|
|
29
|
+
};
|
|
@@ -0,0 +1,102 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* export.ts — Genome export for M16 (no lock-in).
|
|
3
|
+
*
|
|
4
|
+
* Loads the full aggregated genome and writes it to a destination file as
|
|
5
|
+
* either portable JSON (array of GenomeEntry) or Markdown (one section per
|
|
6
|
+
* entry). READ-ONLY on the genome — never mutates hub.jsonl or any source.
|
|
7
|
+
*
|
|
8
|
+
* GUARDRAILS:
|
|
9
|
+
* - Read-only: genome sources are never modified.
|
|
10
|
+
* - Never throws: all errors are caught; ok:false returned on failure.
|
|
11
|
+
* - No lock-in: JSON output is a plain array; Markdown is human-readable.
|
|
12
|
+
* - Local-only: no network calls; no new runtime deps.
|
|
13
|
+
*/
|
|
14
|
+
import fs from 'node:fs';
|
|
15
|
+
import path from 'node:path';
|
|
16
|
+
import { loadGenome } from './store.js';
|
|
17
|
+
// ---------------------------------------------------------------------------
|
|
18
|
+
// Markdown rendering
|
|
19
|
+
// ---------------------------------------------------------------------------
|
|
20
|
+
/**
|
|
21
|
+
* Render a single GenomeEntry as a Markdown section.
|
|
22
|
+
*
|
|
23
|
+
* Format:
|
|
24
|
+
* ## <title>
|
|
25
|
+
*
|
|
26
|
+
* **Project:** <project> **Tags:** tag1, tag2 **Date:** <ts>
|
|
27
|
+
*
|
|
28
|
+
* <text>
|
|
29
|
+
*
|
|
30
|
+
* ---
|
|
31
|
+
*/
|
|
32
|
+
function entryToMarkdown(entry) {
|
|
33
|
+
const lines = [];
|
|
34
|
+
lines.push(`## ${entry.title}`);
|
|
35
|
+
lines.push('');
|
|
36
|
+
const meta = [];
|
|
37
|
+
if (entry.project)
|
|
38
|
+
meta.push(`**Project:** ${entry.project}`);
|
|
39
|
+
if (entry.tags.length > 0)
|
|
40
|
+
meta.push(`**Tags:** ${entry.tags.join(', ')}`);
|
|
41
|
+
meta.push(`**Date:** ${entry.ts}`);
|
|
42
|
+
meta.push(`**Source:** ${entry.source}`);
|
|
43
|
+
lines.push(meta.join(' '));
|
|
44
|
+
lines.push('');
|
|
45
|
+
lines.push(entry.text);
|
|
46
|
+
lines.push('');
|
|
47
|
+
lines.push('---');
|
|
48
|
+
lines.push('');
|
|
49
|
+
return lines.join('\n');
|
|
50
|
+
}
|
|
51
|
+
/**
|
|
52
|
+
* Render all entries as a Markdown document.
|
|
53
|
+
*/
|
|
54
|
+
function entriesToMarkdown(entries) {
|
|
55
|
+
const header = [
|
|
56
|
+
'# Genome Export',
|
|
57
|
+
'',
|
|
58
|
+
`Exported ${entries.length} entr${entries.length === 1 ? 'y' : 'ies'} from the ashlr genome.`,
|
|
59
|
+
'',
|
|
60
|
+
'---',
|
|
61
|
+
'',
|
|
62
|
+
].join('\n');
|
|
63
|
+
return header + entries.map(entryToMarkdown).join('');
|
|
64
|
+
}
|
|
65
|
+
// ---------------------------------------------------------------------------
|
|
66
|
+
// Public: exportGenome
|
|
67
|
+
// ---------------------------------------------------------------------------
|
|
68
|
+
/**
|
|
69
|
+
* Export the full aggregated genome to `dest` in the requested format.
|
|
70
|
+
*
|
|
71
|
+
* - `'json'`: pretty-printed JSON array of GenomeEntry objects.
|
|
72
|
+
* - `'md'`: Markdown document with one section per entry.
|
|
73
|
+
*
|
|
74
|
+
* Creates the destination directory if it does not exist.
|
|
75
|
+
* Returns `{ ok: true, count, path }` on success.
|
|
76
|
+
* Returns `{ ok: false, count: 0, path: dest }` on any error — never throws.
|
|
77
|
+
*/
|
|
78
|
+
export function exportGenome(cfg, dest, format) {
|
|
79
|
+
const absPath = path.resolve(dest);
|
|
80
|
+
try {
|
|
81
|
+
// Load the genome (never throws).
|
|
82
|
+
const entries = loadGenome(cfg);
|
|
83
|
+
// Ensure destination directory exists.
|
|
84
|
+
const dir = path.dirname(absPath);
|
|
85
|
+
fs.mkdirSync(dir, { recursive: true });
|
|
86
|
+
// Render output.
|
|
87
|
+
let content;
|
|
88
|
+
if (format === 'json') {
|
|
89
|
+
content = JSON.stringify(entries, null, 2) + '\n';
|
|
90
|
+
}
|
|
91
|
+
else {
|
|
92
|
+
content = entriesToMarkdown(entries);
|
|
93
|
+
}
|
|
94
|
+
// Write (overwrite if exists — this is an export, not an append).
|
|
95
|
+
fs.writeFileSync(absPath, content, 'utf8');
|
|
96
|
+
return { ok: true, count: entries.length, path: absPath };
|
|
97
|
+
}
|
|
98
|
+
catch {
|
|
99
|
+
return { ok: false, count: 0, path: absPath };
|
|
100
|
+
}
|
|
101
|
+
}
|
|
102
|
+
//# sourceMappingURL=export.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"export.js","sourceRoot":"","sources":["../../../src/core/genome/export.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* playbook.ts — Genome playbook synthesis (M16).
|
|
3
|
+
*
|
|
4
|
+
* Recalls similar past genome entries for a goal and synthesizes a concise
|
|
5
|
+
* "how we've approached this before — what worked / what failed / cost"
|
|
6
|
+
* string using the LOCAL provider. Falls back to a concatenated-recall
|
|
7
|
+
* synthesis on any failure, over-budget condition, or absent provider.
|
|
8
|
+
*
|
|
9
|
+
* Guardrails:
|
|
10
|
+
* - LOCAL-ONLY: no cloud calls; synthesis uses local provider best-effort.
|
|
11
|
+
* - Never throws; always returns a Playbook.
|
|
12
|
+
* - Bounded: synthesis prompt and output are capped; playbookText hard-truncates.
|
|
13
|
+
* - PRIVACY: works only from already-sanitised recall entries (genome never
|
|
14
|
+
* stores secrets/raw payloads per M7/M16 privacy discipline).
|
|
15
|
+
*/
|
|
16
|
+
import type { AshlrConfig, Playbook } from '../types.js';
|
|
17
|
+
/**
|
|
18
|
+
* Build a playbook for `goal` by recalling similar past entries and
|
|
19
|
+
* synthesizing a concise guidance string via the LOCAL provider.
|
|
20
|
+
*
|
|
21
|
+
* Falls back to a concatenated-recall synthesis on any failure, over-budget
|
|
22
|
+
* condition, or when no local provider is reachable.
|
|
23
|
+
*
|
|
24
|
+
* Never throws. Returns `{ goal, entries, synthesis }`.
|
|
25
|
+
*/
|
|
26
|
+
export declare function buildPlaybook(goal: string, cfg: AshlrConfig, opts?: {
|
|
27
|
+
limit?: number;
|
|
28
|
+
}): Promise<Playbook>;
|
|
29
|
+
/**
|
|
30
|
+
* Render a playbook to an injection-ready string capped at `maxChars`.
|
|
31
|
+
* Appends an elision marker when truncated. Pure; never throws.
|
|
32
|
+
*/
|
|
33
|
+
export declare function playbookText(p: Playbook, maxChars: number): string;
|