File size: 1,533 Bytes
5710dd0 | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 | /**
* Serialize a `ChatState` into a plain, JSON-shaped object for the audit
* panel's state tree and structural diff. Maps become key-sorted plain
* objects (stable display order); everything else is passed through by
* reference (state is immutable, so sharing is safe and keeps the
* reference-equality fast path in `diffValue` useful).
*/
import type {
InteractionMessage,
SessionStateMessage,
TaskMessage,
TodoMessage,
} from '@moonshot-ai/kap-server/protocol';
import type { ChatState, TimelineMessage } from '../transcript/store';
/** Plain-object view of a `ChatState` (Maps unwrapped). */
export interface SerializedChatState {
readonly timeline: readonly TimelineMessage[];
readonly interactions: Record<string, InteractionMessage>;
readonly tasks: Record<string, TaskMessage>;
readonly todos: Record<string, TodoMessage>;
readonly sessionState: SessionStateMessage | undefined;
readonly hasMoreOlder: boolean;
}
function mapToSortedObject<V>(map: ReadonlyMap<string, V>): Record<string, V> {
const out: Record<string, V> = {};
for (const key of [...map.keys()].toSorted()) out[key] = map.get(key) as V;
return out;
}
export function serializeState(state: ChatState): SerializedChatState {
return {
timeline: state.entries.map((entry) => entry.message),
interactions: mapToSortedObject(state.interactions),
tasks: mapToSortedObject(state.tasks),
todos: mapToSortedObject(state.todos),
sessionState: state.sessionState,
hasMoreOlder: state.hasMoreOlder,
};
}
|