{"version":3,"file":"load.mjs","names":[],"sources":["../../../../../../../ai/src/orchestrator/load.ts"],"sourcesContent":["import type { CheckpointRecord } from \"../contracts/orchestrator/checkpoint-store.contract\";\nimport type { OrchestratorEngineContext } from \"./engine-context.type\";\n\n/**\n * Outcome of Phase 1 — load session (orchestrator.md §4 Phase 1).\n *\n * `record` is the latest persisted checkpoint, or `undefined` for a\n * brand-new session. `state` is the starting accumulator the turn\n * mutates: the rehydrated `state` on a subsequent call, or the\n * `config.state ?? {}` seed on first call (the framework never\n * re-seeds from `config.state` once a session exists — §4 Phase 1).\n * `turnIndex` is the index of the turn ABOUT to run (loaded + 1, or 0\n * on first call). `previousTurnIndex` is the loaded value (or -1 when\n * none) — needed by resume's `runId` derivation (§9.1).\n */\nexport type LoadedSession<TState> = {\n  /** Latest persisted checkpoint, or `undefined` for a new session. */\n  record: CheckpointRecord | undefined;\n  /** Whether a prior checkpoint existed (drives `session.loaded.found`). */\n  found: boolean;\n  /** Starting state accumulator for this turn. */\n  state: TState;\n  /** Index of the turn about to run. */\n  turnIndex: number;\n  /** Index of the last settled turn (-1 when the session is new). */\n  previousTurnIndex: number;\n};\n\n/**\n * Deep-clone a JSON-serializable value so a rehydrated checkpoint's\n * `state` can be mutated by the turn without aliasing the stored row\n * (the in-memory store hands back live references). Mirrors the\n * round-trip semantics the design mandates for state (§5 — \"JSON-\n * serializable only\", `JSON.parse(JSON.stringify(...))`-equivalent).\n */\nfunction cloneState<TState>(state: unknown): TState {\n  if (state === undefined || state === null) {\n    return {} as TState;\n  }\n\n  return JSON.parse(JSON.stringify(state)) as TState;\n}\n\n/**\n * Phase 1 — load session. Reads the latest checkpoint for the session\n * and resolves the starting state accumulator + the turn index about\n * to run.\n *\n * First-call seeding (Q2): when no checkpoint exists this is the\n * session's birth — `state` defaults to `config.state ?? {}` and\n * `turnIndex` is 0. Subsequent calls rehydrate the persisted `state`\n * and advance the turn index. The dev-passed `options.history` is the\n * per-call seed (Path 2 — the framework never persists messages), so\n * load does not touch history.\n *\n * Does NOT apply the per-call `state` patch — that shallow-merges over\n * this result in the dispatch phase (§5), where the supervisor seed is\n * assembled.\n */\nexport async function loadSession<TState>(\n  ctx: OrchestratorEngineContext<unknown, TState>,\n  sessionId: string,\n): Promise<LoadedSession<TState>> {\n  const record = await ctx.checkpointStore.load(ctx.config.name, sessionId);\n\n  if (!record) {\n    return {\n      record: undefined,\n      found: false,\n      state: cloneState<TState>(ctx.config.state),\n      turnIndex: 0,\n      previousTurnIndex: -1,\n    };\n  }\n\n  return {\n    record,\n    found: true,\n    state: cloneState<TState>(record.state),\n    turnIndex: record.turn_index + 1,\n    previousTurnIndex: record.turn_index,\n  };\n}\n"],"mappings":";;;;;;;;AAmCA,SAAS,WAAmB,OAAwB;CAClD,IAAI,UAAU,UAAa,UAAU,MACnC,OAAO,CAAC;CAGV,OAAO,KAAK,MAAM,KAAK,UAAU,KAAK,CAAC;AACzC;;;;;;;;;;;;;;;;;AAkBA,eAAsB,YACpB,KACA,WACgC;CAChC,MAAM,SAAS,MAAM,IAAI,gBAAgB,KAAK,IAAI,OAAO,MAAM,SAAS;CAExE,IAAI,CAAC,QACH,OAAO;EACL,QAAQ;EACR,OAAO;EACP,OAAO,WAAmB,IAAI,OAAO,KAAK;EAC1C,WAAW;EACX,mBAAmB;CACrB;CAGF,OAAO;EACL;EACA,OAAO;EACP,OAAO,WAAmB,OAAO,KAAK;EACtC,WAAW,OAAO,aAAa;EAC/B,mBAAmB,OAAO;CAC5B;AACF"}