@axiom-lattice/gateway 4.6.1 → 4.7.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.
Files changed (43) hide show
  1. package/dist/OrphanRecoveryRuntime-MQDEJX3M.mjs +8 -0
  2. package/dist/OrphanRecoveryRuntime-MQDEJX3M.mjs.map +1 -0
  3. package/dist/RecoveryCallerDeps-6SJUYJ5S.mjs +8 -0
  4. package/dist/RecoveryCallerDeps-6SJUYJ5S.mjs.map +1 -0
  5. package/dist/{a2a-standard-PIOKEHPS.mjs → a2a-standard-PBYPNHOA.mjs} +59 -21
  6. package/dist/a2a-standard-PBYPNHOA.mjs.map +1 -0
  7. package/dist/chunk-KDQKTU3N.mjs +288 -0
  8. package/dist/chunk-KDQKTU3N.mjs.map +1 -0
  9. package/dist/chunk-NOXGKYUV.mjs +37 -0
  10. package/dist/chunk-NOXGKYUV.mjs.map +1 -0
  11. package/dist/{chunk-526UYVNQ.mjs → chunk-NPHK4SZ6.mjs} +4 -4
  12. package/dist/embed/{embed-page-AgentDetailSideApp-7NYLPLAX.js → embed-page-AgentDetailSideApp-2C2ZR62Q.js} +1 -1
  13. package/dist/embed/{embed-page-AgentGovernanceWorkbench-LNGNSI7X.js → embed-page-AgentGovernanceWorkbench-GG4ONSTS.js} +1 -1
  14. package/dist/embed/{embed-page-MessageGraph-E6DZDT65.js → embed-page-MessageGraph-WMYTVUUC.js} +1 -1
  15. package/dist/embed/{embed-page-ReactChart-3VE7F5VJ.js → embed-page-ReactChart-7XCMDMH6.js} +1 -1
  16. package/dist/embed/{embed-page-TasksSideApp-QM5TZ7EG.js → embed-page-TasksSideApp-4ZJ4Q4CL.js} +1 -1
  17. package/dist/embed/{embed-page-TeamWorkspace-E7RFY3ZY.js → embed-page-TeamWorkspace-H5OOEN3K.js} +1 -1
  18. package/dist/embed/{embed-page-TopologyRuntimeView-DLPDUB7Z.js → embed-page-TopologyRuntimeView-QMXWERVC.js} +1 -1
  19. package/dist/embed/{embed-page-WorkflowAutomationView-FKSVOHHB.js → embed-page-WorkflowAutomationView-L2OEGCA5.js} +1 -1
  20. package/dist/embed/{embed-page-chunk-H6TK3FAR.js → embed-page-chunk-2G54EIW2.js} +1 -1
  21. package/dist/embed/{embed-page-chunk-I7PWCKAG.js → embed-page-chunk-CZE4IEB3.js} +1 -1
  22. package/dist/embed/{embed-page-chunk-WWTU55RX.js → embed-page-chunk-N2ISCAS7.js} +1 -1
  23. package/dist/embed/{embed-page-chunk-EXCJ42IB.js → embed-page-chunk-OHDEKFTU.js} +1 -1
  24. package/dist/embed/{embed-page-chunk-KN7D66KL.js → embed-page-chunk-SUMYB6ZA.js} +1 -1
  25. package/dist/embed/{embed-page-chunk-U276WBDI.js → embed-page-chunk-XIXSRYJY.js} +6 -6
  26. package/dist/embed/embed-page.js +1 -1
  27. package/dist/index.d.mts +226 -3
  28. package/dist/index.d.ts +226 -3
  29. package/dist/index.js +638 -257
  30. package/dist/index.js.map +1 -1
  31. package/dist/index.mjs +86 -78
  32. package/dist/index.mjs.map +1 -1
  33. package/dist/{open-AMEMJOFJ.mjs → open-STFMNRO5.mjs} +8 -8
  34. package/dist/{open-exposure-I44Q4M3T.mjs → open-exposure-VU227IO3.mjs} +5 -5
  35. package/dist/{open-files-EJ6O2SGX.mjs → open-files-NPNQQ6TY.mjs} +4 -4
  36. package/dist/{open-session-LBTCU3AE.mjs → open-session-IHDGAXL3.mjs} +4 -4
  37. package/package.json +7 -7
  38. package/dist/a2a-standard-PIOKEHPS.mjs.map +0 -1
  39. /package/dist/{chunk-526UYVNQ.mjs.map → chunk-NPHK4SZ6.mjs.map} +0 -0
  40. /package/dist/{open-AMEMJOFJ.mjs.map → open-STFMNRO5.mjs.map} +0 -0
  41. /package/dist/{open-exposure-I44Q4M3T.mjs.map → open-exposure-VU227IO3.mjs.map} +0 -0
  42. /package/dist/{open-files-EJ6O2SGX.mjs.map → open-files-NPNQQ6TY.mjs.map} +0 -0
  43. /package/dist/{open-session-LBTCU3AE.mjs.map → open-session-IHDGAXL3.mjs.map} +0 -0
