Converts raw `HistoricalMessage` records from GraphQL/API responses into display-ready `ProcessedMessage` arrays, grouping consecutive assistant turns, resolving approval states, and extracting escalated approvals. ## Key Components ### Exports - **`processHistoricalMessages(messages, options)`** — Main entry point. Iterates over historical messages, groups assistant turns using an accumulator, flushes user/system messages inline, and returns a `ProcessHistoricalMessagesResult`. - **`ProcessHistoricalMessagesResult`** — Return type containing `messages: ProcessedMessage[]` and `escalatedApprovals: Map`. ### Internal Functions - **`processMessageData(data, accumulator, approvalStatuses, options, escalatedApprovals)`** — Dispatches a single `MessageData` item to the appropriate accumulator method based on `MESSAGE_TYPE` (`TEXT`, `THINKING`, `EXECUTING_TOOL`, `EXECUTED_TOOL`, `APPROVAL_REQUEST`). - **`flushAssistantMessage()`** — Drains the `MessageSegmentAccumulator` into a single assistant `ProcessedMessage`, using the last message ID in the group for stable React keys. Resets all grouping state unconditionally. - **`getOwnerDisplayName(owner)`** — Resolves a human-readable sender name from a `MessageOwner` (admin full name, or `'You'` for clients). - **`getOwnerAvatar(owner)`** — Extracts the admin's profile image URL from the owner, if present. - **`pushStandaloneMessages(processedMessages, msg, messageDataArray)`** — Emits `SYSTEM`-type messages directly as `role: 'user'` entries with `authorType: 'system'`. ## Usage Example ```typescript import { processHistoricalMessages } from './process-historical-messages' const { messages, escalatedApprovals } = processHistoricalMessages( rawHistoricalMessages, { assistantName: 'Fae', assistantType: 'fae', assistantAvatar: '/avatars/fae.png', approvalStatuses: { 'req-123': 'approved' }, displayApprovalTypes: ['CLIENT'], batchApprovalsEnabled: true, onApprove: (id) => console.log('Approved', id), onReject: (id) => console.log('Rejected', id), } ) // Render messages messages.forEach((msg) => console.log(msg.role, msg.content)) // Handle approvals that require elevated review escalatedApprovals.forEach((approval, id) => { console.log(`Escalated: ${id}`, approval.command) }) ``` ## Notes - `displayApprovalTypes` intentionally has **no default** on the history path — omitting it displays all approval types, preserving pre-existing history semantics and avoiding silent data loss on reload. - `batchApprovalsEnabled` defaults to `true` so consumers without the flag still receive the batch approval UI. - `streamSeq` is propagated via `Math.max` across rows in an assistant group, ensuring accurate history-merge coverage downstream. **Source:** [`process-historical-messages.ts`](https://github.com/flamingo-stack/openframe-oss-lib/blob/main/process-historical-messages.ts)