hippo-memory 1.59.0 → 1.61.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/README.md +1 -1
- package/dist/ablation.js +9 -27
- package/dist/agent-memories/apply.js +4 -1
- package/dist/agent-memories/claude-code.js +1 -1
- package/dist/agent-memories/codex.js +1 -1
- package/dist/agent-memories/gemini.js +1 -1
- package/dist/agent-memories/legacy.js +1 -1
- package/dist/agent-memories/source.js +1 -1
- package/dist/agent-memories/sync.js +8 -3
- package/dist/ambient-store.d.ts +14 -0
- package/dist/ambient-store.js +90 -0
- package/dist/ambient.d.ts +23 -0
- package/dist/ambient.js +72 -50
- package/dist/api/assemble.d.ts +93 -0
- package/dist/api/assemble.js +152 -0
- package/dist/api/audit.d.ts +17 -0
- package/dist/api/audit.js +23 -0
- package/dist/api/auth.d.ts +79 -0
- package/dist/api/auth.js +178 -0
- package/dist/api/context-types.d.ts +105 -0
- package/dist/api/context-types.js +3 -0
- package/dist/api/context.d.ts +31 -0
- package/dist/api/context.js +705 -0
- package/dist/api/dormant.d.ts +30 -0
- package/dist/api/dormant.js +140 -0
- package/dist/api/drill-down.d.ts +84 -0
- package/dist/api/drill-down.js +123 -0
- package/dist/api/forget.d.ts +57 -0
- package/dist/api/forget.js +87 -0
- package/dist/api/goals.d.ts +18 -0
- package/dist/api/goals.js +33 -0
- package/dist/api/learn.d.ts +31 -0
- package/dist/api/learn.js +88 -0
- package/dist/api/outcome.d.ts +61 -0
- package/dist/api/outcome.js +66 -0
- package/dist/api/promote.d.ts +54 -0
- package/dist/api/promote.js +203 -0
- package/dist/api/quarantine.d.ts +24 -0
- package/dist/api/quarantine.js +121 -0
- package/dist/api/recall-types.d.ts +390 -0
- package/dist/api/recall-types.js +3 -0
- package/dist/api/recall.d.ts +36 -0
- package/dist/api/recall.js +634 -0
- package/dist/api/remember.d.ts +35 -0
- package/dist/api/remember.js +43 -0
- package/dist/api/sleep.d.ts +136 -0
- package/dist/api/sleep.js +271 -0
- package/dist/api/tokens.d.ts +26 -0
- package/dist/api/tokens.js +60 -0
- package/dist/api/types.d.ts +56 -0
- package/dist/api/types.js +38 -0
- package/dist/api.d.ts +20 -1260
- package/dist/api.js +25 -2711
- package/dist/audit.d.ts +3 -0
- package/dist/audit.js +7 -3
- package/dist/auth.d.ts +45 -4
- package/dist/auth.js +125 -48
- package/dist/autolearn.js +7 -4
- package/dist/capture/command.d.ts +33 -0
- package/dist/capture/command.js +264 -0
- package/dist/capture/compact.d.ts +44 -0
- package/dist/capture/compact.js +354 -0
- package/dist/capture/extract.d.ts +21 -0
- package/dist/capture/extract.js +464 -0
- package/dist/capture/transcript.d.ts +40 -0
- package/dist/capture/transcript.js +193 -0
- package/dist/capture-error.js +2 -1
- package/dist/churn-git.js +4 -2
- package/dist/cli/audit.d.ts +3 -0
- package/dist/cli/audit.js +159 -0
- package/dist/cli/auth.d.ts +2 -0
- package/dist/cli/auth.js +171 -0
- package/dist/cli/briefs.d.ts +4 -0
- package/dist/cli/briefs.js +435 -0
- package/dist/cli/card.d.ts +3 -0
- package/dist/cli/card.js +333 -0
- package/dist/cli/context.d.ts +15 -0
- package/dist/cli/context.js +366 -0
- package/dist/cli/continuity.d.ts +6 -0
- package/dist/cli/continuity.js +445 -0
- package/dist/cli/curate.d.ts +19 -0
- package/dist/cli/curate.js +555 -0
- package/dist/cli/dag.d.ts +5 -0
- package/dist/cli/dag.js +177 -0
- package/dist/cli/decisions.d.ts +4 -0
- package/dist/cli/decisions.js +528 -0
- package/dist/cli/eval.d.ts +5 -0
- package/dist/cli/eval.js +213 -0
- package/dist/cli/explain.d.ts +4 -0
- package/dist/cli/explain.js +150 -0
- package/dist/cli/goals.d.ts +2 -0
- package/dist/cli/goals.js +196 -0
- package/dist/cli/hook-blocks.d.ts +18 -0
- package/dist/cli/hook-blocks.js +233 -0
- package/dist/cli/init.d.ts +2 -0
- package/dist/cli/init.js +305 -0
- package/dist/cli/maintenance.d.ts +4 -0
- package/dist/cli/maintenance.js +179 -0
- package/dist/cli/playbooks.d.ts +4 -0
- package/dist/cli/playbooks.js +556 -0
- package/dist/cli/projects.js +1 -1
- package/dist/cli/recall.d.ts +7 -0
- package/dist/cli/recall.js +597 -0
- package/dist/cli/remember.d.ts +5 -0
- package/dist/cli/remember.js +442 -0
- package/dist/cli/serve.d.ts +5 -0
- package/dist/cli/serve.js +40 -0
- package/dist/cli/session-hooks.d.ts +29 -0
- package/dist/cli/session-hooks.js +637 -0
- package/dist/cli/setup.d.ts +4 -0
- package/dist/cli/setup.js +376 -0
- package/dist/cli/shared.d.ts +15 -19
- package/dist/cli/shared.js +50 -341
- package/dist/cli/slack.d.ts +2 -0
- package/dist/cli/slack.js +171 -0
- package/dist/cli/status.d.ts +18 -0
- package/dist/cli/status.js +400 -0
- package/dist/cli/transfer.d.ts +10 -0
- package/dist/cli/transfer.js +438 -0
- package/dist/cli/usage.d.ts +85 -0
- package/dist/cli/usage.js +741 -0
- package/dist/cli.d.ts +319 -13
- package/dist/cli.js +436 -8580
- package/dist/client.js +15 -8
- package/dist/compaction-record.js +12 -9
- package/dist/config.js +12 -11
- package/dist/connectors/github/backfill.js +94 -87
- package/dist/connectors/github/cli-impl.js +5 -3
- package/dist/connectors/github/dlq.js +67 -54
- package/dist/connectors/github/ingest.js +34 -35
- package/dist/connectors/github/tenant-routing.js +3 -2
- package/dist/connectors/github/webhook.js +135 -216
- package/dist/connectors/slack/dlq.js +49 -61
- package/dist/connectors/slack/ingest.js +55 -48
- package/dist/connectors/slack/tenant-routing.js +4 -3
- package/dist/connectors/slack/webhook.js +72 -74
- package/dist/consolidate/conflicts.d.ts +10 -0
- package/dist/consolidate/conflicts.js +178 -0
- package/dist/consolidate/decay.d.ts +12 -0
- package/dist/consolidate/decay.js +145 -0
- package/dist/consolidate/llm-passes.d.ts +3 -0
- package/dist/consolidate/llm-passes.js +141 -0
- package/dist/consolidate/merge.d.ts +7 -0
- package/dist/consolidate/merge.js +251 -0
- package/dist/consolidate/physics-pass.d.ts +3 -0
- package/dist/consolidate/physics-pass.js +60 -0
- package/dist/consolidate/run.d.ts +69 -0
- package/dist/consolidate/run.js +76 -0
- package/dist/consolidate/sleep.d.ts +18 -0
- package/dist/consolidate/sleep.js +209 -0
- package/dist/consolidate/traces.d.ts +4 -0
- package/dist/consolidate/traces.js +178 -0
- package/dist/context-auto.js +7 -11
- package/dist/context-render.d.ts +1 -1
- package/dist/context-render.js +1 -1
- package/dist/customer-notes.d.ts +3 -0
- package/dist/customer-notes.js +6 -4
- package/dist/dag.js +13 -12
- package/dist/dashboard-actions.d.ts +20 -0
- package/dist/dashboard-actions.js +88 -0
- package/dist/dashboard-params.d.ts +45 -0
- package/dist/dashboard-params.js +127 -0
- package/dist/dashboard-queries.d.ts +15 -0
- package/dist/dashboard-queries.js +355 -0
- package/dist/dashboard-snapshot.d.ts +138 -0
- package/dist/dashboard-snapshot.js +308 -0
- package/dist/dashboard-types.d.ts +163 -0
- package/dist/dashboard-types.js +3 -0
- package/dist/dashboard.d.ts +6 -7
- package/dist/dashboard.js +231 -203
- package/dist/db/busy.d.ts +5 -0
- package/dist/db/busy.js +24 -0
- package/dist/db/continuity.d.ts +5 -0
- package/dist/db/continuity.js +145 -0
- package/dist/db/meta.d.ts +8 -0
- package/dist/db/meta.js +35 -0
- package/dist/db/migrate.d.ts +9 -0
- package/dist/db/migrate.js +138 -0
- package/dist/db/migrations/index.d.ts +5 -0
- package/dist/db/migrations/index.js +109 -0
- package/dist/db/migrations/types.d.ts +14 -0
- package/dist/db/migrations/types.js +2 -0
- package/dist/db/migrations/v01.d.ts +3 -0
- package/dist/db/migrations/v01.js +38 -0
- package/dist/db/migrations/v02.d.ts +3 -0
- package/dist/db/migrations/v02.js +21 -0
- package/dist/db/migrations/v03.d.ts +3 -0
- package/dist/db/migrations/v03.js +22 -0
- package/dist/db/migrations/v04.d.ts +3 -0
- package/dist/db/migrations/v04.js +28 -0
- package/dist/db/migrations/v05.d.ts +3 -0
- package/dist/db/migrations/v05.js +21 -0
- package/dist/db/migrations/v06.d.ts +3 -0
- package/dist/db/migrations/v06.js +25 -0
- package/dist/db/migrations/v07.d.ts +3 -0
- package/dist/db/migrations/v07.js +13 -0
- package/dist/db/migrations/v08.d.ts +3 -0
- package/dist/db/migrations/v08.js +8 -0
- package/dist/db/migrations/v09.d.ts +3 -0
- package/dist/db/migrations/v09.js +13 -0
- package/dist/db/migrations/v10.d.ts +3 -0
- package/dist/db/migrations/v10.js +17 -0
- package/dist/db/migrations/v11.d.ts +3 -0
- package/dist/db/migrations/v11.js +15 -0
- package/dist/db/migrations/v12.d.ts +3 -0
- package/dist/db/migrations/v12.js +11 -0
- package/dist/db/migrations/v13.d.ts +3 -0
- package/dist/db/migrations/v13.js +15 -0
- package/dist/db/migrations/v14.d.ts +3 -0
- package/dist/db/migrations/v14.js +66 -0
- package/dist/db/migrations/v15.d.ts +3 -0
- package/dist/db/migrations/v15.js +42 -0
- package/dist/db/migrations/v16.d.ts +3 -0
- package/dist/db/migrations/v16.js +61 -0
- package/dist/db/migrations/v17.d.ts +3 -0
- package/dist/db/migrations/v17.js +46 -0
- package/dist/db/migrations/v18.d.ts +3 -0
- package/dist/db/migrations/v18.js +60 -0
- package/dist/db/migrations/v19.d.ts +3 -0
- package/dist/db/migrations/v19.js +28 -0
- package/dist/db/migrations/v20.d.ts +3 -0
- package/dist/db/migrations/v20.js +42 -0
- package/dist/db/migrations/v21.d.ts +3 -0
- package/dist/db/migrations/v21.js +16 -0
- package/dist/db/migrations/v22.d.ts +3 -0
- package/dist/db/migrations/v22.js +82 -0
- package/dist/db/migrations/v23.d.ts +3 -0
- package/dist/db/migrations/v23.js +48 -0
- package/dist/db/migrations/v24.d.ts +3 -0
- package/dist/db/migrations/v24.js +72 -0
- package/dist/db/migrations/v25.d.ts +3 -0
- package/dist/db/migrations/v25.js +46 -0
- package/dist/db/migrations/v26.d.ts +3 -0
- package/dist/db/migrations/v26.js +23 -0
- package/dist/db/migrations/v27.d.ts +3 -0
- package/dist/db/migrations/v27.js +57 -0
- package/dist/db/migrations/v28.d.ts +3 -0
- package/dist/db/migrations/v28.js +38 -0
- package/dist/db/migrations/v29.d.ts +3 -0
- package/dist/db/migrations/v29.js +78 -0
- package/dist/db/migrations/v30.d.ts +3 -0
- package/dist/db/migrations/v30.js +92 -0
- package/dist/db/migrations/v31.d.ts +3 -0
- package/dist/db/migrations/v31.js +74 -0
- package/dist/db/migrations/v32.d.ts +3 -0
- package/dist/db/migrations/v32.js +102 -0
- package/dist/db/migrations/v33.d.ts +3 -0
- package/dist/db/migrations/v33.js +104 -0
- package/dist/db/migrations/v34.d.ts +3 -0
- package/dist/db/migrations/v34.js +93 -0
- package/dist/db/migrations/v35.d.ts +3 -0
- package/dist/db/migrations/v35.js +98 -0
- package/dist/db/migrations/v36.d.ts +3 -0
- package/dist/db/migrations/v36.js +98 -0
- package/dist/db/migrations/v37.d.ts +3 -0
- package/dist/db/migrations/v37.js +219 -0
- package/dist/db/migrations/v38.d.ts +3 -0
- package/dist/db/migrations/v38.js +277 -0
- package/dist/db/migrations/v39.d.ts +3 -0
- package/dist/db/migrations/v39.js +59 -0
- package/dist/db/migrations/v40.d.ts +3 -0
- package/dist/db/migrations/v40.js +74 -0
- package/dist/db/migrations/v41.d.ts +3 -0
- package/dist/db/migrations/v41.js +43 -0
- package/dist/db/migrations/v42.d.ts +3 -0
- package/dist/db/migrations/v42.js +41 -0
- package/dist/db/migrations/v43.d.ts +3 -0
- package/dist/db/migrations/v43.js +67 -0
- package/dist/db/migrations/v44.d.ts +3 -0
- package/dist/db/migrations/v44.js +28 -0
- package/dist/db/migrations/v45.d.ts +3 -0
- package/dist/db/migrations/v45.js +30 -0
- package/dist/db/migrations/v46.d.ts +3 -0
- package/dist/db/migrations/v46.js +25 -0
- package/dist/db/migrations/v47.d.ts +3 -0
- package/dist/db/migrations/v47.js +17 -0
- package/dist/db/migrations/v48.d.ts +3 -0
- package/dist/db/migrations/v48.js +10 -0
- package/dist/db/migrations/v49.d.ts +3 -0
- package/dist/db/migrations/v49.js +31 -0
- package/dist/db/migrations/v50.d.ts +3 -0
- package/dist/db/migrations/v50.js +67 -0
- package/dist/db/migrations/v51.d.ts +3 -0
- package/dist/db/migrations/v51.js +14 -0
- package/dist/db/migrations/v52.d.ts +3 -0
- package/dist/db/migrations/v52.js +7 -0
- package/dist/db/open.d.ts +23 -0
- package/dist/db/open.js +146 -0
- package/dist/db/sqlite.d.ts +21 -0
- package/dist/db/sqlite.js +8 -0
- package/dist/db/tables.d.ts +7 -0
- package/dist/db/tables.js +38 -0
- package/dist/db.d.ts +6 -46
- package/dist/db.js +5 -3036
- package/dist/decisions.d.ts +4 -1
- package/dist/decisions.js +9 -7
- package/dist/dedupe.js +3 -2
- package/dist/delivery-recorder.js +5 -1
- package/dist/doctor.js +4 -3
- package/dist/dormant.js +1 -0
- package/dist/embedding-provider.d.ts +1 -1
- package/dist/embedding-provider.js +7 -5
- package/dist/embeddings.d.ts +9 -52
- package/dist/embeddings.js +47 -298
- package/dist/env.d.ts +75 -0
- package/dist/env.js +119 -0
- package/dist/eval-suite.js +1 -1
- package/dist/eval.js +2 -2
- package/dist/extract.js +5 -4
- package/dist/gated-write.js +3 -1
- package/dist/goals.d.ts +3 -1
- package/dist/goals.js +18 -0
- package/dist/graph/read.d.ts +73 -0
- package/dist/graph/read.js +325 -0
- package/dist/graph/rows.d.ts +45 -0
- package/dist/graph/rows.js +51 -0
- package/dist/graph/types.d.ts +83 -0
- package/dist/graph/types.js +11 -0
- package/dist/graph/write.d.ts +93 -0
- package/dist/{graph.js → graph/write.js} +8 -391
- package/dist/graph-extract.js +2 -1
- package/dist/graph-recall.d.ts +1 -1
- package/dist/graph-recall.js +2 -2
- package/dist/graph-stream.js +1 -1
- package/dist/graph-view.d.ts +1 -1
- package/dist/graph-view.js +1 -1
- package/dist/half-life-migration.d.ts +1 -1
- package/dist/half-life-migration.js +2 -1
- package/dist/handoff.js +3 -0
- package/dist/hooks/codex-session.d.ts +8 -0
- package/dist/hooks/codex-session.js +76 -0
- package/dist/hooks/codex-wrapper.d.ts +55 -0
- package/dist/hooks/codex-wrapper.js +288 -0
- package/dist/hooks/json-hooks.d.ts +63 -0
- package/dist/hooks/json-hooks.js +356 -0
- package/dist/hooks/opencode.d.ts +50 -0
- package/dist/hooks/opencode.js +202 -0
- package/dist/hooks/shared.d.ts +54 -0
- package/dist/hooks/shared.js +77 -0
- package/dist/http-retry.d.ts +2 -0
- package/dist/http-retry.js +4 -3
- package/dist/http-util.d.ts +3 -0
- package/dist/http-util.js +10 -0
- package/dist/{importers.d.ts → importers/core.d.ts} +13 -17
- package/dist/importers/core.js +141 -0
- package/dist/importers/markdown-parse.d.ts +41 -0
- package/dist/importers/markdown-parse.js +132 -0
- package/dist/importers/markdown.d.ts +3 -0
- package/dist/importers/markdown.js +92 -0
- package/dist/importers/sources.d.ts +7 -0
- package/dist/importers/sources.js +229 -0
- package/dist/importers/vault.d.ts +11 -0
- package/dist/importers/vault.js +352 -0
- package/dist/incidents.d.ts +3 -0
- package/dist/incidents.js +8 -5
- package/dist/index.d.ts +25 -6
- package/dist/index.js +23 -6
- package/dist/invalidation.js +2 -1
- package/dist/judgment.js +7 -3
- package/dist/keyset.d.ts +13 -0
- package/dist/keyset.js +8 -0
- package/dist/local-embedding.d.ts +13 -0
- package/dist/local-embedding.js +165 -0
- package/dist/log.d.ts +7 -0
- package/dist/log.js +19 -1
- package/dist/mcp/admin-tools.d.ts +8 -0
- package/dist/mcp/admin-tools.js +116 -0
- package/dist/mcp/format.d.ts +27 -0
- package/dist/mcp/format.js +135 -0
- package/dist/mcp/memory-tools.d.ts +5 -0
- package/dist/mcp/memory-tools.js +83 -0
- package/dist/mcp/protocol.d.ts +83 -0
- package/dist/mcp/protocol.js +55 -0
- package/dist/mcp/recall-tools.d.ts +6 -0
- package/dist/mcp/recall-tools.js +320 -0
- package/dist/mcp/request.d.ts +10 -0
- package/dist/mcp/request.js +163 -0
- package/dist/mcp/server.d.ts +4 -70
- package/dist/mcp/server.js +8 -1172
- package/dist/mcp/session-state.d.ts +11 -0
- package/dist/mcp/session-state.js +28 -0
- package/dist/mcp/stdio.d.ts +8 -0
- package/dist/mcp/stdio.js +79 -0
- package/dist/mcp/tools.d.ts +11 -0
- package/dist/mcp/tools.js +247 -0
- package/dist/memory.d.ts +8 -3
- package/dist/memory.js +27 -1
- package/dist/multihop.d.ts +1 -1
- package/dist/multihop.js +2 -1
- package/dist/owner-validation.js +2 -1
- package/dist/physics-state.js +10 -7
- package/dist/policies.d.ts +3 -0
- package/dist/policies.js +8 -6
- package/dist/postinstall.js +3 -2
- package/dist/predictions/planning-fallacy.d.ts +100 -0
- package/dist/predictions/planning-fallacy.js +190 -0
- package/dist/{predictions.d.ts → predictions/store.d.ts} +7 -102
- package/dist/predictions/store.js +434 -0
- package/dist/processes.d.ts +3 -0
- package/dist/processes.js +8 -5
- package/dist/project-briefs.d.ts +3 -0
- package/dist/project-briefs.js +7 -5
- package/dist/project-identity.d.ts +1 -1
- package/dist/project-identity.js +12 -6
- package/dist/project-merge.js +3 -1
- package/dist/quarantine.d.ts +2 -1
- package/dist/quarantine.js +8 -5
- package/dist/raw-archive-mirror-cleanup.js +2 -1
- package/dist/raw-archive.js +1 -1
- package/dist/recall-history.js +3 -2
- package/dist/recall-pipeline.d.ts +2 -2
- package/dist/recall-pipeline.js +16 -8
- package/dist/recall-scope.js +1 -1
- package/dist/recall-trace.d.ts +3 -3
- package/dist/recall-trace.js +10 -14
- package/dist/refine-llm.js +20 -11
- package/dist/reject-flow.js +6 -1
- package/dist/rerankers/clef.d.ts +2 -2
- package/dist/rerankers/clef.js +72 -30
- package/dist/rerankers/cross-encoder.js +6 -4
- package/dist/rerankers/jev.d.ts +4 -2
- package/dist/rerankers/jev.js +24 -19
- package/dist/rerankers/llm.d.ts +4 -2
- package/dist/rerankers/llm.js +61 -41
- package/dist/rerankers/types.d.ts +1 -1
- package/dist/salience.js +1 -1
- package/dist/same-text.d.ts +2 -0
- package/dist/same-text.js +4 -0
- package/dist/scheduler.d.ts +1 -0
- package/dist/scheduler.js +26 -3
- package/dist/scope.js +4 -3
- package/dist/search/as-of.d.ts +10 -0
- package/dist/search/as-of.js +22 -0
- package/dist/search/bm25-search.d.ts +14 -0
- package/dist/search/bm25-search.js +43 -0
- package/dist/search/bm25.d.ts +15 -0
- package/dist/search/bm25.js +54 -0
- package/dist/search/boosts.d.ts +54 -0
- package/dist/search/boosts.js +94 -0
- package/dist/search/breakdown.d.ts +7 -0
- package/dist/search/breakdown.js +20 -0
- package/dist/search/explain.d.ts +25 -0
- package/dist/search/explain.js +31 -0
- package/dist/search/finalize.d.ts +8 -0
- package/dist/search/finalize.js +52 -0
- package/dist/search/fusion.d.ts +27 -0
- package/dist/search/fusion.js +42 -0
- package/dist/search/hybrid-score.d.ts +20 -0
- package/dist/search/hybrid-score.js +73 -0
- package/dist/search/hybrid.d.ts +46 -0
- package/dist/search/hybrid.js +64 -0
- package/dist/search/physics-search.d.ts +29 -0
- package/dist/search/physics-search.js +162 -0
- package/dist/search/rerank.d.ts +10 -0
- package/dist/search/rerank.js +72 -0
- package/dist/search/temporal.d.ts +15 -0
- package/dist/search/temporal.js +45 -0
- package/dist/search/types.d.ts +91 -0
- package/dist/search/types.js +2 -0
- package/dist/search/vector.d.ts +30 -0
- package/dist/search/vector.js +71 -0
- package/dist/secret-detect.d.ts +2 -0
- package/dist/secret-detect.js +3 -1
- package/dist/server/auth.d.ts +52 -0
- package/dist/server/auth.js +221 -0
- package/dist/server/client-ip.d.ts +25 -0
- package/dist/server/client-ip.js +92 -0
- package/dist/server/cursor.d.ts +23 -0
- package/dist/server/cursor.js +58 -0
- package/dist/server/lifecycle.d.ts +7 -0
- package/dist/server/lifecycle.js +29 -0
- package/dist/server/mcp-http.d.ts +5 -0
- package/dist/server/mcp-http.js +199 -0
- package/dist/server/request.d.ts +33 -0
- package/dist/server/request.js +103 -0
- package/dist/server/routes/admin.d.ts +9 -0
- package/dist/server/routes/admin.js +158 -0
- package/dist/server/routes/customer-notes.d.ts +7 -0
- package/dist/server/routes/customer-notes.js +112 -0
- package/dist/server/routes/decisions.d.ts +7 -0
- package/dist/server/routes/decisions.js +133 -0
- package/dist/server/routes/incidents.d.ts +7 -0
- package/dist/server/routes/incidents.js +126 -0
- package/dist/server/routes/memories.d.ts +10 -0
- package/dist/server/routes/memories.js +179 -0
- package/dist/server/routes/policies.d.ts +8 -0
- package/dist/server/routes/policies.js +151 -0
- package/dist/server/routes/predictions.d.ts +7 -0
- package/dist/server/routes/predictions.js +164 -0
- package/dist/server/routes/processes.d.ts +7 -0
- package/dist/server/routes/processes.js +161 -0
- package/dist/server/routes/project-briefs.d.ts +8 -0
- package/dist/server/routes/project-briefs.js +136 -0
- package/dist/server/routes/recall.d.ts +8 -0
- package/dist/server/routes/recall.js +340 -0
- package/dist/server/routes/skills.d.ts +8 -0
- package/dist/server/routes/skills.js +150 -0
- package/dist/server/types.d.ts +56 -0
- package/dist/server/types.js +2 -0
- package/dist/server/validation.d.ts +14 -0
- package/dist/server/validation.js +91 -0
- package/dist/server.d.ts +7 -61
- package/dist/server.js +92 -2368
- package/dist/session-digest.d.ts +1 -1
- package/dist/session-digest.js +9 -2
- package/dist/shared.d.ts +3 -1
- package/dist/shared.js +46 -40
- package/dist/skills.d.ts +3 -0
- package/dist/skills.js +7 -5
- package/dist/stdin.js +3 -2
- package/dist/store/audit-event.d.ts +19 -0
- package/dist/store/audit-event.js +33 -0
- package/dist/store/candidates.d.ts +42 -0
- package/dist/store/candidates.js +152 -0
- package/dist/store/conflicts.d.ts +44 -0
- package/dist/store/conflicts.js +444 -0
- package/dist/store/delete-and-batch.d.ts +63 -0
- package/dist/store/delete-and-batch.js +310 -0
- package/dist/store/entry-reads.d.ts +92 -0
- package/dist/store/entry-reads.js +255 -0
- package/dist/store/entry-row.d.ts +67 -0
- package/dist/store/entry-row.js +208 -0
- package/dist/store/entry-writes.d.ts +46 -0
- package/dist/store/entry-writes.js +148 -0
- package/dist/store/handoffs.d.ts +26 -0
- package/dist/store/handoffs.js +184 -0
- package/dist/store/index-and-stats.d.ts +52 -0
- package/dist/store/index-and-stats.js +214 -0
- package/dist/store/markdown.d.ts +10 -0
- package/dist/store/markdown.js +108 -0
- package/dist/store/mirrors.d.ts +49 -0
- package/dist/store/mirrors.js +312 -0
- package/dist/store/open.d.ts +15 -0
- package/dist/store/open.js +223 -0
- package/dist/store/rows.d.ts +178 -0
- package/dist/store/rows.js +158 -0
- package/dist/store/search-rows.d.ts +86 -0
- package/dist/store/search-rows.js +254 -0
- package/dist/store/sessions.d.ts +83 -0
- package/dist/store/sessions.js +272 -0
- package/dist/store/summaries.d.ts +94 -0
- package/dist/store/summaries.js +377 -0
- package/dist/store/tenant-lookup.d.ts +12 -0
- package/dist/store/tenant-lookup.js +16 -0
- package/dist/store-cards.js +2 -1
- package/dist/summary-dirty.d.ts +4 -0
- package/dist/summary-dirty.js +32 -0
- package/dist/support-bundle.js +4 -3
- package/dist/tenant.js +2 -2
- package/dist/token-ledger.js +1 -0
- package/dist/tokenize.d.ts +2 -0
- package/dist/tokenize.js +16 -0
- package/dist/transcript-tail.d.ts +7 -0
- package/dist/transcript-tail.js +48 -0
- package/dist/vector-store.d.ts +27 -0
- package/dist/vector-store.js +210 -0
- package/dist/version.d.ts +2 -2
- package/dist/version.js +2 -2
- package/dist/working-memory.js +1 -1
- package/dist/yaml.js +36 -11
- package/dist-ui/assets/ibm-plex-mono-latin-400-normal-CvHOgSBP.woff +0 -0
- package/dist-ui/assets/ibm-plex-mono-latin-400-normal-DMJ8VG8y.woff2 +0 -0
- package/dist-ui/assets/ibm-plex-mono-latin-500-normal-CB9ihrfo.woff +0 -0
- package/dist-ui/assets/ibm-plex-mono-latin-500-normal-DSY6xOcd.woff2 +0 -0
- package/dist-ui/assets/ibm-plex-mono-latin-600-normal-BgSNZQsw.woff2 +0 -0
- package/dist-ui/assets/ibm-plex-mono-latin-600-normal-DWFSQ4vo.woff +0 -0
- package/dist-ui/assets/ibm-plex-sans-latin-400-normal-CDDApCn2.woff2 +0 -0
- package/dist-ui/assets/ibm-plex-sans-latin-400-normal-CYLoc0-x.woff +0 -0
- package/dist-ui/assets/ibm-plex-sans-latin-500-normal-6ng42L7E.woff2 +0 -0
- package/dist-ui/assets/ibm-plex-sans-latin-500-normal-BgVn5rGT.woff +0 -0
- package/dist-ui/assets/ibm-plex-sans-latin-600-normal-Cu4Hd6ag.woff +0 -0
- package/dist-ui/assets/ibm-plex-sans-latin-600-normal-CuJfVYMP.woff2 +0 -0
- package/dist-ui/assets/index-DPN7cP19.js +33 -0
- package/dist-ui/assets/index-dFloKRVr.css +1 -0
- package/dist-ui/index.html +3 -25
- package/extensions/openclaw-plugin/openclaw.plugin.json +1 -1
- package/extensions/openclaw-plugin/package.json +1 -1
- package/openclaw.plugin.json +1 -1
- package/package.json +2 -1
- package/dist/capture.d.ts +0 -155
- package/dist/capture.js +0 -1293
- package/dist/consolidate.d.ts +0 -58
- package/dist/consolidate.js +0 -1123
- package/dist/graph.d.ts +0 -245
- package/dist/hooks.d.ts +0 -208
- package/dist/hooks.js +0 -1073
- package/dist/importers.js +0 -897
- package/dist/predictions.js +0 -620
- package/dist/search.d.ts +0 -320
- package/dist/search.js +0 -968
- package/dist/store.d.ts +0 -744
- package/dist/store.js +0 -3372
- package/dist-ui/assets/d3-BiWEKnn4.js +0 -1
- package/dist-ui/assets/index-BhT8RvO6.js +0 -61
- package/dist-ui/assets/index-RoXXJ5dq.css +0 -1
- package/dist-ui/assets/three-BDgTxR1l.js +0 -4112
|
@@ -0,0 +1,150 @@
|
|
|
1
|
+
// /v1/skills routes.
|
|
2
|
+
import { closeSkill, exportSkills, loadSkillById, loadSkills, saveSkill, VALID_SKILL_STATES } from '../../skills.js';
|
|
3
|
+
import { HttpError, sendJson } from '../../http-util.js';
|
|
4
|
+
import { buildContextWithAuth } from '../auth.js';
|
|
5
|
+
import { byCreatedAt, pageOf, parseCursor } from '../cursor.js';
|
|
6
|
+
import { isJsonString, isSetMember, parseJsonBody, parseListLimit } from '../validation.js';
|
|
7
|
+
// ── skills (E2 first-class object, executable/exportable) ──
|
|
8
|
+
//
|
|
9
|
+
// 6 routes: POST /v1/skills (new; body skillName + instructions + trigger?),
|
|
10
|
+
// GET /v1/skills (list, status filter; shared parseListLimit), GET
|
|
11
|
+
// /v1/skills/export (renders ACTIVE skills as an AGENTS.md/CLAUDE.md markdown
|
|
12
|
+
// block -> {markdown}; literal 'export' is non-numeric so the /:id (\d+) route
|
|
13
|
+
// cannot capture it, but it is ordered first regardless), GET /v1/skills/:id,
|
|
14
|
+
// POST /v1/skills/:id/supersede, POST /v1/skills/:id/close. DoS caps:
|
|
15
|
+
// skillName 256, instructions 8192, trigger 1024, changeSummary 4096. The store
|
|
16
|
+
// validates + throws; the boundary maps validation -> 400, not-found -> 404,
|
|
17
|
+
// not-active -> 409. Mirrors /v1/processes; "executable" = exportable
|
|
18
|
+
// instruction (no code exec).
|
|
19
|
+
export async function handleCreateSkill({ req, res, opts }) {
|
|
20
|
+
const ctx = await buildContextWithAuth(req, opts);
|
|
21
|
+
const body = await parseJsonBody(req, ctx);
|
|
22
|
+
const skillName = body['skillName'];
|
|
23
|
+
if (!isJsonString(skillName) || skillName.trim().length === 0) {
|
|
24
|
+
throw new HttpError(400, 'skillName is required (non-empty string)');
|
|
25
|
+
}
|
|
26
|
+
if (skillName.length > 256) {
|
|
27
|
+
throw new HttpError(400, 'skillName exceeds 256-character cap');
|
|
28
|
+
}
|
|
29
|
+
const instructions = body['instructions'];
|
|
30
|
+
if (!isJsonString(instructions) || instructions.trim().length === 0) {
|
|
31
|
+
throw new HttpError(400, 'instructions are required (non-empty string)');
|
|
32
|
+
}
|
|
33
|
+
if (instructions.length > 8192) {
|
|
34
|
+
throw new HttpError(400, 'instructions exceed 8192-character cap');
|
|
35
|
+
}
|
|
36
|
+
const triggerRaw = body['trigger'];
|
|
37
|
+
let trigger;
|
|
38
|
+
if (triggerRaw !== undefined && triggerRaw !== null) {
|
|
39
|
+
if (!isJsonString(triggerRaw)) {
|
|
40
|
+
throw new HttpError(400, 'trigger must be a string');
|
|
41
|
+
}
|
|
42
|
+
if (triggerRaw.length > 1024) {
|
|
43
|
+
throw new HttpError(400, 'trigger exceeds 1024-character cap');
|
|
44
|
+
}
|
|
45
|
+
trigger = triggerRaw;
|
|
46
|
+
}
|
|
47
|
+
const skill = saveSkill(opts.hippoRoot, ctx.tenantId, {
|
|
48
|
+
skillName,
|
|
49
|
+
instructions,
|
|
50
|
+
trigger,
|
|
51
|
+
}, ctx.actor.subject);
|
|
52
|
+
sendJson(res, 201, { skill });
|
|
53
|
+
return;
|
|
54
|
+
}
|
|
55
|
+
export async function handleListSkills({ req, res, opts, query }) {
|
|
56
|
+
const status = query.get('status') ?? 'all';
|
|
57
|
+
const limit = parseListLimit(query.get('limit'));
|
|
58
|
+
const after = parseCursor(query.get('cursor'), 'string', 'integer');
|
|
59
|
+
const ctx = await buildContextWithAuth(req, opts);
|
|
60
|
+
let skills;
|
|
61
|
+
if (status === 'all') {
|
|
62
|
+
skills = loadSkills(opts.hippoRoot, ctx.tenantId, { limit: limit + 1, after });
|
|
63
|
+
}
|
|
64
|
+
else {
|
|
65
|
+
if (!isSetMember(VALID_SKILL_STATES, status)) {
|
|
66
|
+
throw new HttpError(400, `status must be one of: active | superseded | closed | all (got "${status}")`);
|
|
67
|
+
}
|
|
68
|
+
skills = loadSkills(opts.hippoRoot, ctx.tenantId, {
|
|
69
|
+
status,
|
|
70
|
+
limit: limit + 1,
|
|
71
|
+
after,
|
|
72
|
+
});
|
|
73
|
+
}
|
|
74
|
+
const page = pageOf(skills, limit, byCreatedAt);
|
|
75
|
+
sendJson(res, 200, { skills: page.items, next_cursor: page.nextCursor });
|
|
76
|
+
return;
|
|
77
|
+
}
|
|
78
|
+
// The export renderer: must precede the /:id GET (literal 'export' is
|
|
79
|
+
// non-numeric so the /(\d+)/ route would not match it, but order it first).
|
|
80
|
+
export async function handleExportSkills({ req, res, opts }) {
|
|
81
|
+
const ctx = await buildContextWithAuth(req, opts);
|
|
82
|
+
const markdown = exportSkills(opts.hippoRoot, ctx.tenantId);
|
|
83
|
+
sendJson(res, 200, { markdown });
|
|
84
|
+
return;
|
|
85
|
+
}
|
|
86
|
+
export async function handleSupersedeSkill({ req, res, opts }, skillSupersedeMatch) {
|
|
87
|
+
const id = parseInt(skillSupersedeMatch[1], 10);
|
|
88
|
+
const ctx = await buildContextWithAuth(req, opts);
|
|
89
|
+
const body = await parseJsonBody(req, ctx);
|
|
90
|
+
const instructions = body['instructions'];
|
|
91
|
+
if (!isJsonString(instructions) || instructions.trim().length === 0) {
|
|
92
|
+
throw new HttpError(400, 'instructions are required (non-empty string)');
|
|
93
|
+
}
|
|
94
|
+
if (instructions.length > 8192) {
|
|
95
|
+
throw new HttpError(400, 'instructions exceed 8192-character cap');
|
|
96
|
+
}
|
|
97
|
+
const triggerRaw = body['trigger'];
|
|
98
|
+
let trigger;
|
|
99
|
+
if (triggerRaw !== undefined && triggerRaw !== null) {
|
|
100
|
+
if (!isJsonString(triggerRaw)) {
|
|
101
|
+
throw new HttpError(400, 'trigger must be a string');
|
|
102
|
+
}
|
|
103
|
+
if (triggerRaw.length > 1024) {
|
|
104
|
+
throw new HttpError(400, 'trigger exceeds 1024-character cap');
|
|
105
|
+
}
|
|
106
|
+
trigger = triggerRaw;
|
|
107
|
+
}
|
|
108
|
+
const changeRaw = body['changeSummary'];
|
|
109
|
+
let changeSummary;
|
|
110
|
+
if (changeRaw !== undefined && changeRaw !== null) {
|
|
111
|
+
if (!isJsonString(changeRaw)) {
|
|
112
|
+
throw new HttpError(400, 'changeSummary must be a string');
|
|
113
|
+
}
|
|
114
|
+
if (changeRaw.length > 4096) {
|
|
115
|
+
throw new HttpError(400, 'changeSummary exceeds 4096-character cap');
|
|
116
|
+
}
|
|
117
|
+
changeSummary = changeRaw;
|
|
118
|
+
}
|
|
119
|
+
const existing = loadSkillById(opts.hippoRoot, ctx.tenantId, id);
|
|
120
|
+
if (!existing) {
|
|
121
|
+
throw new HttpError(404, `skill ${id} not found`);
|
|
122
|
+
}
|
|
123
|
+
const skill = saveSkill(opts.hippoRoot, ctx.tenantId, {
|
|
124
|
+
skillName: existing.skillName,
|
|
125
|
+
instructions,
|
|
126
|
+
trigger,
|
|
127
|
+
changeSummary,
|
|
128
|
+
supersedesSkillId: id,
|
|
129
|
+
}, ctx.actor.subject);
|
|
130
|
+
sendJson(res, 200, { skill });
|
|
131
|
+
return;
|
|
132
|
+
}
|
|
133
|
+
export async function handleCloseSkill({ req, res, opts }, skillCloseMatch) {
|
|
134
|
+
const id = parseInt(skillCloseMatch[1], 10);
|
|
135
|
+
const ctx = await buildContextWithAuth(req, opts);
|
|
136
|
+
const skill = closeSkill(opts.hippoRoot, ctx.tenantId, id, ctx.actor.subject);
|
|
137
|
+
sendJson(res, 200, { skill });
|
|
138
|
+
return;
|
|
139
|
+
}
|
|
140
|
+
export async function handleGetSkill({ req, res, opts }, skillByIdMatch) {
|
|
141
|
+
const id = parseInt(skillByIdMatch[1], 10);
|
|
142
|
+
const ctx = await buildContextWithAuth(req, opts);
|
|
143
|
+
const skill = loadSkillById(opts.hippoRoot, ctx.tenantId, id);
|
|
144
|
+
if (!skill) {
|
|
145
|
+
throw new HttpError(404, `skill ${id} not found`);
|
|
146
|
+
}
|
|
147
|
+
sendJson(res, 200, { skill });
|
|
148
|
+
return;
|
|
149
|
+
}
|
|
150
|
+
//# sourceMappingURL=skills.js.map
|
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
import type { IncomingMessage, ServerResponse } from 'node:http';
|
|
2
|
+
export interface ServerHandle {
|
|
3
|
+
port: number;
|
|
4
|
+
url: string;
|
|
5
|
+
stop: () => Promise<void>;
|
|
6
|
+
/** Introspection-only (v1.26.2): the underlying node:http Server, exposed so
|
|
7
|
+
* tests can assert keep-alive/headers timeout hardening without reaching
|
|
8
|
+
* into serve()'s closure. Additive field — do not depend on it for control
|
|
9
|
+
* flow outside tests. */
|
|
10
|
+
server?: import('node:http').Server;
|
|
11
|
+
}
|
|
12
|
+
/** Identity an {@link AuthResolver} vouches for. The core sanitises it before use. */
|
|
13
|
+
export interface ResolvedBearer {
|
|
14
|
+
tenantId: string;
|
|
15
|
+
subject: string;
|
|
16
|
+
/** Not 'admin' means 'member'. Admin is tenant-only, yet can mint member API keys (POST /v1/auth/keys); an add-on revokes them through the exported authRevoke when the IdP deprovisions the minter. */
|
|
17
|
+
role: 'admin' | 'member';
|
|
18
|
+
scopes?: readonly string[];
|
|
19
|
+
}
|
|
20
|
+
/** Sole judge of non-`hk_` bearer tokens: null is a 401; a throw or missed deadline is a 503, so throw only when upstream is down. */
|
|
21
|
+
export type AuthResolver = (token: string) => ResolvedBearer | null | Promise<ResolvedBearer | null>;
|
|
22
|
+
export interface ServeOpts {
|
|
23
|
+
hippoRoot: string;
|
|
24
|
+
/** Runs on every request and SSE heartbeat, so keep it cache-backed; API keys never reach it. */
|
|
25
|
+
authResolver?: AuthResolver;
|
|
26
|
+
/** Deadline for one authResolver call; defaults to 5000 ms. */
|
|
27
|
+
authResolverTimeoutMs?: number;
|
|
28
|
+
port?: number;
|
|
29
|
+
host?: string;
|
|
30
|
+
/** Stop and exit on SIGINT/SIGTERM. Only `hippo serve` owns the process, so only it sets this. */
|
|
31
|
+
handleSignals?: boolean;
|
|
32
|
+
/** How long stop() lets in-flight requests finish before closing their sockets; defaults to 5000 ms. */
|
|
33
|
+
shutdownDrainMs?: number;
|
|
34
|
+
}
|
|
35
|
+
/** Per-request values the /v1 route handlers read. */
|
|
36
|
+
export interface RouteRequest {
|
|
37
|
+
req: IncomingMessage;
|
|
38
|
+
res: ServerResponse;
|
|
39
|
+
opts: ServeOpts;
|
|
40
|
+
query: URLSearchParams;
|
|
41
|
+
}
|
|
42
|
+
/** One /v1 route: an exact path, a matchPath pattern, or a regex, each paired with the handler for one method. */
|
|
43
|
+
export type Route = {
|
|
44
|
+
method: string;
|
|
45
|
+
path: string;
|
|
46
|
+
handler: (r: RouteRequest) => Promise<void>;
|
|
47
|
+
} | {
|
|
48
|
+
method: string;
|
|
49
|
+
pattern: string;
|
|
50
|
+
handler: (r: RouteRequest, params: Record<string, string>) => Promise<void>;
|
|
51
|
+
} | {
|
|
52
|
+
method: string;
|
|
53
|
+
regex: RegExp;
|
|
54
|
+
handler: (r: RouteRequest, match: RegExpMatchArray) => Promise<void>;
|
|
55
|
+
};
|
|
56
|
+
//# sourceMappingURL=types.d.ts.map
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
import type { IncomingMessage } from 'node:http';
|
|
2
|
+
import type { Context } from '../api.js';
|
|
3
|
+
import { type JsonValue } from '../http-util.js';
|
|
4
|
+
export declare function isJsonString(value: JsonValue | undefined): value is string;
|
|
5
|
+
export declare function isJsonNumber(value: JsonValue | undefined): value is number;
|
|
6
|
+
export declare function isJsonBoolean(value: JsonValue | undefined): value is boolean;
|
|
7
|
+
export declare function isSetMember<T extends string>(set: ReadonlySet<T>, value: string): value is T;
|
|
8
|
+
export declare function parseListLimit(limitRaw: string | null, defaultLimit?: number, maxLimit?: number): number;
|
|
9
|
+
/** `_authed` is proof the caller passed auth: an unauthenticated request must never make the server read its body. */
|
|
10
|
+
export declare function parseJsonBody(req: IncomingMessage, _authed: Context): Promise<Record<string, JsonValue>>;
|
|
11
|
+
export declare function getString(obj: Record<string, JsonValue>, key: string): string | undefined;
|
|
12
|
+
export declare function getStringArray(obj: Record<string, JsonValue>, key: string): string[] | undefined;
|
|
13
|
+
export declare function validateIdSegment(id: string, fieldName: string): void;
|
|
14
|
+
//# sourceMappingURL=validation.d.ts.map
|
|
@@ -0,0 +1,91 @@
|
|
|
1
|
+
import { HttpError, isJsonObjectRecord, readBody } from '../http-util.js';
|
|
2
|
+
export function isJsonString(value) {
|
|
3
|
+
return typeof value === 'string';
|
|
4
|
+
}
|
|
5
|
+
export function isJsonNumber(value) {
|
|
6
|
+
return typeof value === 'number';
|
|
7
|
+
}
|
|
8
|
+
export function isJsonBoolean(value) {
|
|
9
|
+
return typeof value === 'boolean';
|
|
10
|
+
}
|
|
11
|
+
// Runtime membership check for a `ReadonlySet<T>` of string-literal union
|
|
12
|
+
// members, used at every `body` field validated against a VALID_* set below.
|
|
13
|
+
// Set<T>.has(value: T) itself gives no narrowing (its parameter type is T,
|
|
14
|
+
// not a type predicate) so callers previously needed a separate `as T` cast
|
|
15
|
+
// at both the check and the later usage; this helper is the one place that
|
|
16
|
+
// assertion lives, so downstream call sites narrow via the `value is T`
|
|
17
|
+
// return instead of re-asserting.
|
|
18
|
+
export function isSetMember(set, value) {
|
|
19
|
+
// SAFETY: `value as T` is discarded unless `set.has` (the real runtime
|
|
20
|
+
// check) confirms membership; the `value is T` return type is what
|
|
21
|
+
// performs the actual narrowing for callers.
|
|
22
|
+
return set.has(value);
|
|
23
|
+
}
|
|
24
|
+
// Parse a `?limit=` query param for the E2 list routes. Defaults to 100; requires
|
|
25
|
+
// a positive INTEGER <= 1000. Number.isInteger rejects fractional values like
|
|
26
|
+
// "1.5" that Number.isFinite would pass but SQLite `LIMIT ?` rejects with a
|
|
27
|
+
// datatype mismatch (a 500). Shared across the decision/incident/process/policy
|
|
28
|
+
// list routes so the guard cannot drift (codex review 2026-05-30 P2: fractional
|
|
29
|
+
// limit reached SQLite on the policy route; the same latent hole existed in the
|
|
30
|
+
// sibling routes this was copied from).
|
|
31
|
+
export function parseListLimit(limitRaw, defaultLimit = 100, maxLimit = 1000) {
|
|
32
|
+
if (limitRaw === null)
|
|
33
|
+
return defaultLimit;
|
|
34
|
+
const limit = Number(limitRaw);
|
|
35
|
+
if (!Number.isInteger(limit) || limit <= 0 || limit > maxLimit) {
|
|
36
|
+
throw new HttpError(400, `limit must be a positive integer <= ${maxLimit}`);
|
|
37
|
+
}
|
|
38
|
+
return limit;
|
|
39
|
+
}
|
|
40
|
+
/** `_authed` is proof the caller passed auth: an unauthenticated request must never make the server read its body. */
|
|
41
|
+
export async function parseJsonBody(req, _authed) {
|
|
42
|
+
const raw = await readBody(req);
|
|
43
|
+
if (raw.length === 0)
|
|
44
|
+
return {};
|
|
45
|
+
try {
|
|
46
|
+
const parsed = JSON.parse(raw);
|
|
47
|
+
if (!isJsonObjectRecord(parsed)) {
|
|
48
|
+
throw new HttpError(400, 'request body must be a JSON object');
|
|
49
|
+
}
|
|
50
|
+
return parsed;
|
|
51
|
+
}
|
|
52
|
+
catch (e) {
|
|
53
|
+
if (e instanceof HttpError)
|
|
54
|
+
throw e;
|
|
55
|
+
throw new HttpError(400, 'invalid JSON body');
|
|
56
|
+
}
|
|
57
|
+
}
|
|
58
|
+
export function getString(obj, key) {
|
|
59
|
+
const v = obj[key];
|
|
60
|
+
return isJsonString(v) ? v : undefined;
|
|
61
|
+
}
|
|
62
|
+
export function getStringArray(obj, key) {
|
|
63
|
+
const v = obj[key];
|
|
64
|
+
if (!Array.isArray(v))
|
|
65
|
+
return undefined;
|
|
66
|
+
if (!v.every(isJsonString))
|
|
67
|
+
return undefined;
|
|
68
|
+
return v;
|
|
69
|
+
}
|
|
70
|
+
/**
|
|
71
|
+
* v1.6.4: charset + length validation for `:id` route captures. Routes call
|
|
72
|
+
* this immediately after `matchPath` to reject empty / overlong / illegal
|
|
73
|
+
* ids with a useful 400 instead of silently falling through to "not found".
|
|
74
|
+
*
|
|
75
|
+
* Allowed charset matches all production id shapes Hippo emits: `mem_<hex>`,
|
|
76
|
+
* `sum_<hex>`, `sess-<id>`, Slack bot ids like `B01ABCD`, etc. The `:` and
|
|
77
|
+
* `.` are allowed for forward-compat. The `/` is intentionally absent —
|
|
78
|
+
* Hippo never emits ids with slashes, and `rejectEncodedSlash` already
|
|
79
|
+
* stops `%2F`-smuggled ones at the front door.
|
|
80
|
+
*/
|
|
81
|
+
const ID_SEGMENT_RE = /^[A-Za-z0-9_:.\-]+$/;
|
|
82
|
+
export function validateIdSegment(id, fieldName) {
|
|
83
|
+
if (id.length === 0)
|
|
84
|
+
throw new HttpError(400, `${fieldName} is required`);
|
|
85
|
+
if (id.length > 256)
|
|
86
|
+
throw new HttpError(400, `${fieldName} exceeds 256-character cap`);
|
|
87
|
+
if (!ID_SEGMENT_RE.test(id)) {
|
|
88
|
+
throw new HttpError(400, `${fieldName} contains invalid characters; allowed: A-Z a-z 0-9 _ : . -`);
|
|
89
|
+
}
|
|
90
|
+
}
|
|
91
|
+
//# sourceMappingURL=validation.js.map
|
package/dist/server.d.ts
CHANGED
|
@@ -1,66 +1,12 @@
|
|
|
1
|
-
import { type
|
|
2
|
-
/** Test-only: reset the module-level recall-history Map. Call from beforeEach. */
|
|
3
|
-
export declare function __resetSessionRecallHistoryHttp(): void;
|
|
4
|
-
import { authRevoke, type Actor, type Context } from './api.js';
|
|
1
|
+
import { type Actor, authRevoke, type Context } from './api.js';
|
|
5
2
|
import { ForbiddenError } from './api-errors.js';
|
|
3
|
+
import type { ServeOpts, ServerHandle } from './server/types.js';
|
|
6
4
|
export { authRevoke, ForbiddenError, type Context, type Actor };
|
|
7
|
-
export
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
* tests can assert keep-alive/headers timeout hardening without reaching
|
|
13
|
-
* into serve()'s closure. Additive field — do not depend on it for control
|
|
14
|
-
* flow outside tests. */
|
|
15
|
-
server?: import('node:http').Server;
|
|
16
|
-
}
|
|
17
|
-
/** Identity an {@link AuthResolver} vouches for. The core sanitises it before use. */
|
|
18
|
-
export interface ResolvedBearer {
|
|
19
|
-
tenantId: string;
|
|
20
|
-
subject: string;
|
|
21
|
-
/** Not 'admin' means 'member'. Admin is tenant-only, yet can mint member API keys (POST /v1/auth/keys); an add-on revokes them through the exported authRevoke when the IdP deprovisions the minter. */
|
|
22
|
-
role: 'admin' | 'member';
|
|
23
|
-
scopes?: readonly string[];
|
|
24
|
-
}
|
|
25
|
-
/** Sole judge of non-`hk_` bearer tokens: null is a 401; a throw or missed deadline is a 503, so throw only when upstream is down. */
|
|
26
|
-
export type AuthResolver = (token: string) => ResolvedBearer | null | Promise<ResolvedBearer | null>;
|
|
27
|
-
export interface ServeOpts {
|
|
28
|
-
hippoRoot: string;
|
|
29
|
-
/** Runs on every request and SSE heartbeat, so keep it cache-backed; API keys never reach it. */
|
|
30
|
-
authResolver?: AuthResolver;
|
|
31
|
-
/** Deadline for one authResolver call; defaults to 5000 ms. */
|
|
32
|
-
authResolverTimeoutMs?: number;
|
|
33
|
-
port?: number;
|
|
34
|
-
host?: string;
|
|
35
|
-
/** Stop and exit on SIGINT/SIGTERM. Only `hippo serve` owns the process, so only it sets this. */
|
|
36
|
-
handleSignals?: boolean;
|
|
37
|
-
}
|
|
38
|
-
/**
|
|
39
|
-
* Recognise loopback remote addresses. Node reports IPv6-mapped IPv4 as
|
|
40
|
-
* '::ffff:127.0.0.1' on dual-stack sockets, so we accept that alongside
|
|
41
|
-
* the bare v4 and v6 loopbacks. Anything else is treated as remote.
|
|
42
|
-
*/
|
|
43
|
-
export declare function isLoopback(remoteAddress: string | undefined): boolean;
|
|
44
|
-
export declare const LOOPBACK_HOST_HEADER: RegExp;
|
|
45
|
-
/** A browser request sent by another site. Non-browser clients send neither header and pass. */
|
|
46
|
-
export declare function isCrossSite(req: IncomingMessage): boolean;
|
|
47
|
-
/**
|
|
48
|
-
* Rate-limit key for a request. Defaults to the socket's remote address.
|
|
49
|
-
*
|
|
50
|
-
* Behind a TLS-terminating proxy (Fly, most PaaS ingress) every socket
|
|
51
|
-
* carries the proxy's address, so per-IP buckets collapse into one global
|
|
52
|
-
* bucket that unauthenticated traffic can drain before auth runs. Set
|
|
53
|
-
* HIPPO_CLIENT_IP_HEADER to the header the proxy stamps with the real
|
|
54
|
-
* client address (fly-client-ip on Fly, which the edge always overwrites)
|
|
55
|
-
* to key buckets per client instead.
|
|
56
|
-
*
|
|
57
|
-
* Only set this when a trusted proxy fronts EVERY request: a directly
|
|
58
|
-
* reachable server honoring the header would let clients mint a fresh
|
|
59
|
-
* bucket per request and bypass the limiter entirely.
|
|
60
|
-
*/
|
|
61
|
-
export declare function clientIpForRateLimit(req: IncomingMessage): string;
|
|
62
|
-
/** Add-ons call this to refuse a subject that would collide with a built-in actor. */
|
|
63
|
-
export declare function isReservedActor(subject: string): boolean;
|
|
5
|
+
export { isCrossSite, LOOPBACK_HOST_HEADER } from './http-util.js';
|
|
6
|
+
export { __resetSessionRecallHistoryHttp } from './server/routes/recall.js';
|
|
7
|
+
export { clientIpForRateLimit } from './server/client-ip.js';
|
|
8
|
+
export { isLoopback, isReservedActor } from './server/auth.js';
|
|
9
|
+
export type { AuthResolver, ResolvedBearer, ServeOpts, ServerHandle } from './server/types.js';
|
|
64
10
|
/**
|
|
65
11
|
* Boot the HTTP daemon on host:port and write the pidfile under hippoRoot.
|
|
66
12
|
*
|