package/dist/index.d.ts CHANGED
@@ -1,6 +1,6 @@
1
1
  import * as http from 'http';
2
- import { ProjectRoomMessage, ProjectBotMembership, ProjectMembership, TaskItem, ChannelAdapter, InboundMessage, Binding, BindingRegistry, ChannelInstallationStore, DispatchResult, ProjectRoomEventScope, ProjectRoomBusinessEventDraft, ProjectRoomScopedBusinessEvent, ProjectRoomBusinessEvent, ProjectRoomEventSubscription, TaskStore, ProjectRoomStore, ProjectBotMembershipStore, ThreadStore, ProjectRoom, Thread, ProjectStore, LoggerType, PinoFileOptions } from '@axiom-lattice/protocols';
3
- import { TrustedAgentMessageDispatcher, TrustedMessageOptions, TaskLifecycleListener, TaskLifecycleService, IMessageQueueStore, Agent } from '@axiom-lattice/core';
2
+ import { ProjectRoomMessage, ProjectBotMembership, ProjectMembership, TaskItem, ChannelAdapter, InboundMessage, Binding, BindingRegistry, ChannelInstallationStore, DispatchResult, ProjectRoomEventScope, ProjectRoomBusinessEventDraft, ProjectRoomScopedBusinessEvent, ProjectRoomBusinessEvent, ProjectRoomEventSubscription, TaskStore, ProjectRoomStore, ProjectBotMembershipStore, ThreadStore, ProjectRoom, Thread, ProjectStore, TaskWorkItemStore, TenantStore, LoggerType, PinoFileOptions } from '@axiom-lattice/protocols';
3
+ import { TrustedAgentMessageDispatcher, TrustedMessageOptions, TaskLifecycleListener, TaskLifecycleService, IMessageQueueStore, Agent, TaskRunRegistry } from '@axiom-lattice/core';
4
4
  import * as fastify from 'fastify';
5
5
 
6
6
  /** Public publisher surface for committed Project Room business facts. */
@@ -764,6 +764,229 @@ declare class AgentTaskConsumer {
764
764
  trigger_agent_task(taskRequest: AgentTaskRequest): void;
765
765
  }
766
766
 
767
+ /** Minimal caller-graph client surface used by recovery. */
768
+ interface RecoveryCallerClient {
769
+ getState(config: unknown): Promise<unknown>;
770
+ updateState(config: unknown, values: unknown, asNode?: string): Promise<unknown>;
771
+ invoke(input: unknown, config: unknown): Promise<unknown>;
772
+ }
773
+ interface TopCallerRecoveryDeps {
774
+ /**
775
+ * Resolve a caller's agent client + config from the resolved top caller.
776
+ *
777
+ * @param top The resolved top-level caller thread + assistant.
778
+ * @param tenantId The orphan task's tenant, used to scope the caller client.
779
+ */
780
+ callerFor(top: {
781
+ threadId: string;
782
+ assistantId?: string;
783
+ }, tenantId: string): Promise<{
784
+ client: RecoveryCallerClient;
785
+ config: unknown;
786
+ agent?: unknown;
787
+ } | undefined>;
788
+ /** Live-run registry (defaults to the shared Core singleton). */
789
+ registry?: {
790
+ isLive(taskId: string): boolean;
791
+ };
792
+ /** Resume the continuation (tests can call client.invoke(null, config)). */
793
+ resume(client: RecoveryCallerClient, config: unknown, agent?: unknown): Promise<void>;
794
+ }
795
+ /** Dependencies for an on-demand single-task recovery ({@link recoverTask}). */
796
+ interface RecoverTaskDeps {
797
+ /** Lifecycle used to converge the orphan to `failed(no_executor)`. */
798
+ lifecycle: Pick<TaskLifecycleService, "failTask">;
799
+ /** Live-run registry (defaults to the shared Core singleton). */
800
+ registry?: TaskRunRegistry;
801
+ /**
802
+ * The tenant's other orphan candidates (normally every `in_progress` task),
803
+ * used to walk the caller chain up to the true top-level caller.
804
+ *
805
+ * @remarks
806
+ * Without this set {@link resolveTopCaller} can only see the target itself,
807
+ * so a nested middle run would be mistaken for a direct child of its
808
+ * immediate (frozen) caller. Defaults to `[converged]` when omitted.
809
+ */
810
+ orphans?: TaskItem[];
811
+ /** Resolve a caller's agent client + config from the resolved top caller. */
812
+ callerFor: TopCallerRecoveryDeps["callerFor"];
813
+ /** Resume the continuation (tests can call client.invoke(null, config)). */
814
+ resume: TopCallerRecoveryDeps["resume"];
815
+ }
816
+ /**
817
+ * Outcome of an on-demand single-task recovery attempt.
818
+ *
819
+ * @remarks
820
+ * - `recovered`: the task was converged and its top-level caller was resumed.
821
+ * - `skipped`: nothing was changed; `reason` names the guard (for example
822
+ * `not_in_progress`, `live`, `middle`, `project_task`, `no_top_caller`,
823
+ * `not_found`).
824
+ * - `converged_no_call`: the task was converged to `failed`, but the caller had
825
+ * no pending `task` call left to resolve, so no continuation was resumed.
826
+ */
827
+ type RecoverTaskResult = {
828
+ kind: "recovered";
829
+ } | {
830
+ kind: "skipped";
831
+ reason: string;
832
+ } | {
833
+ kind: "converged_no_call";
834
+ };
835
+ /**
836
+ * Backfills one converged direct-child task's top-level caller.
837
+ *
838
+ * @param task The converged orphan task (must carry `context.caller_thread_id`).
839
+ * @param top The resolved top-level caller.
840
+ * @param deps Caller resolver, live-run registry, and resume hook.
841
+ * @returns `"recovered"` or a `"skipped:<reason>"` string.
842
+ */
843
+ declare function recoverTopCaller(task: TaskItem, top: {
844
+ threadId: string;
845
+ assistantId?: string;
846
+ }, deps: TopCallerRecoveryDeps): Promise<string>;
847
+ /**
848
+ * Recovers a single orphan task on demand, reusing the collapse logic.
849
+ *
850
+ * @param task The candidate task (any status).
851
+ * @param deps Lifecycle, live-run registry, orphan candidate set (for the
852
+ * caller-chain walk), caller resolver, and resume hook.
853
+ * @returns A discriminated outcome: `recovered`, `skipped:<reason>`, or
854
+ * `converged_no_call` when the task was converged but the caller had no
855
+ * pending `task` call to resolve.
856
+ * @remarks
857
+ * Mirrors {@link runOrphanRecovery} for exactly one task: anything not
858
+ * `in_progress`, or still held by a live run, is skipped; the rest is converged
859
+ * to `failed` (`no_executor`, ADR-143) and its **top-level** caller is
860
+ * backfilled. `deps.orphans` must carry the tenant's other `in_progress`
861
+ * candidates so a nested middle run is correctly skipped (`middle`) instead of
862
+ * being mistaken for a direct child of its frozen immediate caller.
863
+ *
864
+ * This is an **offline/maintenance** entry point (the `task:recover` CLI): run
865
+ * it when the Gateway is stopped, or from within the Gateway process. The
866
+ * `live` guard reads the process-local {@link taskRunRegistry}, so it is
867
+ * meaningful only in-process and cannot detect a run held by another process.
868
+ *
869
+ * The convergence actor is `system:on-demand-recovery` (distinct from the
870
+ * startup sweep's `system:orphan-recovery`), so on-demand convergences are
871
+ * auditable in the task work-item trail. No HTTP route is added and recovery
872
+ * semantics are unchanged.
873
+ */
874
+ declare function recoverTask(task: TaskItem, deps: RecoverTaskDeps): Promise<RecoverTaskResult>;
875
+ /** Walks caller links up to the thread that is not any orphan's run thread. */
876
+ declare function resolveTopCaller(task: TaskItem, orphans: TaskItem[]): {
877
+ threadId: string;
878
+ assistantId?: string;
879
+ } | undefined;
880
+ /**
881
+ * Runs the whole collapse recovery once: reconcile orphan tasks, then backfill
882
+ * the top-level caller of every direct-child orphan, grouped per top caller.
883
+ * Best-effort; a failing group is contained and never aborts the others.
884
+ *
885
+ * @param deps Reconcile source, caller resolution, resume, and logger.
886
+ * @returns The recovered and skipped `taskId:reason` entries.
887
+ */
888
+ declare function runOrphanRecovery(deps: {
889
+ reconcile: () => Promise<{
890
+ convergedTasks: TaskItem[];
891
+ }>;
892
+ callerFor: TopCallerRecoveryDeps["callerFor"];
893
+ resume: TopCallerRecoveryDeps["resume"];
894
+ log: {
895
+ info(msg: string, ctx: Record<string, unknown>): void;
896
+ warn(msg: string, ctx: Record<string, unknown>): void;
897
+ };
898
+ }): Promise<{
899
+ recovered: string[];
900
+ skipped: string[];
901
+ }>;
902
+
903
+ /**
904
+ * Shared orphan-recovery runtime: the startup sweep and the on-demand
905
+ * single-task entry point share one dependency shape and one lifecycle.
906
+ *
907
+ * @remarks
908
+ * `recoverAll()` is the behavior-preserving move of the gateway startup block
909
+ * (reconcile every tenant's orphaned ordinary tasks, then backfill the
910
+ * top-level caller). `recoverTask()` is the A-lite on-demand entry: no HTTP
911
+ * route, just a programmatic call used by the `task:recover` CLI/script.
912
+ */
913
+
914
+ /** Dependencies shared by the startup sweep and the single-task entry. */
915
+ interface OrphanRecoveryRuntimeDeps {
916
+ /** Task store used to enumerate tenants' orphans and read one task by id. */
917
+ taskStore: TaskStore;
918
+ /** Work-item store used to build the lifecycle when `lifecycle` is omitted. */
919
+ workItemStore: TaskWorkItemStore;
920
+ /** Tenant store supplying `getAllTenants()` for the startup sweep. */
921
+ tenantStore: Pick<TenantStore, "getAllTenants">;
922
+ /** Lifecycle used to converge orphans (built from the stores when omitted). */
923
+ lifecycle?: Pick<TaskLifecycleService, "failTask">;
924
+ /** Resolve a caller's agent client + config from the resolved top caller. */
925
+ callerFor: TopCallerRecoveryDeps["callerFor"];
926
+ /** Resume the continuation (tests can call client.invoke(null, config)). */
927
+ resume: TopCallerRecoveryDeps["resume"];
928
+ /** Structured logger. */
929
+ log: {
930
+ info(msg: string, ctx: Record<string, unknown>): void;
931
+ warn(msg: string, ctx: Record<string, unknown>): void;
932
+ };
933
+ }
934
+ /** Entry points returned by {@link createOrphanRecoveryRuntime}. */
935
+ interface OrphanRecoveryRuntime {
936
+ /** Startup/interval sweep over every tenant's orphaned ordinary tasks. */
937
+ recoverAll(): Promise<{
938
+ recovered: string[];
939
+ skipped: string[];
940
+ }>;
941
+ /**
942
+ * On-demand recovery of exactly one task within one tenant.
943
+ *
944
+ * @remarks Offline/maintenance: run when the Gateway is stopped, or from the
945
+ * Gateway process. The `live` guard reads the process-local task registry and
946
+ * cannot see a run held by another process. Governed Project tasks are refused
947
+ * (`skipped:project_task`) so this never bypasses their managed runtime.
948
+ */
949
+ recoverTask(input: {
950
+ tenantId: string;
951
+ taskId: string;
952
+ }): Promise<RecoverTaskResult>;
953
+ }
954
+ /**
955
+ * Builds the shared orphan-recovery runtime.
956
+ *
957
+ * @param deps Task/work-item/tenant stores, optional lifecycle, caller
958
+ * resolver, resume hook, and logger.
959
+ * @returns `recoverAll()` (startup sweep) and `recoverTask()` (on-demand).
960
+ * @remarks
961
+ * Governed Project tasks are excluded from `recoverAll()` (they have their own
962
+ * observer-based reconciliation) and from `recoverTask()`
963
+ * (`skipped:project_task`), so the on-demand entry can never bypass the managed
964
+ * Project runtime. `recoverTask()` delegates to {@link recoverSingleTask} with
965
+ * the shared lifecycle and the process-local live-run registry, so it never
966
+ * converges a task a live run still holds — in-process only.
967
+ *
968
+ * @example
969
+ * ```ts
970
+ * const runtime = createOrphanRecoveryRuntime({ taskStore, workItemStore, tenantStore, callerFor, resume, log });
971
+ * await runtime.recoverAll();
972
+ * const outcome = await runtime.recoverTask({ tenantId, taskId });
973
+ * ```
974
+ */
975
+ declare function createOrphanRecoveryRuntime(deps: OrphanRecoveryRuntimeDeps): OrphanRecoveryRuntime;
976
+
977
+ /**
978
+ * Builds the caller-resolution and resume hooks used by orphan recovery.
979
+ *
980
+ * @returns `callerFor` (resolves a top caller's agent client + config, omitting
981
+ * the in-memory `agent` when it is absent) and `resume` (prefers
982
+ * `agent.resumeTask()`, otherwise a raw checkpoint continuation via
983
+ * `client.invoke(null, config)`).
984
+ * @remarks
985
+ * `callerFor` uses `getAgentClientAsync` (falls back to `getAgentClient`) so a
986
+ * DB-backed assistant that is not resident in memory can still be loaded.
987
+ */
988
+ declare function createRecoveryCallerDeps(): Pick<TopCallerRecoveryDeps, "callerFor" | "resume">;
989
+
767
990
  /**
768
991
  * Logger configuration for gateway
769
992
  */
@@ -794,4 +1017,4 @@ declare const LatticeGateway: {
794
1017
  AgentTaskConsumer: typeof AgentTaskConsumer;
795
1018
  };
796
1019
 
797
- export { type GatewayLoggerConfig, LatticeGateway, type LatticeGatewayConfig };
1020
+ export { type GatewayLoggerConfig, LatticeGateway, type LatticeGatewayConfig, type OrphanRecoveryRuntime, type OrphanRecoveryRuntimeDeps, type RecoverTaskDeps, type RecoverTaskResult, createOrphanRecoveryRuntime, createRecoveryCallerDeps, recoverTask, recoverTopCaller, resolveTopCaller, runOrphanRecovery };