@thru/replay 0.2.4 → 0.2.5

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.
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/chain-client.ts","../src/async-queue.ts","../src/dedup-buffer.ts","../src/logger.ts","../src/live-pump.ts","../src/retry.ts","../src/replay-stream.ts","../src/replay/helpers.ts","../src/replay/block-replay.ts","../src/replay/transaction-replay.ts","../src/types.ts","../src/replay/event-replay.ts","../src/page-assembler.ts","../src/account-replay.ts","../src/sinks/console.ts"],"names":["createClient","QueryService","StreamingService","create","GetAccountRequestSchema","ListAccountsRequestSchema","ListBlocksRequestSchema","StreamBlocksRequestSchema","ListTransactionsRequestSchema","StreamTransactionsRequestSchema","ListEventsRequestSchema","StreamEventsRequestSchema","createGrpcTransport","StreamAccountUpdatesRequestSchema","GetHeightRequestSchema","delay","FilterSchema","PageRequestSchema","DEFAULT_PAGE_SIZE","DEFAULT_SAFETY_MARGIN","PAGE_ORDER_ASC","EventSchema","bytesToHex","FilterParamValueSchema","AccountView","PubkeySchema"],"mappings":"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","file":"index.cjs","sourcesContent":["import { create } from \"@bufbuild/protobuf\";\nimport {\n type CallOptions,\n createClient,\n type Interceptor,\n type Transport,\n} from \"@connectrpc/connect\";\nimport { createGrpcTransport } from \"@connectrpc/connect-node\";\nimport {\n QueryService,\n StreamingService,\n type GetHeightRequest,\n GetHeightRequestSchema,\n type GetHeightResponse,\n type GetAccountRequest,\n GetAccountRequestSchema,\n type Account,\n type ListAccountsRequest,\n ListAccountsRequestSchema,\n type ListAccountsResponse,\n type ListBlocksRequest,\n ListBlocksRequestSchema,\n type ListBlocksResponse,\n type ListEventsRequest,\n ListEventsRequestSchema,\n type ListEventsResponse,\n type ListTransactionsRequest,\n ListTransactionsRequestSchema,\n type ListTransactionsResponse,\n type StreamBlocksRequest,\n StreamBlocksRequestSchema,\n type StreamBlocksResponse,\n type StreamEventsRequest,\n StreamEventsRequestSchema,\n type StreamEventsResponse,\n type StreamTransactionsRequest,\n StreamTransactionsRequestSchema,\n type StreamTransactionsResponse,\n type StreamAccountUpdatesRequest,\n StreamAccountUpdatesRequestSchema,\n type StreamAccountUpdatesResponse,\n} from \"@thru/proto\";\n\nexport interface ChainClientOptions {\n baseUrl?: string;\n apiKey?: string;\n userAgent?: string;\n transport?: Transport;\n interceptors?: Interceptor[];\n callOptions?: CallOptions;\n useBinaryFormat?: boolean;\n}\n\n/**\n * Factory function that creates fresh ChainClient instances.\n * Called on each reconnection to ensure a new gRPC transport.\n */\nexport type ChainClientFactory = () => ChainClient;\n\nexport interface BlockSource {\n listBlocks(request: Partial<ListBlocksRequest>): Promise<ListBlocksResponse>;\n streamBlocks(request: Partial<StreamBlocksRequest>): AsyncIterable<StreamBlocksResponse>;\n}\n\nexport interface TransactionSource {\n listTransactions(\n request: Partial<ListTransactionsRequest>,\n ): Promise<ListTransactionsResponse>;\n streamTransactions(\n request: Partial<StreamTransactionsRequest>,\n ): AsyncIterable<StreamTransactionsResponse>;\n}\n\nexport interface EventSource {\n listEvents(request: Partial<ListEventsRequest>): Promise<ListEventsResponse>;\n streamEvents(\n request: Partial<StreamEventsRequest>,\n ): AsyncIterable<StreamEventsResponse>;\n}\n\nexport interface AccountSource {\n getAccount(request: Partial<GetAccountRequest>): Promise<Account>;\n listAccounts(request: Partial<ListAccountsRequest>): Promise<ListAccountsResponse>;\n streamAccountUpdates(\n request: Partial<StreamAccountUpdatesRequest>,\n ): AsyncIterable<StreamAccountUpdatesResponse>;\n}\n\nexport type ReplayDataSource = BlockSource & TransactionSource & EventSource & AccountSource;\n\nexport class ChainClient implements ReplayDataSource {\n private readonly query: ReturnType<typeof createClient<typeof QueryService>>;\n private readonly streaming: ReturnType<typeof createClient<typeof StreamingService>>;\n private readonly callOptions?: CallOptions;\n\n constructor(private readonly options: ChainClientOptions) {\n const transport = options.transport ?? this.createTransport();\n this.query = createClient(QueryService, transport);\n this.streaming = createClient(StreamingService, transport);\n this.callOptions = options.callOptions;\n }\n\n getAccount(request: Partial<GetAccountRequest>): Promise<Account> {\n return this.query.getAccount(create(GetAccountRequestSchema, request), this.callOptions);\n }\n\n listAccounts(request: Partial<ListAccountsRequest>): Promise<ListAccountsResponse> {\n return this.query.listAccounts(create(ListAccountsRequestSchema, request), this.callOptions);\n }\n\n listBlocks(request: Partial<ListBlocksRequest>): Promise<ListBlocksResponse> {\n return this.query.listBlocks(create(ListBlocksRequestSchema, request), this.callOptions);\n }\n\n streamBlocks(\n request: Partial<StreamBlocksRequest>,\n ): AsyncIterable<StreamBlocksResponse> {\n return this.streaming.streamBlocks(create(StreamBlocksRequestSchema, request), this.callOptions);\n }\n\n listTransactions(\n request: Partial<ListTransactionsRequest>,\n ): Promise<ListTransactionsResponse> {\n return this.query.listTransactions(create(ListTransactionsRequestSchema, request), this.callOptions);\n }\n\n streamTransactions(\n request: Partial<StreamTransactionsRequest>,\n ): AsyncIterable<StreamTransactionsResponse> {\n return this.streaming.streamTransactions(create(StreamTransactionsRequestSchema, request), this.callOptions);\n }\n\n listEvents(request: Partial<ListEventsRequest>): Promise<ListEventsResponse> {\n return this.query.listEvents(create(ListEventsRequestSchema, request), this.callOptions);\n }\n\n streamEvents(\n request: Partial<StreamEventsRequest>,\n ): AsyncIterable<StreamEventsResponse> {\n return this.streaming.streamEvents(create(StreamEventsRequestSchema, request), this.callOptions);\n }\n\n private createTransport(): Transport {\n if (!this.options.baseUrl) {\n throw new Error(\"ChainClient requires baseUrl when no transport is provided\");\n }\n\n const headerInterceptor = this.createHeaderInterceptor();\n const userInterceptors = this.options.interceptors ?? [];\n const mergedInterceptors = [\n ...userInterceptors,\n ...(headerInterceptor ? [headerInterceptor] : []),\n ];\n\n return createGrpcTransport({\n baseUrl: this.options.baseUrl,\n useBinaryFormat: this.options.useBinaryFormat ?? true,\n interceptors: mergedInterceptors.length ? mergedInterceptors : undefined,\n pingIntervalMs: 30_000,\n pingIdleConnection: true,\n pingTimeoutMs: 10_000,\n idleConnectionTimeoutMs: 0,\n });\n }\n\n private createHeaderInterceptor(): Interceptor | null {\n const headers: Record<string, string> = {};\n if (this.options.apiKey) headers.Authorization = `Bearer ${this.options.apiKey}`;\n if (this.options.userAgent) headers[\"User-Agent\"] = this.options.userAgent;\n if (!Object.keys(headers).length) return null;\n return (next) => async (req) => {\n for (const [key, value] of Object.entries(headers)) req.header.set(key, value);\n return next(req);\n };\n }\n\n streamAccountUpdates(\n request: Partial<StreamAccountUpdatesRequest>,\n ): AsyncIterable<StreamAccountUpdatesResponse> {\n return this.streaming.streamAccountUpdates(create(StreamAccountUpdatesRequestSchema, request), this.callOptions);\n }\n\n getHeight(): Promise<GetHeightResponse> {\n return this.query.getHeight(create(GetHeightRequestSchema, {}), this.callOptions);\n }\n}\n","type Resolver<T> = (result: IteratorResult<T>) => void;\ntype Rejecter = (err: unknown) => void;\n\nexport class AsyncQueue<T> implements AsyncIterable<T> {\n private readonly values: T[] = [];\n private readonly pending: Array<{ resolve: Resolver<T>; reject: Rejecter }> = [];\n private closed = false;\n private failure: unknown;\n\n push(value: T): void {\n if (this.closed) throw new Error(\"Cannot push into a closed queue\");\n if (this.failure) throw this.failure;\n const waiter = this.pending.shift();\n if (waiter) waiter.resolve({ value, done: false });\n else this.values.push(value);\n }\n\n next(): Promise<IteratorResult<T>> {\n if (this.failure) return Promise.reject(this.failure);\n if (this.values.length) {\n const value = this.values.shift()!;\n return Promise.resolve({ value, done: false });\n }\n if (this.closed) return Promise.resolve({ value: undefined as never, done: true });\n return new Promise((resolve, reject) => {\n this.pending.push({ resolve, reject });\n });\n }\n\n close(): void {\n this.closed = true;\n while (this.pending.length) {\n const waiter = this.pending.shift();\n waiter?.resolve({ value: undefined as never, done: true });\n }\n }\n\n fail(err: unknown): void {\n this.failure = err ?? new Error(\"AsyncQueue failure\");\n while (this.pending.length) {\n const waiter = this.pending.shift();\n waiter?.reject(this.failure);\n }\n }\n\n get isClosed(): boolean {\n return this.closed;\n }\n\n [Symbol.asyncIterator](): AsyncIterator<T> {\n return {\n next: () => this.next(),\n };\n }\n}\n","import type { Slot } from \"./types\";\n\ninterface DedupBufferOptions<T> {\n slotOf: (item: T) => Slot;\n keyOf: (item: T) => string;\n}\n\nexport class DedupBuffer<T> {\n private readonly slotOf: (item: T) => Slot;\n private readonly keyOf: (item: T) => string;\n private readonly slots: Slot[] = [];\n private readonly itemsBySlot = new Map<Slot, Map<string, T>>();\n private sizeValue = 0;\n\n constructor(options: DedupBufferOptions<T>) {\n this.slotOf = options.slotOf;\n this.keyOf = options.keyOf;\n }\n\n insert(item: T): boolean {\n const slot = this.slotOf(item);\n const key = this.keyOf(item);\n let bucket = this.itemsBySlot.get(slot);\n if (!bucket) {\n bucket = new Map();\n this.itemsBySlot.set(slot, bucket);\n const idx = this.findInsertIndex(slot);\n this.slots.splice(idx, 0, slot);\n }\n if (bucket.has(key)) return false;\n bucket.set(key, item);\n this.sizeValue += 1;\n return true;\n }\n\n discardUpTo(cutoff: Slot): number {\n let removed = 0;\n while (this.slots.length && this.slots[0] <= cutoff) {\n const slot = this.slots.shift()!;\n const bucket = this.itemsBySlot.get(slot);\n if (!bucket) continue;\n removed += bucket.size;\n this.itemsBySlot.delete(slot);\n }\n this.sizeValue = Math.max(0, this.sizeValue - removed);\n return removed;\n }\n\n drainAbove(cutoff: Slot): T[] {\n if (!this.slots.length) return [];\n const drained: T[] = [];\n const keep: Slot[] = [];\n for (const slot of this.slots) {\n if (slot > cutoff) {\n const bucket = this.itemsBySlot.get(slot);\n if (bucket) {\n for (const item of bucket.values()) drained.push(item);\n this.itemsBySlot.delete(slot);\n this.sizeValue -= bucket.size;\n }\n } else {\n keep.push(slot);\n }\n }\n this.slots.length = 0;\n this.slots.push(...keep);\n return drained;\n }\n\n drainAll(): T[] {\n if (!this.slots.length) return [];\n const drained: T[] = [];\n for (const slot of this.slots) {\n const bucket = this.itemsBySlot.get(slot);\n if (!bucket) continue;\n for (const item of bucket.values()) drained.push(item);\n this.sizeValue -= bucket.size;\n this.itemsBySlot.delete(slot);\n }\n this.slots.length = 0;\n return drained;\n }\n\n minSlot(): Slot | null {\n return this.slots.length ? this.slots[0] : null;\n }\n\n get size(): number {\n return this.sizeValue;\n }\n\n private findInsertIndex(slot: Slot): number {\n let low = 0;\n let high = this.slots.length;\n while (low < high) {\n const mid = (low + high) >> 1;\n if (this.slots[mid] < slot) low = mid + 1;\n else high = mid;\n }\n return low;\n }\n}\n","import type { ReplayLogger } from \"./types\";\n\nconst noop = (): void => undefined;\n\nexport const NOOP_LOGGER: ReplayLogger = {\n debug: noop,\n info: noop,\n warn: noop,\n error: noop,\n};\n\nexport function createConsoleLogger(prefix = \"Replay\"): ReplayLogger {\n return {\n debug: (message, meta) => console.debug(`[${prefix}] ${message}`, meta ?? \"\"),\n info: (message, meta) => console.info(`[${prefix}] ${message}`, meta ?? \"\"),\n warn: (message, meta) => console.warn(`[${prefix}] ${message}`, meta ?? \"\"),\n error: (message, meta) => console.error(`[${prefix}] ${message}`, meta ?? \"\"),\n };\n}\n","import { AsyncQueue } from \"./async-queue\";\nimport { DedupBuffer } from \"./dedup-buffer\";\nimport { NOOP_LOGGER } from \"./logger\";\nimport type { ReplayLogger, Slot } from \"./types\";\n\ntype PumpMode = \"buffering\" | \"streaming\";\n\nexport class LivePump<T> {\n private readonly queue = new AsyncQueue<T>();\n private readonly buffer: DedupBuffer<T>;\n private readonly slotOf: (item: T) => Slot;\n private readonly keyOf: (item: T) => string;\n private readonly source: AsyncIterable<T>;\n private readonly logger: ReplayLogger;\n private mode: PumpMode;\n private minSlotSeen: Slot | null = null;\n private maxSlotSeen: Slot | null = null;\n private minEmitSlot: Slot | null = null;\n private pumpPromise: Promise<void>;\n\n constructor(options: {\n source: AsyncIterable<T>;\n slotOf: (item: T) => Slot;\n keyOf?: (item: T) => string;\n logger?: ReplayLogger;\n startInStreamingMode?: boolean;\n initialEmitFloor?: Slot;\n }) {\n this.source = options.source;\n this.slotOf = options.slotOf;\n this.keyOf = options.keyOf ?? ((item) => options.slotOf(item).toString());\n this.logger = options.logger ?? NOOP_LOGGER;\n this.buffer = new DedupBuffer({ slotOf: this.slotOf, keyOf: this.keyOf });\n this.mode = options.startInStreamingMode ? \"streaming\" : \"buffering\";\n if (options.startInStreamingMode) this.minEmitSlot = options.initialEmitFloor ?? 0n;\n this.pumpPromise = this.start();\n }\n\n minSlot(): Slot | null {\n if (this.minSlotSeen !== null) return this.minSlotSeen;\n return this.buffer.minSlot();\n }\n\n maxSlot(): Slot | null {\n return this.maxSlotSeen;\n }\n\n bufferedSize(): number {\n return this.buffer.size;\n }\n\n discardBufferedUpTo(cutoffSlot: Slot): number {\n if (this.mode === \"streaming\") return 0;\n const discarded = this.buffer.discardUpTo(cutoffSlot);\n if (discarded) {\n this.logger.debug(\n `discarded ${discarded} buffered items up to cutoff slot ${cutoffSlot}`\n );\n }\n return discarded;\n }\n\n enableStreaming(cutoffSlot: Slot): { drained: T[]; discarded: number } {\n if (this.mode === \"streaming\") return { drained: [], discarded: 0 };\n const discarded = this.discardBufferedUpTo(cutoffSlot);\n const drained = this.buffer.drainAbove(cutoffSlot);\n this.mode = \"streaming\";\n this.minEmitSlot = cutoffSlot;\n return { drained, discarded };\n }\n\n updateEmitFloor(slot: Slot): void {\n this.minEmitSlot = slot;\n }\n\n async next(): Promise<IteratorResult<T>> {\n return this.queue.next();\n }\n\n async close(): Promise<void> {\n this.queue.close();\n await this.pumpPromise;\n }\n\n private async start(): Promise<void> {\n try {\n for await (const item of this.source) {\n const slot = this.slotOf(item);\n if (this.minSlotSeen === null || slot < this.minSlotSeen) this.minSlotSeen = slot;\n if (this.maxSlotSeen === null || slot > this.maxSlotSeen) this.maxSlotSeen = slot;\n if (this.mode === \"buffering\") this.buffer.insert(item);\n else {\n if (this.minEmitSlot !== null && slot < this.minEmitSlot) continue;\n this.queue.push(item);\n }\n }\n this.queue.close();\n } catch (err) {\n // Don't log here - let the consumer (ReplayStream) handle logging\n // since it knows whether a retry will happen\n this.queue.fail(err);\n }\n }\n}\n","/**\n * Retry utilities for stream reconnection with exponential backoff.\n */\n\nexport interface RetryConfig {\n /** Initial delay before first retry (default: 1000ms) */\n initialDelayMs: number;\n /** Maximum delay between retries (default: 30000ms) */\n maxDelayMs: number;\n /** Timeout for connection/read operations (default: 30000ms) */\n connectionTimeoutMs: number;\n}\n\nexport const DEFAULT_RETRY_CONFIG: RetryConfig = {\n initialDelayMs: 1000,\n maxDelayMs: 30000,\n connectionTimeoutMs: 300_000,\n};\n\n/**\n * Calculate exponential backoff delay for a given attempt number.\n * Starts at initialDelayMs and doubles each attempt, capped at maxDelayMs.\n *\n * @param attempt - Zero-based attempt number (0 = first retry)\n * @param config - Retry configuration\n * @returns Delay in milliseconds\n */\nexport function calculateBackoff(attempt: number, config: RetryConfig): number {\n const delay = config.initialDelayMs * Math.pow(2, attempt);\n return Math.min(delay, config.maxDelayMs);\n}\n\n/**\n * Wrap a promise with a timeout. Rejects with TimeoutError if the promise\n * doesn't resolve within the specified time.\n *\n * @param promise - Promise to wrap\n * @param timeoutMs - Timeout in milliseconds\n * @returns Promise that resolves with the original value or rejects on timeout\n */\nexport function withTimeout<T>(\n promise: Promise<T>,\n timeoutMs: number\n): Promise<T> {\n return new Promise<T>((resolve, reject) => {\n const timer = setTimeout(() => {\n reject(new TimeoutError(`Operation timed out after ${timeoutMs}ms`));\n }, timeoutMs);\n\n promise\n .then((value) => {\n clearTimeout(timer);\n resolve(value);\n })\n .catch((err) => {\n clearTimeout(timer);\n reject(err);\n });\n });\n}\n\n/**\n * Error thrown when an operation times out.\n */\nexport class TimeoutError extends Error {\n constructor(message: string) {\n super(message);\n this.name = \"TimeoutError\";\n }\n}\n\n/**\n * Delay execution for a specified number of milliseconds.\n */\nexport function delay(ms: number): Promise<void> {\n return new Promise((resolve) => setTimeout(resolve, ms));\n}\n","import { LivePump } from \"./live-pump\";\nimport { NOOP_LOGGER } from \"./logger\";\nimport {\n DEFAULT_RETRY_CONFIG,\n calculateBackoff,\n withTimeout,\n delay,\n type RetryConfig,\n} from \"./retry\";\nimport type { BackfillFetcher, LiveSubscriber, ReplayConfig, ReplayMetrics, Slot } from \"./types\";\n\nconst DEFAULT_METRICS: ReplayMetrics = {\n bufferedItems: 0,\n emittedBackfill: 0,\n emittedLive: 0,\n emittedReconnect: 0,\n discardedDuplicates: 0,\n};\n\nfunction compareBigint(a: Slot, b: Slot): number {\n if (a === b) return 0;\n return a < b ? -1 : 1;\n}\n\nexport class ReplayStream<T, Cursor = unknown> implements AsyncIterable<T> {\n private readonly config: ReplayConfig<T, Cursor>;\n private readonly logger;\n private readonly metrics: ReplayMetrics = { ...DEFAULT_METRICS };\n\n constructor(config: ReplayConfig<T, Cursor>) {\n this.config = config;\n this.logger = config.logger ?? NOOP_LOGGER;\n }\n\n getMetrics(): ReplayMetrics {\n return { ...this.metrics };\n }\n\n [Symbol.asyncIterator](): AsyncIterator<T> {\n return this.run();\n }\n\n private async *run(): AsyncGenerator<T> {\n const {\n startSlot,\n fetchBackfill,\n subscribeLive,\n extractSlot,\n extractKey,\n safetyMargin,\n resubscribeOnEnd,\n onReconnect,\n } = this.config;\n const shouldResubscribeOnEnd = resubscribeOnEnd ?? true;\n const keyOf = extractKey ?? ((item: T) => extractSlot(item).toString());\n\n // Mutable data sources - may be replaced on reconnection with fresh client\n let currentSubscribeLive: LiveSubscriber<T> = subscribeLive;\n let currentFetchBackfill: BackfillFetcher<T, Cursor> = fetchBackfill;\n\n const createLivePump = (slot: Slot, startStreaming = false, emitFloor?: Slot) =>\n new LivePump<T>({\n source: currentSubscribeLive(slot),\n slotOf: extractSlot,\n keyOf,\n logger: this.logger,\n startInStreamingMode: startStreaming,\n initialEmitFloor: emitFloor,\n });\n let livePump = createLivePump(startSlot);\n\n let cursor: Cursor | undefined;\n let backfillDone = false;\n let currentSlot: Slot = startSlot > 0n ? startSlot - 1n : 0n;\n let lastEmittedSlot: Slot | null = null;\n let lastSlotKeys = new Set<string>();\n\n const seenItem = (slot: Slot, key: string): boolean => {\n if (lastEmittedSlot === null) return false;\n if (slot < lastEmittedSlot) return true;\n if (slot > lastEmittedSlot) return false;\n return lastSlotKeys.has(key);\n };\n\n const recordEmission = (slot: Slot, key: string): void => {\n if (lastEmittedSlot === null || slot !== lastEmittedSlot) {\n lastEmittedSlot = slot;\n lastSlotKeys = new Set([key]);\n } else {\n lastSlotKeys.add(key);\n }\n };\n\n this.logger.info(\n `replay entering BACKFILLING state (startSlot=${startSlot}, safetyMargin=${safetyMargin})`\n );\n\n while (!backfillDone) {\n const page = await fetchBackfill({ startSlot, cursor });\n if (!page.items.length && !page.cursor && !page.done) {\n // Nothing returned but not marked done: continue to avoid tight loops\n this.logger.warn(\"empty backfill page without cursor; retrying\");\n continue;\n }\n\n const sorted = [...page.items].sort((a, b) =>\n compareBigint(extractSlot(a), extractSlot(b)),\n );\n\n for (const item of sorted) {\n const slot = extractSlot(item);\n const key = keyOf(item);\n if (slot < startSlot) continue;\n if (seenItem(slot, key)) {\n this.metrics.discardedDuplicates += 1;\n continue;\n }\n currentSlot = slot;\n recordEmission(slot, key);\n this.metrics.emittedBackfill += 1;\n yield item;\n }\n\n const duplicatesTrimmed = livePump.discardBufferedUpTo(currentSlot);\n this.metrics.discardedDuplicates += duplicatesTrimmed;\n\n cursor = page.cursor;\n\n const maxStreamSlot = livePump.maxSlot();\n if (maxStreamSlot !== null) {\n const catchUpSlot =\n maxStreamSlot > safetyMargin ? (maxStreamSlot - safetyMargin) : 0n;\n if (currentSlot >= catchUpSlot) {\n this.logger.info(\n `replay reached SWITCHING threshold (currentSlot=${currentSlot}, maxStreamSlot=${maxStreamSlot}, catchUpSlot=${catchUpSlot})`\n );\n backfillDone = true;\n }\n }\n\n if (page.done || cursor === undefined) backfillDone = true;\n }\n\n this.logger.info(`replay entering SWITCHING state (currentSlot=${currentSlot})`);\n\n const { drained, discarded } = livePump.enableStreaming(currentSlot);\n this.metrics.bufferedItems = drained.length;\n this.metrics.discardedDuplicates += discarded;\n\n for (const item of drained) {\n const slot = extractSlot(item);\n const key = keyOf(item);\n if (seenItem(slot, key)) {\n this.metrics.discardedDuplicates += 1;\n continue;\n }\n currentSlot = slot;\n recordEmission(slot, key);\n this.metrics.emittedLive += 1;\n yield item;\n livePump.updateEmitFloor(currentSlot);\n }\n if (!drained.length) livePump.updateEmitFloor(currentSlot);\n\n this.logger.info(\"replay entering STREAMING state\");\n const retryConfig = DEFAULT_RETRY_CONFIG;\n let retryAttempt = 0;\n while (true) {\n try {\n // Add timeout to detect hung streams\n const next = await withTimeout(\n livePump.next(),\n retryConfig.connectionTimeoutMs\n );\n retryAttempt = 0; // Reset on successful message\n if (next.done) {\n if (!shouldResubscribeOnEnd) break;\n throw new Error(\"stream ended\");\n }\n const slot = extractSlot(next.value);\n const key = keyOf(next.value);\n if (seenItem(slot, key)) {\n this.metrics.discardedDuplicates += 1;\n continue;\n }\n currentSlot = slot;\n recordEmission(slot, key);\n this.metrics.emittedLive += 1;\n yield next.value;\n livePump.updateEmitFloor(currentSlot);\n } catch (err) {\n const errMsg = err instanceof Error ? err.message : String(err);\n const backoffMs = calculateBackoff(retryAttempt, retryConfig);\n this.logger.warn(\n `live stream disconnected (${errMsg}); reconnecting in ${backoffMs}ms from slot ${currentSlot} (attempt ${retryAttempt + 1})`\n );\n await delay(backoffMs);\n await safeClose(livePump);\n retryAttempt++;\n\n // Get fresh data sources from new client if factory provided\n if (onReconnect) {\n try {\n const fresh = onReconnect();\n currentSubscribeLive = fresh.subscribeLive;\n if (fresh.fetchBackfill) {\n currentFetchBackfill = fresh.fetchBackfill;\n }\n this.logger.info(\"created fresh client for reconnection\");\n } catch (factoryErr) {\n this.logger.error(\n `failed to create fresh client: ${factoryErr instanceof Error ? factoryErr.message : String(factoryErr)}; using existing`\n );\n }\n }\n\n // Mini-backfill to catch any missed events during disconnection\n if (onReconnect && currentSlot > 0n) {\n for await (const item of this.miniBackfill(\n currentSlot,\n currentFetchBackfill,\n extractSlot,\n keyOf,\n seenItem,\n recordEmission\n )) {\n // Update currentSlot as we yield items to prevent gaps\n const itemSlot = extractSlot(item);\n if (itemSlot > currentSlot) {\n currentSlot = itemSlot;\n }\n yield item;\n }\n }\n\n const resumeSlot = currentSlot > 0n ? currentSlot : 0n;\n livePump = createLivePump(resumeSlot, true, currentSlot);\n }\n }\n }\n\n /**\n * Perform mini-backfill from lastProcessedSlot to catch up after reconnection.\n * Ensures no data gaps from events that occurred during disconnection.\n */\n private async *miniBackfill(\n fromSlot: Slot,\n fetchBackfill: BackfillFetcher<T, Cursor>,\n extractSlot: (item: T) => Slot,\n keyOf: (item: T) => string,\n seenItem: (slot: Slot, key: string) => boolean,\n recordEmission: (slot: Slot, key: string) => void\n ): AsyncGenerator<T> {\n this.logger.info(`mini-backfill starting from slot ${fromSlot}`);\n const MINI_BACKFILL_TIMEOUT = 30000; // 30 seconds max\n const startTime = Date.now();\n\n let cursor: Cursor | undefined;\n let itemsYielded = 0;\n\n try {\n while (true) {\n if (Date.now() - startTime > MINI_BACKFILL_TIMEOUT) {\n this.logger.warn(`mini-backfill timed out after ${MINI_BACKFILL_TIMEOUT}ms`);\n break;\n }\n\n const page = await fetchBackfill({ startSlot: fromSlot, cursor });\n\n const sorted = [...page.items].sort((a, b) =>\n compareBigint(extractSlot(a), extractSlot(b))\n );\n\n for (const item of sorted) {\n const slot = extractSlot(item);\n const key = keyOf(item);\n if (seenItem(slot, key)) {\n this.metrics.discardedDuplicates += 1;\n continue;\n }\n recordEmission(slot, key);\n itemsYielded++;\n this.metrics.emittedReconnect += 1;\n yield item;\n }\n\n cursor = page.cursor;\n if (page.done || cursor === undefined) break;\n }\n\n this.logger.info(`mini-backfill complete: ${itemsYielded} items yielded`);\n } catch (err) {\n this.logger.warn(\n `mini-backfill failed: ${err instanceof Error ? err.message : String(err)}; proceeding with live stream`\n );\n }\n }\n}\n\nasync function safeClose<T>(pump: LivePump<T>): Promise<void> {\n try {\n await pump.close();\n } catch {\n /* ignore */\n }\n}\n","import { create } from \"@bufbuild/protobuf\";\nimport { type Filter, FilterSchema, type PageResponse } from \"@thru/proto\";\nimport type { Slot } from \"../types\";\n\nexport function combineFilters(base?: Filter, user?: Filter): Filter | undefined {\n if (!base && !user) return undefined;\n if (!base) return user;\n if (!user) return base;\n const expressionParts: string[] = [];\n if (base.expression) expressionParts.push(`(${base.expression})`);\n if (user.expression) expressionParts.push(`(${user.expression})`);\n return create(FilterSchema, {\n expression: expressionParts.join(\" && \") || undefined,\n params: { ...base.params, ...user.params },\n });\n}\n\nexport function slotLiteralFilter(fieldExpr: string, slot: Slot): Filter {\n return create(FilterSchema, {\n expression: `${fieldExpr} >= uint(${slot.toString()})`,\n });\n}\n\nexport function backfillPage<T>(\n items: T[],\n page?: PageResponse,\n): { items: T[]; cursor?: string; done: boolean } {\n const cursor = page?.nextPageToken ?? undefined;\n return {\n items,\n cursor,\n done: !cursor,\n };\n}\n\nexport async function* mapAsyncIterable<S, T>(\n iterable: AsyncIterable<S>,\n selector: (value: S) => T | null | undefined,\n): AsyncGenerator<T> {\n for await (const value of iterable) {\n const mapped = selector(value);\n if (mapped !== undefined && mapped !== null) yield mapped;\n }\n}\n","import { create } from \"@bufbuild/protobuf\";\nimport {\n type Filter,\n type PageRequest,\n PageRequestSchema,\n type ConsensusStatus,\n type Block,\n type BlockView,\n type ListBlocksRequest,\n ListBlocksRequestSchema,\n type StreamBlocksRequest,\n StreamBlocksRequestSchema,\n type StreamBlocksResponse,\n} from \"@thru/proto\";\nimport type { BlockSource } from \"../chain-client\";\nimport { ReplayStream } from \"../replay-stream\";\nimport { NOOP_LOGGER } from \"../logger\";\nimport type { ReplayLogger, Slot } from \"../types\";\nimport { backfillPage, combineFilters, mapAsyncIterable, slotLiteralFilter } from \"./helpers\";\n\nexport interface BlockReplayOptions {\n client: BlockSource;\n startSlot: Slot;\n safetyMargin?: bigint;\n pageSize?: number;\n filter?: Filter;\n view?: BlockView;\n minConsensus?: ConsensusStatus;\n logger?: ReplayLogger;\n resubscribeOnEnd?: boolean;\n}\n\nconst DEFAULT_PAGE_SIZE = 128;\nconst DEFAULT_SAFETY_MARGIN = 32n;\nconst PAGE_ORDER_ASC = \"slot asc\";\n\nexport function createBlockReplay(options: BlockReplayOptions): ReplayStream<Block, string> {\n const safetyMargin = options.safetyMargin ?? DEFAULT_SAFETY_MARGIN;\n const logger = options.logger ?? NOOP_LOGGER;\n\n const fetchBackfill = async ({\n startSlot,\n cursor,\n }: {\n startSlot: Slot;\n cursor?: string;\n }) => {\n const page = create(PageRequestSchema, {\n pageSize: options.pageSize ?? DEFAULT_PAGE_SIZE,\n orderBy: PAGE_ORDER_ASC,\n pageToken: cursor,\n });\n\n const mergedFilter = combineFilters(slotLiteralFilter(\"block.header.slot\", startSlot), options.filter);\n logger.debug?.(\"block backfill request\", {\n startSlot: startSlot.toString(),\n cursor,\n pageSize: page.pageSize,\n });\n\n let response;\n try {\n response = await options.client.listBlocks(\n create(ListBlocksRequestSchema, {\n filter: mergedFilter,\n page,\n view: options.view,\n minConsensus: options.minConsensus,\n }),\n );\n } catch (err) {\n logger.error(\"block backfill request failed\", {\n startSlot: startSlot.toString(),\n cursor,\n err,\n });\n throw err;\n }\n\n return backfillPage(response.blocks, response.page);\n };\n\n const subscribeLive = (startSlot: Slot): AsyncIterable<Block> => {\n const request = create(StreamBlocksRequestSchema, {\n startSlot,\n filter: options.filter,\n view: options.view,\n minConsensus: options.minConsensus,\n });\n return mapAsyncIterable(\n options.client.streamBlocks(request),\n (resp: StreamBlocksResponse) => resp.block,\n );\n };\n\n return new ReplayStream<Block, string>({\n startSlot: options.startSlot,\n safetyMargin,\n fetchBackfill,\n subscribeLive,\n extractSlot: (block) => block.header?.slot ?? 0n,\n logger: options.logger,\n resubscribeOnEnd: options.resubscribeOnEnd,\n });\n}\n","import { create } from \"@bufbuild/protobuf\";\nimport {\n type Filter,\n type PageRequest,\n PageRequestSchema,\n type ConsensusStatus,\n type Transaction,\n type ListTransactionsRequest,\n ListTransactionsRequestSchema,\n type StreamTransactionsRequest,\n StreamTransactionsRequestSchema,\n type StreamTransactionsResponse,\n} from \"@thru/proto\";\nimport type { TransactionSource } from \"../chain-client\";\nimport { ReplayStream } from \"../replay-stream\";\nimport type { ReplayLogger, Slot } from \"../types\";\nimport { backfillPage, combineFilters, mapAsyncIterable, slotLiteralFilter } from \"./helpers\";\n\nexport interface TransactionReplayOptions {\n client: TransactionSource;\n startSlot: Slot;\n safetyMargin?: bigint;\n pageSize?: number;\n filter?: Filter;\n minConsensus?: ConsensusStatus;\n returnEvents?: boolean;\n logger?: ReplayLogger;\n resubscribeOnEnd?: boolean;\n}\n\nconst DEFAULT_PAGE_SIZE = 256;\nconst DEFAULT_SAFETY_MARGIN = 64n;\nconst PAGE_ORDER_ASC = \"slot asc\";\n\nexport function createTransactionReplay(\n options: TransactionReplayOptions,\n): ReplayStream<Transaction, string> {\n const safetyMargin = options.safetyMargin ?? DEFAULT_SAFETY_MARGIN;\n\n const fetchBackfill = async ({\n startSlot,\n cursor,\n }: {\n startSlot: Slot;\n cursor?: string;\n }) => {\n const page = create(PageRequestSchema, {\n pageSize: options.pageSize ?? DEFAULT_PAGE_SIZE,\n orderBy: PAGE_ORDER_ASC,\n pageToken: cursor,\n });\n\n const mergedFilter = combineFilters(slotLiteralFilter(\"transaction.slot\", startSlot), options.filter);\n const response = await options.client.listTransactions(\n create(ListTransactionsRequestSchema, {\n filter: mergedFilter,\n page,\n minConsensus: options.minConsensus,\n returnEvents: options.returnEvents,\n }),\n );\n\n return backfillPage(response.transactions, response.page);\n };\n\n const subscribeLive = (startSlot: Slot): AsyncIterable<Transaction> => {\n const mergedFilter = combineFilters(slotLiteralFilter(\"transaction.slot\", startSlot), options.filter);\n const request = create(StreamTransactionsRequestSchema, {\n filter: mergedFilter,\n minConsensus: options.minConsensus,\n });\n return mapAsyncIterable(\n options.client.streamTransactions(request),\n (resp: StreamTransactionsResponse) => resp.transaction,\n );\n };\n\n return new ReplayStream<Transaction, string>({\n startSlot: options.startSlot,\n safetyMargin,\n fetchBackfill,\n subscribeLive,\n extractSlot: (tx) => tx.slot ?? 0n,\n extractKey: transactionKey,\n logger: options.logger,\n resubscribeOnEnd: options.resubscribeOnEnd,\n });\n}\n\nfunction transactionKey(tx: Transaction): string {\n const signatureBytes = tx.signature?.value;\n if (signatureBytes && signatureBytes.length) return bytesToHex(signatureBytes);\n const slotPart = tx.slot?.toString() ?? \"0\";\n const offsetPart = tx.blockOffset?.toString() ?? \"0\";\n return `${slotPart}:${offsetPart}`;\n}\n\nfunction bytesToHex(bytes: Uint8Array): string {\n let hex = \"\";\n for (const byte of bytes) hex += byte.toString(16).padStart(2, \"0\");\n return hex;\n}\n","export type Slot = bigint;\n\n/**\n * Options for providing a client instance, a factory, or both.\n * At least one of client or clientFactory must be provided.\n */\nexport interface ClientOrFactory<T> {\n /** Client instance for initial connection. Optional if clientFactory provided. */\n client?: T;\n /** Factory to create fresh clients on reconnection. Enables robust reconnection. */\n clientFactory?: () => T;\n}\n\n/**\n * Resolve a client from ClientOrFactory options.\n * Prefers clientFactory if available, falls back to client.\n * @throws Error if neither client nor clientFactory is provided\n */\nexport function resolveClient<T>(\n opts: ClientOrFactory<T>,\n optionsName: string\n): T {\n if (opts.clientFactory) {\n return opts.clientFactory();\n }\n if (!opts.client) {\n throw new Error(`${optionsName} requires either client or clientFactory`);\n }\n return opts.client;\n}\n\nexport interface BackfillPage<T, Cursor = unknown> {\n items: T[];\n cursor?: Cursor;\n done?: boolean;\n}\n\nexport type BackfillFetcher<T, Cursor = unknown> = (params: {\n startSlot: Slot;\n cursor?: Cursor;\n}) => Promise<BackfillPage<T, Cursor>>;\n\nexport type LiveSubscriber<T> = (startSlot: Slot) => AsyncIterable<T>;\n\nexport interface ReplayLogger {\n debug(message: string, meta?: Record<string, unknown>): void;\n info(message: string, meta?: Record<string, unknown>): void;\n warn(message: string, meta?: Record<string, unknown>): void;\n error(message: string, meta?: Record<string, unknown>): void;\n}\n\nexport interface ReplayMetrics {\n bufferedItems: number;\n emittedBackfill: number;\n emittedLive: number;\n emittedReconnect: number;\n discardedDuplicates: number;\n}\n\n/**\n * Data sources returned by onReconnect callback.\n * Provides fresh functions that use a new client/transport.\n */\nexport interface ReconnectSources<T, Cursor = unknown> {\n subscribeLive: LiveSubscriber<T>;\n fetchBackfill?: BackfillFetcher<T, Cursor>;\n}\n\nexport interface ReplayConfig<T, Cursor = unknown> {\n startSlot: Slot;\n safetyMargin: bigint;\n fetchBackfill: BackfillFetcher<T, Cursor>;\n subscribeLive: LiveSubscriber<T>;\n extractSlot: (item: T) => Slot;\n extractKey?: (item: T) => string;\n logger?: ReplayLogger;\n resubscribeOnEnd?: boolean;\n /**\n * Called on reconnection to get fresh data sources.\n * When provided, creates new client/transport for each reconnection attempt.\n */\n onReconnect?: () => ReconnectSources<T, Cursor>;\n}\n","import { create } from \"@bufbuild/protobuf\";\nimport {\n type Filter,\n type PageRequest,\n PageRequestSchema,\n type Event,\n EventSchema,\n type ListEventsRequest,\n ListEventsRequestSchema,\n type StreamEventsRequest,\n StreamEventsRequestSchema,\n type StreamEventsResponse,\n} from \"@thru/proto\";\nimport type { EventSource } from \"../chain-client\";\nimport { ReplayStream } from \"../replay-stream\";\nimport type { ReplayLogger, Slot } from \"../types\";\nimport { resolveClient } from \"../types\";\nimport { backfillPage, combineFilters, mapAsyncIterable, slotLiteralFilter } from \"./helpers\";\n\nexport interface EventReplayOptions {\n /** Client instance for initial connection. Optional if clientFactory provided. */\n client?: EventSource;\n /** Factory to create fresh clients on reconnection. Enables robust reconnection. */\n clientFactory?: () => EventSource;\n startSlot: Slot;\n safetyMargin?: bigint;\n pageSize?: number;\n filter?: Filter;\n logger?: ReplayLogger;\n resubscribeOnEnd?: boolean;\n}\n\nconst DEFAULT_PAGE_SIZE = 512;\nconst DEFAULT_SAFETY_MARGIN = 64n;\nconst PAGE_ORDER_ASC = \"slot asc\";\n\nexport function createEventReplay(options: EventReplayOptions): ReplayStream<Event, string> {\n const safetyMargin = options.safetyMargin ?? DEFAULT_SAFETY_MARGIN;\n\n // Resolve initial client - either from options or from factory\n let currentClient = resolveClient(options, \"EventReplayOptions\");\n\n const createFetchBackfill = (client: EventSource) => async ({\n startSlot,\n cursor,\n }: {\n startSlot: Slot;\n cursor?: string;\n }) => {\n const page = create(PageRequestSchema, {\n pageSize: options.pageSize ?? DEFAULT_PAGE_SIZE,\n orderBy: PAGE_ORDER_ASC,\n pageToken: cursor,\n });\n\n const baseFilter = slotLiteralFilter(\"event.slot\", startSlot);\n const mergedFilter = combineFilters(baseFilter, options.filter);\n const response = await client.listEvents(\n create(ListEventsRequestSchema, {\n filter: mergedFilter,\n page,\n }),\n );\n\n return backfillPage(response.events, response.page);\n };\n\n const createSubscribeLive = (client: EventSource) => (startSlot: Slot): AsyncIterable<Event> => {\n const mergedFilter = combineFilters(slotLiteralFilter(\"event.slot\", startSlot), options.filter);\n const request = create(StreamEventsRequestSchema, {\n filter: mergedFilter,\n });\n return mapAsyncIterable(\n client.streamEvents(request),\n (resp: StreamEventsResponse) => streamResponseToEvent(resp),\n );\n };\n\n // Reconnection handler - creates fresh client and returns new data source functions\n const onReconnect = options.clientFactory\n ? () => {\n currentClient = options.clientFactory!();\n return {\n subscribeLive: createSubscribeLive(currentClient),\n fetchBackfill: createFetchBackfill(currentClient),\n };\n }\n : undefined;\n\n return new ReplayStream<Event, string>({\n startSlot: options.startSlot,\n safetyMargin,\n fetchBackfill: createFetchBackfill(currentClient),\n subscribeLive: createSubscribeLive(currentClient),\n extractSlot: (event) => event.slot ?? 0n,\n extractKey: eventKey,\n logger: options.logger,\n resubscribeOnEnd: options.resubscribeOnEnd,\n onReconnect,\n });\n}\n\nfunction streamResponseToEvent(resp: StreamEventsResponse): Event {\n return create(EventSchema, {\n eventId: resp.eventId,\n transactionSignature: resp.signature,\n program: resp.program,\n payload: resp.payload,\n slot: resp.slot,\n callIdx: resp.callIdx,\n timestamp: resp.timestamp,\n });\n}\n\nfunction eventKey(event: Event): string {\n if (event.eventId) return event.eventId;\n const slotPart = event.slot?.toString() ?? \"0\";\n return `${slotPart}:${event.callIdx ?? 0}`;\n}\n","/**\n * Page Assembler for multi-page account updates.\n *\n * Large accounts are split into multiple AccountPage messages (4KB chunks).\n * This module buffers pages and emits complete account data when all pages\n * for a given sequence number are received.\n */\n\nimport type { AccountMeta, AccountPage } from \"@thru/proto\";\nimport type { AccountUpdate } from \"@thru/proto\";\n\n/** Standard page size for account data (4KB) */\nexport const PAGE_SIZE = 4096;\n\n/**\n * Represents a buffered page update waiting for assembly\n */\ninterface BufferedPage {\n pageIdx: number;\n pageData: Uint8Array;\n}\n\n/**\n * State for an account update being assembled from pages\n */\ninterface PendingUpdate {\n slot: bigint;\n seq: bigint;\n meta: AccountMeta;\n pages: Map<number, BufferedPage>;\n expectedPageCount: number;\n receivedAt: number;\n}\n\n/**\n * Assembled account data ready for processing\n */\nexport interface AssembledAccount {\n address: Uint8Array;\n slot: bigint;\n seq: bigint;\n meta: AccountMeta;\n data: Uint8Array;\n isDelete: boolean;\n}\n\n/**\n * Options for the PageAssembler\n */\nexport interface PageAssemblerOptions {\n /**\n * Timeout in milliseconds for incomplete page assemblies.\n * After this duration, incomplete assemblies are discarded.\n * Default: 30000 (30 seconds)\n */\n assemblyTimeout?: number;\n\n /**\n * Maximum number of pending assemblies per address.\n * Older assemblies are evicted when limit is exceeded.\n * Default: 10\n */\n maxPendingPerAddress?: number;\n}\n\n/**\n * Convert address bytes to hex string for use as map key\n */\nfunction addressToKey(address: Uint8Array): string {\n return Array.from(address)\n .map((b) => b.toString(16).padStart(2, \"0\"))\n .join(\"\");\n}\n\n/**\n * Calculate expected page count from data size\n */\nfunction calculatePageCount(dataSize: number): number {\n if (dataSize === 0) return 0;\n return Math.ceil(dataSize / PAGE_SIZE);\n}\n\n/**\n * Assembles multi-page account updates into complete account data.\n *\n * Usage:\n * ```typescript\n * const assembler = new PageAssembler();\n *\n * for await (const response of client.streamAccountUpdates(request)) {\n * if (response.message.case === \"update\") {\n * const assembled = assembler.processUpdate(address, response.message.value);\n * if (assembled) {\n * // Complete account data is ready\n * console.log(\"Assembled account:\", assembled);\n * }\n * }\n * }\n * ```\n */\nexport class PageAssembler {\n private readonly assemblyTimeout: number;\n private readonly maxPendingPerAddress: number;\n\n /**\n * Pending updates keyed by address (hex) -> seq (string) -> PendingUpdate\n */\n private pending: Map<string, Map<string, PendingUpdate>> = new Map();\n\n constructor(options: PageAssemblerOptions = {}) {\n this.assemblyTimeout = options.assemblyTimeout ?? 30000;\n this.maxPendingPerAddress = options.maxPendingPerAddress ?? 10;\n }\n\n /**\n * Process an account update and return assembled account if complete.\n *\n * @param address - Account address bytes\n * @param update - Account update from streaming response\n * @returns Assembled account if all pages received, null otherwise\n */\n processUpdate(address: Uint8Array, update: AccountUpdate): AssembledAccount | null {\n const addressKey = addressToKey(address);\n\n // Handle delete updates immediately\n if (update.delete) {\n // Delete doesn't need page assembly\n return {\n address,\n slot: BigInt(update.slot.toString()),\n seq: update.meta?.seq ? BigInt(update.meta.seq.toString()) : 0n,\n meta: update.meta!,\n data: new Uint8Array(0),\n isDelete: true,\n };\n }\n\n // Updates without meta are incomplete - we need meta to know data size\n if (!update.meta) {\n return null;\n }\n\n const seq = BigInt(update.meta.seq.toString());\n const seqKey = seq.toString();\n const slot = BigInt(update.slot.toString());\n\n // Get or create pending updates for this address\n let addressPending = this.pending.get(addressKey);\n if (!addressPending) {\n addressPending = new Map();\n this.pending.set(addressKey, addressPending);\n }\n\n // Get or create pending update for this sequence\n let pendingUpdate = addressPending.get(seqKey);\n if (!pendingUpdate) {\n const expectedPageCount = calculatePageCount(update.meta.dataSize);\n pendingUpdate = {\n slot,\n seq,\n meta: update.meta,\n pages: new Map(),\n expectedPageCount,\n receivedAt: Date.now(),\n };\n addressPending.set(seqKey, pendingUpdate);\n\n // Enforce max pending limit per address\n this.evictOldPending(addressPending);\n }\n\n // Add page if present\n if (update.page) {\n pendingUpdate.pages.set(update.page.pageIdx, {\n pageIdx: update.page.pageIdx,\n pageData: update.page.pageData,\n });\n }\n\n // Check if all pages received\n if (pendingUpdate.pages.size >= pendingUpdate.expectedPageCount) {\n // Remove from pending\n addressPending.delete(seqKey);\n if (addressPending.size === 0) {\n this.pending.delete(addressKey);\n }\n\n // Assemble data from pages\n const data = this.assemblePages(pendingUpdate);\n\n return {\n address,\n slot: pendingUpdate.slot,\n seq: pendingUpdate.seq,\n meta: pendingUpdate.meta,\n data,\n isDelete: false,\n };\n }\n\n return null;\n }\n\n /**\n * Assemble complete data from buffered pages\n */\n private assemblePages(pending: PendingUpdate): Uint8Array {\n const totalSize = pending.meta.dataSize;\n if (totalSize === 0 || pending.expectedPageCount === 0) {\n return new Uint8Array(0);\n }\n\n const result = new Uint8Array(totalSize);\n let offset = 0;\n\n // Assemble pages in order\n for (let i = 0; i < pending.expectedPageCount; i++) {\n const page = pending.pages.get(i);\n if (page) {\n result.set(page.pageData, offset);\n offset += page.pageData.length;\n }\n }\n\n return result;\n }\n\n /**\n * Evict old pending updates for an address if limit exceeded\n */\n private evictOldPending(addressPending: Map<string, PendingUpdate>): void {\n if (addressPending.size <= this.maxPendingPerAddress) {\n return;\n }\n\n // Find oldest entries to evict\n const entries = Array.from(addressPending.entries());\n entries.sort((a, b) => a[1].receivedAt - b[1].receivedAt);\n\n const toEvict = entries.length - this.maxPendingPerAddress;\n for (let i = 0; i < toEvict; i++) {\n addressPending.delete(entries[i][0]);\n }\n }\n\n /**\n * Clean up expired pending assemblies.\n * Call this periodically to prevent memory leaks.\n */\n cleanup(): number {\n const now = Date.now();\n let evicted = 0;\n\n for (const [addressKey, addressPending] of this.pending.entries()) {\n for (const [seqKey, pending] of addressPending.entries()) {\n if (now - pending.receivedAt > this.assemblyTimeout) {\n addressPending.delete(seqKey);\n evicted++;\n }\n }\n\n if (addressPending.size === 0) {\n this.pending.delete(addressKey);\n }\n }\n\n return evicted;\n }\n\n /**\n * Get current pending count for debugging\n */\n getPendingCount(): number {\n let count = 0;\n for (const addressPending of this.pending.values()) {\n count += addressPending.size;\n }\n return count;\n }\n\n /**\n * Clear all pending assemblies\n */\n clear(): void {\n this.pending.clear();\n }\n}\n","/**\n * Account Replay - streaming account state with backfill reconciliation.\n *\n * This module provides account state streaming with:\n * - Page assembly for large accounts (>4KB)\n * - Sequence number tracking for ordering\n * - Backfill reconciliation with live updates\n * - Block boundary detection via BlockFinished messages\n */\n\nimport { create } from \"@bufbuild/protobuf\";\nimport type { Account, AccountMeta, GetAccountRequest } from \"@thru/proto\";\nimport {\n AccountView,\n FilterSchema,\n FilterParamValueSchema,\n PageRequestSchema,\n PubkeySchema,\n} from \"@thru/proto\";\nimport type {\n StreamAccountUpdatesRequest,\n StreamAccountUpdatesResponse,\n ListAccountsRequest,\n BlockFinished,\n Filter,\n FilterParamValue,\n} from \"@thru/proto\";\nimport type { AccountSource } from \"./chain-client\";\nimport { PageAssembler, type AssembledAccount } from \"./page-assembler\";\nimport {\n DEFAULT_RETRY_CONFIG,\n calculateBackoff,\n delay,\n type RetryConfig,\n} from \"./retry\";\nimport type { ReplayLogger } from \"./types\";\nimport { resolveClient } from \"./types\";\nimport { NOOP_LOGGER } from \"./logger\";\n\n/**\n * Represents a complete account state ready for processing\n */\nexport interface AccountState {\n /** Account address as bytes */\n address: Uint8Array;\n /** Account address as hex string */\n addressHex: string;\n /** Slot at which this state was observed */\n slot: bigint;\n /** Sequence number for ordering updates */\n seq: bigint;\n /** Account metadata */\n meta: AccountMeta;\n /** Complete account data (assembled from pages) */\n data: Uint8Array;\n /** Whether this is a deletion */\n isDelete: boolean;\n /** Source: \"backfill\" for GetAccount during backfill, \"stream\" for live updates */\n source: \"backfill\" | \"stream\";\n}\n\n/**\n * Block finished event for detecting transaction boundaries\n */\nexport interface BlockFinishedEvent {\n slot: bigint;\n}\n\n/**\n * Union type for account replay events\n */\nexport type AccountReplayEvent =\n | { type: \"account\"; account: AccountState }\n | { type: \"blockFinished\"; block: BlockFinishedEvent };\n\n/**\n * Options for account replay (single address)\n */\nexport interface AccountReplayOptions {\n /** Account source (typically ChainClient) */\n client: AccountSource;\n\n /** Account address to stream updates for */\n address: Uint8Array;\n\n /** Account view (default: FULL for complete data) */\n view?: AccountView;\n\n /** Optional filter expression */\n filter?: {\n expression: string;\n params?: { [key: string]: { kind: { case: string; value: unknown } } };\n };\n\n /** Page assembler options */\n pageAssemblerOptions?: {\n assemblyTimeout?: number;\n maxPendingPerAddress?: number;\n };\n\n /** Cleanup interval for page assembler (default: 10000ms) */\n cleanupInterval?: number;\n}\n\n/**\n * Options for replaying accounts by owner with backfill + streaming.\n * Uses ListAccounts (META_ONLY) + GetAccount for backfill, then StreamAccountUpdates for live updates.\n */\nexport interface AccountsByOwnerReplayOptions {\n /** Account source (typically ChainClient). Optional if clientFactory provided. */\n client?: AccountSource;\n\n /** Factory to create fresh clients on reconnection. Enables robust reconnection. */\n clientFactory?: () => AccountSource;\n\n /** Program owner address - streams all accounts owned by this program */\n owner: Uint8Array;\n\n /** Account view for GetAccount calls (default: FULL for complete data) */\n view?: AccountView;\n\n /** Optional data sizes to filter (e.g., [73, 115] for TokenAccount and MintAccount) */\n dataSizes?: number[];\n\n /** Minimum last_updated_slot for resumable backfill (resume from checkpoint) */\n minUpdatedSlot?: bigint;\n\n /** Page size for ListAccounts pagination (default: 100) */\n pageSize?: number;\n\n /** Max retries for GetAccount failures (default: 3) */\n maxRetries?: number;\n\n /** Page assembler options for streaming phase */\n pageAssemblerOptions?: {\n assemblyTimeout?: number;\n maxPendingPerAddress?: number;\n };\n\n /** Cleanup interval for page assembler (default: 10000ms) */\n cleanupInterval?: number;\n\n /** Called when backfill queue is drained. Returns the highest slot seen during backfill. */\n onBackfillComplete?: (highestSlot: bigint) => void;\n\n /** Logger for debug/info/warn/error messages (default: NOOP_LOGGER) */\n logger?: ReplayLogger;\n}\n\n/**\n * Convert address bytes to hex string\n */\nfunction bytesToHex(bytes: Uint8Array): string {\n return Array.from(bytes)\n .map((b) => b.toString(16).padStart(2, \"0\"))\n .join(\"\");\n}\n\n/**\n * Convert Account snapshot to AccountState (for streaming)\n */\nfunction snapshotToState(account: Account): AccountState | null {\n if (!account.address?.value || !account.meta) {\n return null;\n }\n\n return {\n address: account.address.value,\n addressHex: bytesToHex(account.address.value),\n slot: account.versionContext?.slot ?? 0n,\n seq: BigInt(account.meta.seq.toString()),\n meta: account.meta,\n data: account.data?.data ?? new Uint8Array(0),\n isDelete: account.meta.flags?.isDeleted ?? false,\n source: \"stream\",\n };\n}\n\n/**\n * Convert AssembledAccount to AccountState (for streaming)\n */\nfunction assembledToState(assembled: AssembledAccount): AccountState {\n return {\n address: assembled.address,\n addressHex: bytesToHex(assembled.address),\n slot: assembled.slot,\n seq: assembled.seq,\n meta: assembled.meta,\n data: assembled.data,\n isDelete: assembled.isDelete,\n source: \"stream\",\n };\n}\n\n/**\n * Convert Account from GetAccount to AccountState (for backfill)\n */\nfunction getAccountToState(account: Account): AccountState | null {\n if (!account.address?.value || !account.meta) {\n return null;\n }\n\n return {\n address: account.address.value,\n addressHex: bytesToHex(account.address.value),\n slot: account.meta.lastUpdatedSlot ?? account.versionContext?.slot ?? 0n,\n seq: BigInt(account.meta.seq.toString()),\n meta: account.meta,\n data: account.data?.data ?? new Uint8Array(0),\n isDelete: account.meta.flags?.isDeleted ?? false,\n source: \"backfill\",\n };\n}\n\n/**\n * Build owner filter for ListAccounts (uses account.meta.owner, not snapshot/update prefixes)\n * Note: ListAccounts requires param name \"owner_bytes\" (not \"owner\")\n */\nfunction buildListAccountsOwnerFilter(\n owner: Uint8Array,\n dataSizes?: number[],\n minUpdatedSlot?: bigint\n): Filter {\n // ListAccounts filter uses account.meta.owner (no snapshot/update prefix)\n // Must use params.owner_bytes (required param name for ListAccounts)\n let expression = \"account.meta.owner.value == params.owner_bytes\";\n\n // Add data size filter if specified\n if (dataSizes && dataSizes.length > 0) {\n const sizeConditions = dataSizes\n .map((size) => `account.meta.data_size == uint(${size})`)\n .join(\" || \");\n expression = `(${expression}) && (${sizeConditions})`;\n }\n\n // Add minUpdatedSlot filter for resumable backfill\n if (minUpdatedSlot !== undefined && minUpdatedSlot > 0n) {\n expression = `(${expression}) && account.meta.last_updated_slot >= params.min_updated_slot`;\n }\n\n const params: { [key: string]: FilterParamValue } = {\n owner_bytes: create(FilterParamValueSchema, { kind: { case: \"bytesValue\", value: new Uint8Array(owner) } }),\n };\n\n if (minUpdatedSlot !== undefined && minUpdatedSlot > 0n) {\n params[\"min_updated_slot\"] = create(FilterParamValueSchema, { kind: { case: \"uintValue\", value: minUpdatedSlot } });\n }\n\n return create(FilterSchema, { expression, params });\n}\n\n/**\n * Create an async iterable that replays all accounts owned by a program.\n *\n * This performs hybrid backfill + streaming:\n * 1. Starts StreamAccountUpdates concurrently (yields immediately, marks addresses as \"seen\")\n * 2. ListAccounts with META_ONLY view to get addresses (cheap, no data)\n * 3. GetAccount for each address sequentially (skips if already seen from stream)\n *\n * Stream updates \"win\" - if an address is received from stream, GetAccount is skipped.\n * This provides resumable, complete account indexing with efficient use of resources.\n *\n * @param options - Replay options\n * @returns Async iterable of account replay events\n *\n * @example\n * ```typescript\n * const client = new ChainClient({ baseUrl: \"https://grpc.thru.org\" });\n *\n * for await (const event of createAccountsByOwnerReplay({\n * client,\n * owner: TOKEN_PROGRAM_ID,\n * dataSizes: [73, 115], // TokenAccount, MintAccount\n * minUpdatedSlot: checkpoint.lastProcessedSlot, // Resume from checkpoint\n * onBackfillComplete: (slot) => console.log(`Backfill queue drained at slot ${slot}`),\n * })) {\n * if (event.type === \"account\") {\n * await processAccount(event.account);\n * }\n * }\n * ```\n */\nexport async function* createAccountsByOwnerReplay(\n options: AccountsByOwnerReplayOptions\n): AsyncGenerator<AccountReplayEvent, void, undefined> {\n const {\n owner,\n view = AccountView.FULL,\n dataSizes,\n minUpdatedSlot,\n pageSize = 100,\n maxRetries = 3,\n pageAssemblerOptions,\n cleanupInterval = 10000,\n onBackfillComplete,\n clientFactory,\n logger = NOOP_LOGGER,\n } = options;\n\n // Resolve initial client - either from options or from factory\n let client = resolveClient(options, \"AccountsByOwnerReplayOptions\");\n\n // Track addresses seen from stream (these win - skip GetAccount)\n const seenFromStream = new Set<string>();\n\n // Queue of addresses to fetch via GetAccount\n const fetchQueue: Uint8Array[] = [];\n\n // Highest slot seen (for checkpoint callback)\n let highestSlotSeen = minUpdatedSlot ?? 0n;\n\n // Page assembler for streaming\n const assembler = new PageAssembler(pageAssemblerOptions);\n let cleanupTimer: ReturnType<typeof setInterval> | null = null;\n\n // Buffer for stream events\n const streamBuffer: AccountReplayEvent[] = [];\n let streamDone = false;\n let streamError: Error | null = null;\n\n try {\n // Set up periodic cleanup for page assembler\n cleanupTimer = setInterval(() => {\n assembler.cleanup();\n }, cleanupInterval);\n\n // Start streaming FIRST (concurrent with backfill)\n const streamFilter = buildOwnerFilterWithMinSlot(owner, dataSizes, minUpdatedSlot);\n const stream = client.streamAccountUpdates({ view, filter: streamFilter });\n\n // Process stream in background, buffering events\n const streamProcessor = (async () => {\n try {\n for await (const response of stream) {\n const event = processResponseMulti(response, assembler);\n if (event) {\n if (event.type === \"account\") {\n // Mark as seen - don't need to GetAccount for this one\n seenFromStream.add(event.account.addressHex);\n if (event.account.slot > highestSlotSeen) {\n highestSlotSeen = event.account.slot;\n }\n }\n streamBuffer.push(event);\n }\n }\n } catch (err) {\n streamError = err as Error;\n } finally {\n streamDone = true;\n }\n })();\n\n // Helper to yield buffered stream events\n const yieldStreamBuffer = function* (): Generator<AccountReplayEvent> {\n while (streamBuffer.length > 0) {\n const event = streamBuffer.shift()!;\n if (event.type === \"account\") {\n // Ensure it's marked as seen (should already be, but belt and suspenders)\n seenFromStream.add(event.account.addressHex);\n }\n yield event;\n }\n };\n\n // ListAccounts with META_ONLY view to get addresses (no data)\n const backfillFilter = buildListAccountsOwnerFilter(owner, dataSizes, minUpdatedSlot);\n let pageToken: string | undefined;\n\n do {\n const request: Partial<ListAccountsRequest> = {\n view: AccountView.META_ONLY, // Address + metadata only, no data\n filter: backfillFilter,\n page: create(PageRequestSchema, {\n pageSize,\n pageToken,\n }),\n };\n\n const response = await client.listAccounts(request);\n\n // Queue addresses for GetAccount\n for (const account of response.accounts) {\n if (account.address?.value) {\n fetchQueue.push(account.address.value);\n }\n }\n\n pageToken = response.page?.nextPageToken;\n\n // Yield any buffered stream events between pages\n yield* yieldStreamBuffer();\n } while (pageToken);\n\n // Process fetch queue with GetAccount (sequential)\n for (const address of fetchQueue) {\n const addressHex = bytesToHex(address);\n\n // Skip if already seen from stream\n if (seenFromStream.has(addressHex)) {\n continue;\n }\n\n // Yield any buffered stream events first\n yield* yieldStreamBuffer();\n\n // Check again after processing buffer (stream may have delivered this address)\n if (seenFromStream.has(addressHex)) {\n continue;\n }\n\n // Fetch with retry\n let account: Account | null = null;\n for (let attempt = 0; attempt < maxRetries; attempt++) {\n try {\n account = await client.getAccount({\n address: create(PubkeySchema, { value: address }),\n view: AccountView.FULL,\n });\n break;\n } catch (err) {\n if (attempt === maxRetries - 1) {\n logger.error(`[backfill] failed to fetch account ${addressHex} after ${maxRetries} attempts`, { error: err });\n } else {\n // Brief delay before retry\n await new Promise(resolve => setTimeout(resolve, 100 * (attempt + 1)));\n }\n }\n }\n\n if (account) {\n const state = getAccountToState(account);\n if (state) {\n if (state.slot > highestSlotSeen) {\n highestSlotSeen = state.slot;\n }\n yield { type: \"account\", account: state };\n }\n }\n }\n\n // Signal backfill queue drained\n if (onBackfillComplete) {\n onBackfillComplete(highestSlotSeen);\n }\n\n // Streaming phase with reconnection\n const retryConfig = DEFAULT_RETRY_CONFIG;\n let retryAttempt = 0;\n let currentStream = stream;\n let currentStreamProcessor = streamProcessor;\n\n // Helper to create a new stream and processor with fresh client\n const createStreamProcessor = () => {\n // Get fresh client if factory available (key fix for reconnection)\n if (clientFactory) {\n try {\n client = clientFactory();\n logger.info(\"[account-stream] created fresh client for reconnection\");\n } catch (err) {\n logger.error(\"[account-stream] failed to create fresh client\", { error: err });\n // Continue with existing client as fallback\n }\n }\n\n const newStreamFilter = buildOwnerFilterWithMinSlot(owner, dataSizes, highestSlotSeen > 0n ? highestSlotSeen : minUpdatedSlot);\n const newStream = client.streamAccountUpdates({ view, filter: newStreamFilter });\n const newProcessor = (async () => {\n try {\n for await (const response of newStream) {\n retryAttempt = 0; // Reset on successful message\n const event = processResponseMulti(response, assembler);\n if (event) {\n if (event.type === \"account\") {\n seenFromStream.add(event.account.addressHex);\n if (event.account.slot > highestSlotSeen) {\n highestSlotSeen = event.account.slot;\n }\n }\n streamBuffer.push(event);\n }\n }\n } catch (err) {\n streamError = err as Error;\n } finally {\n streamDone = true;\n }\n })();\n return { stream: newStream, processor: newProcessor };\n };\n\n // Continue yielding stream events with reconnection on error\n while (true) {\n // Yield any buffered events\n yield* yieldStreamBuffer();\n\n // Check if stream finished (normally or with error)\n if (streamDone) {\n if (streamError) {\n // Stream error - reconnect with backoff\n const backoffMs = calculateBackoff(retryAttempt, retryConfig);\n logger.warn(\n `[account-stream] disconnected (${streamError.message}); reconnecting in ${backoffMs}ms (attempt ${retryAttempt + 1})`\n );\n await delay(backoffMs);\n retryAttempt++;\n\n // Reset state\n streamDone = false;\n streamError = null;\n streamBuffer.length = 0;\n\n // Create new stream\n const { stream: newStream, processor: newProcessor } = createStreamProcessor();\n currentStream = newStream;\n currentStreamProcessor = newProcessor;\n continue;\n } else {\n // Stream ended normally (no error) - this shouldn't happen in practice\n // but if it does, reconnect to maintain live updates\n logger.warn(\"[account-stream] stream ended unexpectedly; reconnecting...\");\n streamDone = false;\n const { stream: newStream, processor: newProcessor } = createStreamProcessor();\n currentStream = newStream;\n currentStreamProcessor = newProcessor;\n continue;\n }\n }\n\n // Wait a bit for more stream events\n await delay(10);\n }\n } finally {\n if (cleanupTimer) {\n clearInterval(cleanupTimer);\n }\n assembler.clear();\n }\n}\n\n/**\n * Build owner filter for streaming with minimum slot filter.\n * Only yields accounts updated at or after minSlot.\n */\nfunction buildOwnerFilterWithMinSlot(\n owner: Uint8Array,\n dataSizes?: number[],\n minSlot?: bigint\n): Filter {\n // Base filter: match owner on both snapshot and update\n let expression = \"(has(snapshot.meta.owner) && snapshot.meta.owner.value == params.owner) || (has(account_update.meta.owner) && account_update.meta.owner.value == params.owner)\";\n\n // Add data size filter if specified\n if (dataSizes && dataSizes.length > 0) {\n const sizeConditions = dataSizes\n .map((size) => `snapshot.meta.data_size == uint(${size}) || account_update.meta.data_size == uint(${size})`)\n .join(\" || \");\n expression = `(${expression}) && (${sizeConditions})`;\n }\n\n // Add slot filter for handover from backfill\n // Note: We allow snapshots through (they don't have slot field) and filter updates by slot\n // has() requires a field path, so we check has(snapshot.address) to detect snapshot messages\n if (minSlot !== undefined && minSlot > 0n) {\n // Snapshots pass through (check via has(snapshot.address)), updates must have slot >= minSlot\n expression = `(${expression}) && (has(snapshot.address) || (has(account_update.slot) && account_update.slot >= params.min_slot))`;\n }\n\n const params: { [key: string]: FilterParamValue } = {\n owner: create(FilterParamValueSchema, { kind: { case: \"bytesValue\", value: new Uint8Array(owner) } }),\n };\n\n if (minSlot !== undefined && minSlot > 0n) {\n params[\"min_slot\"] = create(FilterParamValueSchema, { kind: { case: \"uintValue\", value: minSlot } });\n }\n\n return create(FilterSchema, { expression, params });\n}\n\n/**\n * Create an async iterable for account replay with page assembly.\n *\n * This function streams account updates with proper page assembly for\n * large accounts. It handles:\n * - Initial snapshots\n * - Live updates with page assembly\n * - Block finished signals\n *\n * @param options - Account replay options\n * @returns Async iterable of account replay events\n *\n * @example\n * ```typescript\n * const client = new ChainClient({ baseUrl: \"https://grpc.thru.org\" });\n *\n * for await (const event of createAccountReplay({\n * client,\n * address: accountPubkey,\n * view: AccountView.FULL,\n * })) {\n * if (event.type === \"account\") {\n * console.log(\"Account update:\", event.account.seq);\n * } else if (event.type === \"blockFinished\") {\n * console.log(\"Block finished:\", event.block.slot);\n * }\n * }\n * ```\n */\nexport async function* createAccountReplay(\n options: AccountReplayOptions\n): AsyncGenerator<AccountReplayEvent, void, undefined> {\n const {\n client,\n address,\n view = AccountView.FULL,\n filter,\n pageAssemblerOptions,\n cleanupInterval = 10000,\n } = options;\n\n const assembler = new PageAssembler(pageAssemblerOptions);\n let cleanupTimer: ReturnType<typeof setInterval> | null = null;\n\n try {\n // Set up periodic cleanup\n cleanupTimer = setInterval(() => {\n assembler.cleanup();\n }, cleanupInterval);\n\n // Build request with address filter\n const filterParams: { [key: string]: FilterParamValue } = {\n address: create(FilterParamValueSchema, { kind: { case: \"bytesValue\", value: new Uint8Array(address) } }),\n };\n if (filter?.params) {\n for (const [key, value] of Object.entries(filter.params)) {\n filterParams[key] = create(FilterParamValueSchema, value as any);\n }\n }\n\n const request: Partial<StreamAccountUpdatesRequest> = {\n view,\n filter: create(FilterSchema, {\n expression: filter?.expression\n ? `(snapshot.address.value == params.address) && (${filter.expression})`\n : \"snapshot.address.value == params.address\",\n params: filterParams,\n }),\n };\n\n // Stream account updates\n const stream = client.streamAccountUpdates(request);\n\n for await (const response of stream) {\n const event = processResponse(response, address, assembler);\n if (event) {\n yield event;\n }\n }\n } finally {\n // Cleanup\n if (cleanupTimer) {\n clearInterval(cleanupTimer);\n }\n assembler.clear();\n }\n}\n\n/**\n * Process a streaming response and return an event if available\n */\nfunction processResponse(\n response: StreamAccountUpdatesResponse,\n address: Uint8Array,\n assembler: PageAssembler\n): AccountReplayEvent | null {\n switch (response.message.case) {\n case \"snapshot\": {\n const state = snapshotToState(response.message.value);\n if (state) {\n return { type: \"account\", account: state };\n }\n return null;\n }\n\n case \"update\": {\n const assembled = assembler.processUpdate(address, response.message.value);\n if (assembled) {\n return { type: \"account\", account: assembledToState(assembled) };\n }\n return null;\n }\n\n case \"finished\": {\n return {\n type: \"blockFinished\",\n block: { slot: BigInt(response.message.value.slot.toString()) },\n };\n }\n\n default:\n return null;\n }\n}\n\n/**\n * Process a streaming response for multi-account streams (gets address from response)\n */\nfunction processResponseMulti(\n response: StreamAccountUpdatesResponse,\n assembler: PageAssembler\n): AccountReplayEvent | null {\n switch (response.message.case) {\n case \"snapshot\": {\n const state = snapshotToState(response.message.value);\n if (state) {\n return { type: \"account\", account: state };\n }\n return null;\n }\n\n case \"update\": {\n const update = response.message.value;\n // Get address from the update message\n const address = update.address?.value;\n if (!address) {\n // No address in update, cannot process\n return null;\n }\n const assembled = assembler.processUpdate(address, update);\n if (assembled) {\n return { type: \"account\", account: assembledToState(assembled) };\n }\n return null;\n }\n\n case \"finished\": {\n return {\n type: \"blockFinished\",\n block: { slot: BigInt(response.message.value.slot.toString()) },\n };\n }\n\n default:\n return null;\n }\n}\n\n/**\n * State tracker for account sequence numbers.\n *\n * Used to track the highest sequence number seen per account address\n * to ensure updates are applied in order.\n */\nexport class AccountSeqTracker {\n private seqs: Map<string, bigint> = new Map();\n\n /**\n * Get the current sequence number for an address\n */\n getSeq(addressHex: string): bigint | undefined {\n return this.seqs.get(addressHex);\n }\n\n /**\n * Check if an update should be applied (seq > current)\n */\n shouldApply(addressHex: string, seq: bigint): boolean {\n const current = this.seqs.get(addressHex);\n return current === undefined || seq > current;\n }\n\n /**\n * Update the sequence number for an address\n * Only updates if new seq is greater than current\n */\n update(addressHex: string, seq: bigint): boolean {\n const current = this.seqs.get(addressHex);\n if (current === undefined || seq > current) {\n this.seqs.set(addressHex, seq);\n return true;\n }\n return false;\n }\n\n /**\n * Remove tracking for an address\n */\n remove(addressHex: string): void {\n this.seqs.delete(addressHex);\n }\n\n /**\n * Clear all tracking\n */\n clear(): void {\n this.seqs.clear();\n }\n\n /**\n * Get count of tracked addresses\n */\n size(): number {\n return this.seqs.size;\n }\n}\n\n/**\n * Multi-account replay manager for streaming updates from multiple accounts.\n *\n * This class manages multiple account streams and provides:\n * - Unified event stream from multiple accounts\n * - Sequence number tracking per account\n * - Automatic reconnection on errors\n */\nexport class MultiAccountReplay {\n private client: AccountSource;\n private view: AccountView;\n private seqTracker: AccountSeqTracker;\n private activeStreams: Map<string, AbortController> = new Map();\n\n constructor(options: { client: AccountSource; view?: AccountView }) {\n this.client = options.client;\n this.view = options.view ?? AccountView.FULL;\n this.seqTracker = new AccountSeqTracker();\n }\n\n /**\n * Add an account to stream updates for\n */\n async *addAccount(address: Uint8Array): AsyncGenerator<AccountReplayEvent> {\n const addressHex = bytesToHex(address);\n\n // Check if already streaming\n if (this.activeStreams.has(addressHex)) {\n return;\n }\n\n const controller = new AbortController();\n this.activeStreams.set(addressHex, controller);\n\n try {\n for await (const event of createAccountReplay({\n client: this.client,\n address,\n view: this.view,\n })) {\n // Filter by sequence number\n if (event.type === \"account\") {\n if (this.seqTracker.shouldApply(event.account.addressHex, event.account.seq)) {\n this.seqTracker.update(event.account.addressHex, event.account.seq);\n yield event;\n }\n } else {\n yield event;\n }\n }\n } finally {\n this.activeStreams.delete(addressHex);\n }\n }\n\n /**\n * Remove an account from streaming\n */\n removeAccount(address: Uint8Array): void {\n const addressHex = bytesToHex(address);\n const controller = this.activeStreams.get(addressHex);\n if (controller) {\n controller.abort();\n this.activeStreams.delete(addressHex);\n }\n this.seqTracker.remove(addressHex);\n }\n\n /**\n * Get the current sequence number for an account\n */\n getSeq(addressHex: string): bigint | undefined {\n return this.seqTracker.getSeq(addressHex);\n }\n\n /**\n * Stop all streams\n */\n stop(): void {\n for (const controller of this.activeStreams.values()) {\n controller.abort();\n }\n this.activeStreams.clear();\n this.seqTracker.clear();\n }\n}\n","import { ReplaySink, ReplaySinkContext, ReplaySinkMeta } from \"./replay-sink\";\n\n\nexport class ConsoleSink<T> implements ReplaySink<T> {\n constructor(private readonly prefix = \"ReplaySink\") {}\n\n open(meta?: ReplaySinkMeta): void {\n const suffix = meta?.stream ? ` (${meta.stream})` : \"\";\n console.info(`${this.prefix}${suffix} opened`, meta?.label ?? \"\");\n }\n\n write(item: T, ctx: ReplaySinkContext): void {\n const slotLabel = ctx.slot.toString();\n console.info(\n `${this.prefix} ${ctx.phase.toUpperCase()} slot=${slotLabel}`,\n item,\n );\n }\n\n close(err?: unknown): void {\n if (err) console.warn(`${this.prefix} closing with error`, err);\n else console.info(`${this.prefix} closed`);\n }\n}\n"]}
1
+ {"version":3,"sources":["../src/chain-client.ts","../src/async-queue.ts","../src/dedup-buffer.ts","../src/logger.ts","../src/live-pump.ts","../src/retry.ts","../src/replay-stream.ts","../src/replay/helpers.ts","../src/replay/block-replay.ts","../src/replay/transaction-replay.ts","../src/types.ts","../src/replay/event-replay.ts","../src/page-assembler.ts","../src/account-replay.ts","../src/sinks/console.ts"],"names":["createClient","QueryService","StreamingService","create","GetAccountRequestSchema","ListAccountsRequestSchema","ListBlocksRequestSchema","StreamBlocksRequestSchema","ListTransactionsRequestSchema","StreamTransactionsRequestSchema","ListEventsRequestSchema","StreamEventsRequestSchema","createGrpcTransport","StreamAccountUpdatesRequestSchema","GetHeightRequestSchema","delay","FilterSchema","PageRequestSchema","DEFAULT_PAGE_SIZE","DEFAULT_SAFETY_MARGIN","PAGE_ORDER_ASC","EventSchema","bytesToHex","FilterParamValueSchema","AccountView","PubkeySchema"],"mappings":"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","file":"index.cjs","sourcesContent":["import { create } from \"@bufbuild/protobuf\";\nimport {\n type CallOptions,\n createClient,\n type Interceptor,\n type Transport,\n} from \"@connectrpc/connect\";\nimport { createGrpcTransport } from \"@connectrpc/connect-node\";\nimport {\n QueryService,\n StreamingService,\n type GetHeightRequest,\n GetHeightRequestSchema,\n type GetHeightResponse,\n type GetAccountRequest,\n GetAccountRequestSchema,\n type Account,\n type ListAccountsRequest,\n ListAccountsRequestSchema,\n type ListAccountsResponse,\n type ListBlocksRequest,\n ListBlocksRequestSchema,\n type ListBlocksResponse,\n type ListEventsRequest,\n ListEventsRequestSchema,\n type ListEventsResponse,\n type ListTransactionsRequest,\n ListTransactionsRequestSchema,\n type ListTransactionsResponse,\n type StreamBlocksRequest,\n StreamBlocksRequestSchema,\n type StreamBlocksResponse,\n type StreamEventsRequest,\n StreamEventsRequestSchema,\n type StreamEventsResponse,\n type StreamTransactionsRequest,\n StreamTransactionsRequestSchema,\n type StreamTransactionsResponse,\n type StreamAccountUpdatesRequest,\n StreamAccountUpdatesRequestSchema,\n type StreamAccountUpdatesResponse,\n} from \"@thru/proto\";\n\nexport interface ChainClientOptions {\n baseUrl?: string;\n apiKey?: string;\n userAgent?: string;\n transport?: Transport;\n interceptors?: Interceptor[];\n callOptions?: CallOptions;\n useBinaryFormat?: boolean;\n}\n\n/**\n * Factory function that creates fresh ChainClient instances.\n * Called on each reconnection to ensure a new gRPC transport.\n */\nexport type ChainClientFactory = () => ChainClient;\n\nexport interface BlockSource {\n listBlocks(request: Partial<ListBlocksRequest>): Promise<ListBlocksResponse>;\n streamBlocks(request: Partial<StreamBlocksRequest>): AsyncIterable<StreamBlocksResponse>;\n}\n\nexport interface TransactionSource {\n listTransactions(\n request: Partial<ListTransactionsRequest>,\n ): Promise<ListTransactionsResponse>;\n streamTransactions(\n request: Partial<StreamTransactionsRequest>,\n ): AsyncIterable<StreamTransactionsResponse>;\n}\n\nexport interface EventSource {\n listEvents(request: Partial<ListEventsRequest>): Promise<ListEventsResponse>;\n streamEvents(\n request: Partial<StreamEventsRequest>,\n ): AsyncIterable<StreamEventsResponse>;\n}\n\nexport interface AccountSource {\n getAccount(request: Partial<GetAccountRequest>): Promise<Account>;\n listAccounts(request: Partial<ListAccountsRequest>): Promise<ListAccountsResponse>;\n streamAccountUpdates(\n request: Partial<StreamAccountUpdatesRequest>,\n ): AsyncIterable<StreamAccountUpdatesResponse>;\n}\n\nexport type ReplayDataSource = BlockSource & TransactionSource & EventSource & AccountSource;\n\nexport class ChainClient implements ReplayDataSource {\n private readonly query: ReturnType<typeof createClient<typeof QueryService>>;\n private readonly streaming: ReturnType<typeof createClient<typeof StreamingService>>;\n private readonly callOptions?: CallOptions;\n\n constructor(private readonly options: ChainClientOptions) {\n const transport = options.transport ?? this.createTransport();\n this.query = createClient(QueryService, transport);\n this.streaming = createClient(StreamingService, transport);\n this.callOptions = options.callOptions;\n }\n\n getAccount(request: Partial<GetAccountRequest>): Promise<Account> {\n return this.query.getAccount(create(GetAccountRequestSchema, request), this.callOptions);\n }\n\n listAccounts(request: Partial<ListAccountsRequest>): Promise<ListAccountsResponse> {\n return this.query.listAccounts(create(ListAccountsRequestSchema, request), this.callOptions);\n }\n\n listBlocks(request: Partial<ListBlocksRequest>): Promise<ListBlocksResponse> {\n return this.query.listBlocks(create(ListBlocksRequestSchema, request), this.callOptions);\n }\n\n streamBlocks(\n request: Partial<StreamBlocksRequest>,\n ): AsyncIterable<StreamBlocksResponse> {\n return this.streaming.streamBlocks(create(StreamBlocksRequestSchema, request), this.callOptions);\n }\n\n listTransactions(\n request: Partial<ListTransactionsRequest>,\n ): Promise<ListTransactionsResponse> {\n return this.query.listTransactions(create(ListTransactionsRequestSchema, request), this.callOptions);\n }\n\n streamTransactions(\n request: Partial<StreamTransactionsRequest>,\n ): AsyncIterable<StreamTransactionsResponse> {\n return this.streaming.streamTransactions(create(StreamTransactionsRequestSchema, request), this.callOptions);\n }\n\n listEvents(request: Partial<ListEventsRequest>): Promise<ListEventsResponse> {\n return this.query.listEvents(create(ListEventsRequestSchema, request), this.callOptions);\n }\n\n streamEvents(\n request: Partial<StreamEventsRequest>,\n ): AsyncIterable<StreamEventsResponse> {\n return this.streaming.streamEvents(create(StreamEventsRequestSchema, request), this.callOptions);\n }\n\n private createTransport(): Transport {\n if (!this.options.baseUrl) {\n throw new Error(\"ChainClient requires baseUrl when no transport is provided\");\n }\n\n const headerInterceptor = this.createHeaderInterceptor();\n const userInterceptors = this.options.interceptors ?? [];\n const mergedInterceptors = [\n ...userInterceptors,\n ...(headerInterceptor ? [headerInterceptor] : []),\n ];\n\n return createGrpcTransport({\n baseUrl: this.options.baseUrl,\n useBinaryFormat: this.options.useBinaryFormat ?? true,\n interceptors: mergedInterceptors.length ? mergedInterceptors : undefined,\n pingIntervalMs: 30_000,\n pingIdleConnection: true,\n pingTimeoutMs: 10_000,\n idleConnectionTimeoutMs: 0,\n });\n }\n\n private createHeaderInterceptor(): Interceptor | null {\n const headers: Record<string, string> = {};\n if (this.options.apiKey) headers.Authorization = `Bearer ${this.options.apiKey}`;\n if (this.options.userAgent) headers[\"User-Agent\"] = this.options.userAgent;\n if (!Object.keys(headers).length) return null;\n return (next) => async (req) => {\n for (const [key, value] of Object.entries(headers)) req.header.set(key, value);\n return next(req);\n };\n }\n\n streamAccountUpdates(\n request: Partial<StreamAccountUpdatesRequest>,\n ): AsyncIterable<StreamAccountUpdatesResponse> {\n return this.streaming.streamAccountUpdates(create(StreamAccountUpdatesRequestSchema, request), this.callOptions);\n }\n\n getHeight(): Promise<GetHeightResponse> {\n return this.query.getHeight(create(GetHeightRequestSchema, {}), this.callOptions);\n }\n}\n","type Resolver<T> = (result: IteratorResult<T>) => void;\ntype Rejecter = (err: unknown) => void;\n\nexport class AsyncQueue<T> implements AsyncIterable<T> {\n private readonly values: T[] = [];\n private readonly pending: Array<{ resolve: Resolver<T>; reject: Rejecter }> = [];\n private closed = false;\n private failure: unknown;\n\n push(value: T): void {\n if (this.closed) throw new Error(\"Cannot push into a closed queue\");\n if (this.failure) throw this.failure;\n const waiter = this.pending.shift();\n if (waiter) waiter.resolve({ value, done: false });\n else this.values.push(value);\n }\n\n next(): Promise<IteratorResult<T>> {\n if (this.failure) return Promise.reject(this.failure);\n if (this.values.length) {\n const value = this.values.shift()!;\n return Promise.resolve({ value, done: false });\n }\n if (this.closed) return Promise.resolve({ value: undefined as never, done: true });\n return new Promise((resolve, reject) => {\n this.pending.push({ resolve, reject });\n });\n }\n\n close(): void {\n this.closed = true;\n while (this.pending.length) {\n const waiter = this.pending.shift();\n waiter?.resolve({ value: undefined as never, done: true });\n }\n }\n\n fail(err: unknown): void {\n this.failure = err ?? new Error(\"AsyncQueue failure\");\n while (this.pending.length) {\n const waiter = this.pending.shift();\n waiter?.reject(this.failure);\n }\n }\n\n get isClosed(): boolean {\n return this.closed;\n }\n\n [Symbol.asyncIterator](): AsyncIterator<T> {\n return {\n next: () => this.next(),\n };\n }\n}\n","import type { Slot } from \"./types\";\n\ninterface DedupBufferOptions<T> {\n slotOf: (item: T) => Slot;\n keyOf: (item: T) => string;\n}\n\nexport class DedupBuffer<T> {\n private readonly slotOf: (item: T) => Slot;\n private readonly keyOf: (item: T) => string;\n private readonly slots: Slot[] = [];\n private readonly itemsBySlot = new Map<Slot, Map<string, T>>();\n private sizeValue = 0;\n\n constructor(options: DedupBufferOptions<T>) {\n this.slotOf = options.slotOf;\n this.keyOf = options.keyOf;\n }\n\n insert(item: T): boolean {\n const slot = this.slotOf(item);\n const key = this.keyOf(item);\n let bucket = this.itemsBySlot.get(slot);\n if (!bucket) {\n bucket = new Map();\n this.itemsBySlot.set(slot, bucket);\n const idx = this.findInsertIndex(slot);\n this.slots.splice(idx, 0, slot);\n }\n if (bucket.has(key)) return false;\n bucket.set(key, item);\n this.sizeValue += 1;\n return true;\n }\n\n discardUpTo(cutoff: Slot): number {\n let removed = 0;\n while (this.slots.length && this.slots[0] <= cutoff) {\n const slot = this.slots.shift()!;\n const bucket = this.itemsBySlot.get(slot);\n if (!bucket) continue;\n removed += bucket.size;\n this.itemsBySlot.delete(slot);\n }\n this.sizeValue = Math.max(0, this.sizeValue - removed);\n return removed;\n }\n\n drainAbove(cutoff: Slot): T[] {\n if (!this.slots.length) return [];\n const drained: T[] = [];\n const keep: Slot[] = [];\n for (const slot of this.slots) {\n if (slot > cutoff) {\n const bucket = this.itemsBySlot.get(slot);\n if (bucket) {\n for (const item of bucket.values()) drained.push(item);\n this.itemsBySlot.delete(slot);\n this.sizeValue -= bucket.size;\n }\n } else {\n keep.push(slot);\n }\n }\n this.slots.length = 0;\n this.slots.push(...keep);\n return drained;\n }\n\n drainAll(): T[] {\n if (!this.slots.length) return [];\n const drained: T[] = [];\n for (const slot of this.slots) {\n const bucket = this.itemsBySlot.get(slot);\n if (!bucket) continue;\n for (const item of bucket.values()) drained.push(item);\n this.sizeValue -= bucket.size;\n this.itemsBySlot.delete(slot);\n }\n this.slots.length = 0;\n return drained;\n }\n\n minSlot(): Slot | null {\n return this.slots.length ? this.slots[0] : null;\n }\n\n get size(): number {\n return this.sizeValue;\n }\n\n private findInsertIndex(slot: Slot): number {\n let low = 0;\n let high = this.slots.length;\n while (low < high) {\n const mid = (low + high) >> 1;\n if (this.slots[mid] < slot) low = mid + 1;\n else high = mid;\n }\n return low;\n }\n}\n","import type { ReplayLogger } from \"./types\";\n\nconst noop = (): void => undefined;\n\nexport const NOOP_LOGGER: ReplayLogger = {\n debug: noop,\n info: noop,\n warn: noop,\n error: noop,\n};\n\nexport function createConsoleLogger(prefix = \"Replay\"): ReplayLogger {\n return {\n debug: (message, meta) => console.debug(`[${prefix}] ${message}`, meta ?? \"\"),\n info: (message, meta) => console.info(`[${prefix}] ${message}`, meta ?? \"\"),\n warn: (message, meta) => console.warn(`[${prefix}] ${message}`, meta ?? \"\"),\n error: (message, meta) => console.error(`[${prefix}] ${message}`, meta ?? \"\"),\n };\n}\n","import { AsyncQueue } from \"./async-queue\";\nimport { DedupBuffer } from \"./dedup-buffer\";\nimport { NOOP_LOGGER } from \"./logger\";\nimport type { ReplayLogger, Slot } from \"./types\";\n\ntype PumpMode = \"buffering\" | \"streaming\";\n\nexport class LivePump<T> {\n private readonly queue = new AsyncQueue<T>();\n private readonly buffer: DedupBuffer<T>;\n private readonly slotOf: (item: T) => Slot;\n private readonly keyOf: (item: T) => string;\n private readonly source: AsyncIterable<T>;\n private readonly logger: ReplayLogger;\n private mode: PumpMode;\n private minSlotSeen: Slot | null = null;\n private maxSlotSeen: Slot | null = null;\n private minEmitSlot: Slot | null = null;\n private pumpPromise: Promise<void>;\n\n constructor(options: {\n source: AsyncIterable<T>;\n slotOf: (item: T) => Slot;\n keyOf?: (item: T) => string;\n logger?: ReplayLogger;\n startInStreamingMode?: boolean;\n initialEmitFloor?: Slot;\n }) {\n this.source = options.source;\n this.slotOf = options.slotOf;\n this.keyOf = options.keyOf ?? ((item) => options.slotOf(item).toString());\n this.logger = options.logger ?? NOOP_LOGGER;\n this.buffer = new DedupBuffer({ slotOf: this.slotOf, keyOf: this.keyOf });\n this.mode = options.startInStreamingMode ? \"streaming\" : \"buffering\";\n if (options.startInStreamingMode) this.minEmitSlot = options.initialEmitFloor ?? 0n;\n this.pumpPromise = this.start();\n }\n\n minSlot(): Slot | null {\n if (this.minSlotSeen !== null) return this.minSlotSeen;\n return this.buffer.minSlot();\n }\n\n maxSlot(): Slot | null {\n return this.maxSlotSeen;\n }\n\n bufferedSize(): number {\n return this.buffer.size;\n }\n\n discardBufferedUpTo(cutoffSlot: Slot): number {\n if (this.mode === \"streaming\") return 0;\n const discarded = this.buffer.discardUpTo(cutoffSlot);\n if (discarded) {\n this.logger.debug(\n `discarded ${discarded} buffered items up to cutoff slot ${cutoffSlot}`\n );\n }\n return discarded;\n }\n\n enableStreaming(cutoffSlot: Slot): { drained: T[]; discarded: number } {\n if (this.mode === \"streaming\") return { drained: [], discarded: 0 };\n const discarded = this.discardBufferedUpTo(cutoffSlot);\n const drained = this.buffer.drainAbove(cutoffSlot);\n this.mode = \"streaming\";\n this.minEmitSlot = cutoffSlot;\n return { drained, discarded };\n }\n\n updateEmitFloor(slot: Slot): void {\n this.minEmitSlot = slot;\n }\n\n async next(): Promise<IteratorResult<T>> {\n return this.queue.next();\n }\n\n async close(): Promise<void> {\n this.queue.close();\n await this.pumpPromise;\n }\n\n private async start(): Promise<void> {\n try {\n for await (const item of this.source) {\n const slot = this.slotOf(item);\n if (this.minSlotSeen === null || slot < this.minSlotSeen) this.minSlotSeen = slot;\n if (this.maxSlotSeen === null || slot > this.maxSlotSeen) this.maxSlotSeen = slot;\n if (this.mode === \"buffering\") this.buffer.insert(item);\n else {\n if (this.minEmitSlot !== null && slot < this.minEmitSlot) continue;\n this.queue.push(item);\n }\n }\n this.queue.close();\n } catch (err) {\n // Don't log here - let the consumer (ReplayStream) handle logging\n // since it knows whether a retry will happen\n this.queue.fail(err);\n }\n }\n}\n","/**\n * Retry utilities for stream reconnection with exponential backoff.\n */\n\nexport interface RetryConfig {\n /** Initial delay before first retry (default: 1000ms) */\n initialDelayMs: number;\n /** Maximum delay between retries (default: 30000ms) */\n maxDelayMs: number;\n /** Timeout for connection/read operations (default: 30000ms) */\n connectionTimeoutMs: number;\n}\n\nexport const DEFAULT_RETRY_CONFIG: RetryConfig = {\n initialDelayMs: 1000,\n maxDelayMs: 30000,\n connectionTimeoutMs: 300_000,\n};\n\n/**\n * Calculate exponential backoff delay for a given attempt number.\n * Starts at initialDelayMs and doubles each attempt, capped at maxDelayMs.\n *\n * @param attempt - Zero-based attempt number (0 = first retry)\n * @param config - Retry configuration\n * @returns Delay in milliseconds\n */\nexport function calculateBackoff(attempt: number, config: RetryConfig): number {\n const delay = config.initialDelayMs * Math.pow(2, attempt);\n return Math.min(delay, config.maxDelayMs);\n}\n\n/**\n * Wrap a promise with a timeout. Rejects with TimeoutError if the promise\n * doesn't resolve within the specified time.\n *\n * @param promise - Promise to wrap\n * @param timeoutMs - Timeout in milliseconds\n * @returns Promise that resolves with the original value or rejects on timeout\n */\nexport function withTimeout<T>(\n promise: Promise<T>,\n timeoutMs: number\n): Promise<T> {\n return new Promise<T>((resolve, reject) => {\n const timer = setTimeout(() => {\n reject(new TimeoutError(`Operation timed out after ${timeoutMs}ms`));\n }, timeoutMs);\n\n promise\n .then((value) => {\n clearTimeout(timer);\n resolve(value);\n })\n .catch((err) => {\n clearTimeout(timer);\n reject(err);\n });\n });\n}\n\n/**\n * Error thrown when an operation times out.\n */\nexport class TimeoutError extends Error {\n constructor(message: string) {\n super(message);\n this.name = \"TimeoutError\";\n }\n}\n\n/**\n * Delay execution for a specified number of milliseconds.\n */\nexport function delay(ms: number): Promise<void> {\n return new Promise((resolve) => setTimeout(resolve, ms));\n}\n","import { LivePump } from \"./live-pump\";\nimport { NOOP_LOGGER } from \"./logger\";\nimport {\n DEFAULT_RETRY_CONFIG,\n calculateBackoff,\n withTimeout,\n delay,\n type RetryConfig,\n} from \"./retry\";\nimport type { BackfillFetcher, LiveSubscriber, ReplayConfig, ReplayMetrics, Slot } from \"./types\";\n\nconst DEFAULT_METRICS: ReplayMetrics = {\n bufferedItems: 0,\n emittedBackfill: 0,\n emittedLive: 0,\n emittedReconnect: 0,\n discardedDuplicates: 0,\n};\n\nfunction compareBigint(a: Slot, b: Slot): number {\n if (a === b) return 0;\n return a < b ? -1 : 1;\n}\n\nexport class ReplayStream<T, Cursor = unknown> implements AsyncIterable<T> {\n private readonly config: ReplayConfig<T, Cursor>;\n private readonly logger;\n private readonly metrics: ReplayMetrics = { ...DEFAULT_METRICS };\n\n constructor(config: ReplayConfig<T, Cursor>) {\n this.config = config;\n this.logger = config.logger ?? NOOP_LOGGER;\n }\n\n getMetrics(): ReplayMetrics {\n return { ...this.metrics };\n }\n\n [Symbol.asyncIterator](): AsyncIterator<T> {\n return this.run();\n }\n\n private async *run(): AsyncGenerator<T> {\n const {\n startSlot,\n fetchBackfill,\n subscribeLive,\n extractSlot,\n extractKey,\n safetyMargin,\n resubscribeOnEnd,\n onReconnect,\n } = this.config;\n const shouldResubscribeOnEnd = resubscribeOnEnd ?? true;\n const keyOf = extractKey ?? ((item: T) => extractSlot(item).toString());\n\n // Mutable data sources - may be replaced on reconnection with fresh client\n let currentSubscribeLive: LiveSubscriber<T> = subscribeLive;\n let currentFetchBackfill: BackfillFetcher<T, Cursor> = fetchBackfill;\n\n const createLivePump = (slot: Slot, startStreaming = false, emitFloor?: Slot) =>\n new LivePump<T>({\n source: currentSubscribeLive(slot),\n slotOf: extractSlot,\n keyOf,\n logger: this.logger,\n startInStreamingMode: startStreaming,\n initialEmitFloor: emitFloor,\n });\n let livePump = createLivePump(startSlot);\n\n let cursor: Cursor | undefined;\n let backfillDone = false;\n let currentSlot: Slot = startSlot > 0n ? startSlot - 1n : 0n;\n let lastEmittedSlot: Slot | null = null;\n let lastSlotKeys = new Set<string>();\n\n const seenItem = (slot: Slot, key: string): boolean => {\n if (lastEmittedSlot === null) return false;\n if (slot < lastEmittedSlot) return true;\n if (slot > lastEmittedSlot) return false;\n return lastSlotKeys.has(key);\n };\n\n const recordEmission = (slot: Slot, key: string): void => {\n if (lastEmittedSlot === null || slot !== lastEmittedSlot) {\n lastEmittedSlot = slot;\n lastSlotKeys = new Set([key]);\n } else {\n lastSlotKeys.add(key);\n }\n };\n\n this.logger.info(\n `replay entering BACKFILLING state (startSlot=${startSlot}, safetyMargin=${safetyMargin})`\n );\n\n while (!backfillDone) {\n const page = await fetchBackfill({ startSlot, cursor });\n if (!page.items.length && !page.cursor && !page.done) {\n // Nothing returned but not marked done: continue to avoid tight loops\n this.logger.warn(\"empty backfill page without cursor; retrying\");\n continue;\n }\n\n const sorted = [...page.items].sort((a, b) =>\n compareBigint(extractSlot(a), extractSlot(b)),\n );\n\n for (const item of sorted) {\n const slot = extractSlot(item);\n const key = keyOf(item);\n if (slot < startSlot) continue;\n if (seenItem(slot, key)) {\n this.metrics.discardedDuplicates += 1;\n continue;\n }\n currentSlot = slot;\n recordEmission(slot, key);\n this.metrics.emittedBackfill += 1;\n yield item;\n }\n\n const duplicatesTrimmed = livePump.discardBufferedUpTo(currentSlot);\n this.metrics.discardedDuplicates += duplicatesTrimmed;\n\n cursor = page.cursor;\n\n const maxStreamSlot = livePump.maxSlot();\n if (maxStreamSlot !== null) {\n const catchUpSlot =\n maxStreamSlot > safetyMargin ? (maxStreamSlot - safetyMargin) : 0n;\n if (currentSlot >= catchUpSlot) {\n this.logger.info(\n `replay reached SWITCHING threshold (currentSlot=${currentSlot}, maxStreamSlot=${maxStreamSlot}, catchUpSlot=${catchUpSlot})`\n );\n backfillDone = true;\n }\n }\n\n if (page.done || cursor === undefined) backfillDone = true;\n }\n\n this.logger.info(`replay entering SWITCHING state (currentSlot=${currentSlot})`);\n\n const { drained, discarded } = livePump.enableStreaming(currentSlot);\n this.metrics.bufferedItems = drained.length;\n this.metrics.discardedDuplicates += discarded;\n\n for (const item of drained) {\n const slot = extractSlot(item);\n const key = keyOf(item);\n if (seenItem(slot, key)) {\n this.metrics.discardedDuplicates += 1;\n continue;\n }\n currentSlot = slot;\n recordEmission(slot, key);\n this.metrics.emittedLive += 1;\n yield item;\n livePump.updateEmitFloor(currentSlot);\n }\n if (!drained.length) livePump.updateEmitFloor(currentSlot);\n\n this.logger.info(\"replay entering STREAMING state\");\n const retryConfig = DEFAULT_RETRY_CONFIG;\n let retryAttempt = 0;\n while (true) {\n try {\n // Add timeout to detect hung streams\n const next = await withTimeout(\n livePump.next(),\n retryConfig.connectionTimeoutMs\n );\n retryAttempt = 0; // Reset on successful message\n if (next.done) {\n if (!shouldResubscribeOnEnd) break;\n throw new Error(\"stream ended\");\n }\n const slot = extractSlot(next.value);\n const key = keyOf(next.value);\n if (seenItem(slot, key)) {\n this.metrics.discardedDuplicates += 1;\n continue;\n }\n currentSlot = slot;\n recordEmission(slot, key);\n this.metrics.emittedLive += 1;\n yield next.value;\n livePump.updateEmitFloor(currentSlot);\n } catch (err) {\n const errMsg = err instanceof Error ? err.message : String(err);\n const backoffMs = calculateBackoff(retryAttempt, retryConfig);\n this.logger.warn(\n `live stream disconnected (${errMsg}); reconnecting in ${backoffMs}ms from slot ${currentSlot} (attempt ${retryAttempt + 1})`\n );\n await delay(backoffMs);\n await safeClose(livePump);\n retryAttempt++;\n\n // Get fresh data sources from new client if factory provided\n if (onReconnect) {\n try {\n const fresh = onReconnect();\n currentSubscribeLive = fresh.subscribeLive;\n if (fresh.fetchBackfill) {\n currentFetchBackfill = fresh.fetchBackfill;\n }\n this.logger.info(\"created fresh client for reconnection\");\n } catch (factoryErr) {\n this.logger.error(\n `failed to create fresh client: ${factoryErr instanceof Error ? factoryErr.message : String(factoryErr)}; using existing`\n );\n }\n }\n\n // Mini-backfill to catch any missed events during disconnection\n if (onReconnect && currentSlot > 0n) {\n for await (const item of this.miniBackfill(\n currentSlot,\n currentFetchBackfill,\n extractSlot,\n keyOf,\n seenItem,\n recordEmission\n )) {\n // Update currentSlot as we yield items to prevent gaps\n const itemSlot = extractSlot(item);\n if (itemSlot > currentSlot) {\n currentSlot = itemSlot;\n }\n yield item;\n }\n }\n\n const resumeSlot = currentSlot > 0n ? currentSlot : 0n;\n livePump = createLivePump(resumeSlot, true, currentSlot);\n }\n }\n }\n\n /**\n * Perform mini-backfill from lastProcessedSlot to catch up after reconnection.\n * Ensures no data gaps from events that occurred during disconnection.\n */\n private async *miniBackfill(\n fromSlot: Slot,\n fetchBackfill: BackfillFetcher<T, Cursor>,\n extractSlot: (item: T) => Slot,\n keyOf: (item: T) => string,\n seenItem: (slot: Slot, key: string) => boolean,\n recordEmission: (slot: Slot, key: string) => void\n ): AsyncGenerator<T> {\n this.logger.info(`mini-backfill starting from slot ${fromSlot}`);\n const MINI_BACKFILL_TIMEOUT = 30000; // 30 seconds max\n const startTime = Date.now();\n\n let cursor: Cursor | undefined;\n let itemsYielded = 0;\n\n try {\n while (true) {\n if (Date.now() - startTime > MINI_BACKFILL_TIMEOUT) {\n this.logger.warn(`mini-backfill timed out after ${MINI_BACKFILL_TIMEOUT}ms`);\n break;\n }\n\n const page = await fetchBackfill({ startSlot: fromSlot, cursor });\n\n const sorted = [...page.items].sort((a, b) =>\n compareBigint(extractSlot(a), extractSlot(b))\n );\n\n for (const item of sorted) {\n const slot = extractSlot(item);\n const key = keyOf(item);\n if (seenItem(slot, key)) {\n this.metrics.discardedDuplicates += 1;\n continue;\n }\n recordEmission(slot, key);\n itemsYielded++;\n this.metrics.emittedReconnect += 1;\n yield item;\n }\n\n cursor = page.cursor;\n if (page.done || cursor === undefined) break;\n }\n\n this.logger.info(`mini-backfill complete: ${itemsYielded} items yielded`);\n } catch (err) {\n this.logger.warn(\n `mini-backfill failed: ${err instanceof Error ? err.message : String(err)}; proceeding with live stream`\n );\n }\n }\n}\n\nasync function safeClose<T>(pump: LivePump<T>): Promise<void> {\n try {\n // Timeout the close to prevent hanging on stale gRPC connections\n await Promise.race([\n pump.close(),\n new Promise<void>((resolve) => setTimeout(resolve, 5000)),\n ]);\n } catch {\n /* ignore */\n }\n}\n","import { create } from \"@bufbuild/protobuf\";\nimport { type Filter, FilterSchema, type PageResponse } from \"@thru/proto\";\nimport type { Slot } from \"../types\";\n\nexport function combineFilters(base?: Filter, user?: Filter): Filter | undefined {\n if (!base && !user) return undefined;\n if (!base) return user;\n if (!user) return base;\n const expressionParts: string[] = [];\n if (base.expression) expressionParts.push(`(${base.expression})`);\n if (user.expression) expressionParts.push(`(${user.expression})`);\n return create(FilterSchema, {\n expression: expressionParts.join(\" && \") || undefined,\n params: { ...base.params, ...user.params },\n });\n}\n\nexport function slotLiteralFilter(fieldExpr: string, slot: Slot): Filter {\n return create(FilterSchema, {\n expression: `${fieldExpr} >= uint(${slot.toString()})`,\n });\n}\n\nexport function backfillPage<T>(\n items: T[],\n page?: PageResponse,\n): { items: T[]; cursor?: string; done: boolean } {\n const cursor = page?.nextPageToken ?? undefined;\n return {\n items,\n cursor,\n done: !cursor,\n };\n}\n\nexport async function* mapAsyncIterable<S, T>(\n iterable: AsyncIterable<S>,\n selector: (value: S) => T | null | undefined,\n): AsyncGenerator<T> {\n for await (const value of iterable) {\n const mapped = selector(value);\n if (mapped !== undefined && mapped !== null) yield mapped;\n }\n}\n","import { create } from \"@bufbuild/protobuf\";\nimport {\n type Filter,\n type PageRequest,\n PageRequestSchema,\n type ConsensusStatus,\n type Block,\n type BlockView,\n type ListBlocksRequest,\n ListBlocksRequestSchema,\n type StreamBlocksRequest,\n StreamBlocksRequestSchema,\n type StreamBlocksResponse,\n} from \"@thru/proto\";\nimport type { BlockSource } from \"../chain-client\";\nimport { ReplayStream } from \"../replay-stream\";\nimport { NOOP_LOGGER } from \"../logger\";\nimport type { ReplayLogger, Slot } from \"../types\";\nimport { backfillPage, combineFilters, mapAsyncIterable, slotLiteralFilter } from \"./helpers\";\n\nexport interface BlockReplayOptions {\n client: BlockSource;\n startSlot: Slot;\n safetyMargin?: bigint;\n pageSize?: number;\n filter?: Filter;\n view?: BlockView;\n minConsensus?: ConsensusStatus;\n logger?: ReplayLogger;\n resubscribeOnEnd?: boolean;\n}\n\nconst DEFAULT_PAGE_SIZE = 128;\nconst DEFAULT_SAFETY_MARGIN = 32n;\nconst PAGE_ORDER_ASC = \"slot asc\";\n\nexport function createBlockReplay(options: BlockReplayOptions): ReplayStream<Block, string> {\n const safetyMargin = options.safetyMargin ?? DEFAULT_SAFETY_MARGIN;\n const logger = options.logger ?? NOOP_LOGGER;\n\n const fetchBackfill = async ({\n startSlot,\n cursor,\n }: {\n startSlot: Slot;\n cursor?: string;\n }) => {\n const page = create(PageRequestSchema, {\n pageSize: options.pageSize ?? DEFAULT_PAGE_SIZE,\n orderBy: PAGE_ORDER_ASC,\n pageToken: cursor,\n });\n\n const mergedFilter = combineFilters(slotLiteralFilter(\"block.header.slot\", startSlot), options.filter);\n logger.debug?.(\"block backfill request\", {\n startSlot: startSlot.toString(),\n cursor,\n pageSize: page.pageSize,\n });\n\n let response;\n try {\n response = await options.client.listBlocks(\n create(ListBlocksRequestSchema, {\n filter: mergedFilter,\n page,\n view: options.view,\n minConsensus: options.minConsensus,\n }),\n );\n } catch (err) {\n logger.error(\"block backfill request failed\", {\n startSlot: startSlot.toString(),\n cursor,\n err,\n });\n throw err;\n }\n\n return backfillPage(response.blocks, response.page);\n };\n\n const subscribeLive = (startSlot: Slot): AsyncIterable<Block> => {\n const request = create(StreamBlocksRequestSchema, {\n startSlot,\n filter: options.filter,\n view: options.view,\n minConsensus: options.minConsensus,\n });\n return mapAsyncIterable(\n options.client.streamBlocks(request),\n (resp: StreamBlocksResponse) => resp.block,\n );\n };\n\n return new ReplayStream<Block, string>({\n startSlot: options.startSlot,\n safetyMargin,\n fetchBackfill,\n subscribeLive,\n extractSlot: (block) => block.header?.slot ?? 0n,\n logger: options.logger,\n resubscribeOnEnd: options.resubscribeOnEnd,\n });\n}\n","import { create } from \"@bufbuild/protobuf\";\nimport {\n type Filter,\n type PageRequest,\n PageRequestSchema,\n type ConsensusStatus,\n type Transaction,\n type ListTransactionsRequest,\n ListTransactionsRequestSchema,\n type StreamTransactionsRequest,\n StreamTransactionsRequestSchema,\n type StreamTransactionsResponse,\n} from \"@thru/proto\";\nimport type { TransactionSource } from \"../chain-client\";\nimport { ReplayStream } from \"../replay-stream\";\nimport type { ReplayLogger, Slot } from \"../types\";\nimport { backfillPage, combineFilters, mapAsyncIterable, slotLiteralFilter } from \"./helpers\";\n\nexport interface TransactionReplayOptions {\n client: TransactionSource;\n startSlot: Slot;\n safetyMargin?: bigint;\n pageSize?: number;\n filter?: Filter;\n minConsensus?: ConsensusStatus;\n returnEvents?: boolean;\n logger?: ReplayLogger;\n resubscribeOnEnd?: boolean;\n}\n\nconst DEFAULT_PAGE_SIZE = 256;\nconst DEFAULT_SAFETY_MARGIN = 64n;\nconst PAGE_ORDER_ASC = \"slot asc\";\n\nexport function createTransactionReplay(\n options: TransactionReplayOptions,\n): ReplayStream<Transaction, string> {\n const safetyMargin = options.safetyMargin ?? DEFAULT_SAFETY_MARGIN;\n\n const fetchBackfill = async ({\n startSlot,\n cursor,\n }: {\n startSlot: Slot;\n cursor?: string;\n }) => {\n const page = create(PageRequestSchema, {\n pageSize: options.pageSize ?? DEFAULT_PAGE_SIZE,\n orderBy: PAGE_ORDER_ASC,\n pageToken: cursor,\n });\n\n const mergedFilter = combineFilters(slotLiteralFilter(\"transaction.slot\", startSlot), options.filter);\n const response = await options.client.listTransactions(\n create(ListTransactionsRequestSchema, {\n filter: mergedFilter,\n page,\n minConsensus: options.minConsensus,\n returnEvents: options.returnEvents,\n }),\n );\n\n return backfillPage(response.transactions, response.page);\n };\n\n const subscribeLive = (startSlot: Slot): AsyncIterable<Transaction> => {\n const mergedFilter = combineFilters(slotLiteralFilter(\"transaction.slot\", startSlot), options.filter);\n const request = create(StreamTransactionsRequestSchema, {\n filter: mergedFilter,\n minConsensus: options.minConsensus,\n });\n return mapAsyncIterable(\n options.client.streamTransactions(request),\n (resp: StreamTransactionsResponse) => resp.transaction,\n );\n };\n\n return new ReplayStream<Transaction, string>({\n startSlot: options.startSlot,\n safetyMargin,\n fetchBackfill,\n subscribeLive,\n extractSlot: (tx) => tx.slot ?? 0n,\n extractKey: transactionKey,\n logger: options.logger,\n resubscribeOnEnd: options.resubscribeOnEnd,\n });\n}\n\nfunction transactionKey(tx: Transaction): string {\n const signatureBytes = tx.signature?.value;\n if (signatureBytes && signatureBytes.length) return bytesToHex(signatureBytes);\n const slotPart = tx.slot?.toString() ?? \"0\";\n const offsetPart = tx.blockOffset?.toString() ?? \"0\";\n return `${slotPart}:${offsetPart}`;\n}\n\nfunction bytesToHex(bytes: Uint8Array): string {\n let hex = \"\";\n for (const byte of bytes) hex += byte.toString(16).padStart(2, \"0\");\n return hex;\n}\n","export type Slot = bigint;\n\n/**\n * Options for providing a client instance, a factory, or both.\n * At least one of client or clientFactory must be provided.\n */\nexport interface ClientOrFactory<T> {\n /** Client instance for initial connection. Optional if clientFactory provided. */\n client?: T;\n /** Factory to create fresh clients on reconnection. Enables robust reconnection. */\n clientFactory?: () => T;\n}\n\n/**\n * Resolve a client from ClientOrFactory options.\n * Prefers clientFactory if available, falls back to client.\n * @throws Error if neither client nor clientFactory is provided\n */\nexport function resolveClient<T>(\n opts: ClientOrFactory<T>,\n optionsName: string\n): T {\n if (opts.clientFactory) {\n return opts.clientFactory();\n }\n if (!opts.client) {\n throw new Error(`${optionsName} requires either client or clientFactory`);\n }\n return opts.client;\n}\n\nexport interface BackfillPage<T, Cursor = unknown> {\n items: T[];\n cursor?: Cursor;\n done?: boolean;\n}\n\nexport type BackfillFetcher<T, Cursor = unknown> = (params: {\n startSlot: Slot;\n cursor?: Cursor;\n}) => Promise<BackfillPage<T, Cursor>>;\n\nexport type LiveSubscriber<T> = (startSlot: Slot) => AsyncIterable<T>;\n\nexport interface ReplayLogger {\n debug(message: string, meta?: Record<string, unknown>): void;\n info(message: string, meta?: Record<string, unknown>): void;\n warn(message: string, meta?: Record<string, unknown>): void;\n error(message: string, meta?: Record<string, unknown>): void;\n}\n\nexport interface ReplayMetrics {\n bufferedItems: number;\n emittedBackfill: number;\n emittedLive: number;\n emittedReconnect: number;\n discardedDuplicates: number;\n}\n\n/**\n * Data sources returned by onReconnect callback.\n * Provides fresh functions that use a new client/transport.\n */\nexport interface ReconnectSources<T, Cursor = unknown> {\n subscribeLive: LiveSubscriber<T>;\n fetchBackfill?: BackfillFetcher<T, Cursor>;\n}\n\nexport interface ReplayConfig<T, Cursor = unknown> {\n startSlot: Slot;\n safetyMargin: bigint;\n fetchBackfill: BackfillFetcher<T, Cursor>;\n subscribeLive: LiveSubscriber<T>;\n extractSlot: (item: T) => Slot;\n extractKey?: (item: T) => string;\n logger?: ReplayLogger;\n resubscribeOnEnd?: boolean;\n /**\n * Called on reconnection to get fresh data sources.\n * When provided, creates new client/transport for each reconnection attempt.\n */\n onReconnect?: () => ReconnectSources<T, Cursor>;\n}\n","import { create } from \"@bufbuild/protobuf\";\nimport {\n type Filter,\n type PageRequest,\n PageRequestSchema,\n type Event,\n EventSchema,\n type ListEventsRequest,\n ListEventsRequestSchema,\n type StreamEventsRequest,\n StreamEventsRequestSchema,\n type StreamEventsResponse,\n} from \"@thru/proto\";\nimport type { EventSource } from \"../chain-client\";\nimport { ReplayStream } from \"../replay-stream\";\nimport type { ReplayLogger, Slot } from \"../types\";\nimport { resolveClient } from \"../types\";\nimport { backfillPage, combineFilters, mapAsyncIterable, slotLiteralFilter } from \"./helpers\";\n\nexport interface EventReplayOptions {\n /** Client instance for initial connection. Optional if clientFactory provided. */\n client?: EventSource;\n /** Factory to create fresh clients on reconnection. Enables robust reconnection. */\n clientFactory?: () => EventSource;\n startSlot: Slot;\n safetyMargin?: bigint;\n pageSize?: number;\n filter?: Filter;\n logger?: ReplayLogger;\n resubscribeOnEnd?: boolean;\n}\n\nconst DEFAULT_PAGE_SIZE = 512;\nconst DEFAULT_SAFETY_MARGIN = 64n;\nconst PAGE_ORDER_ASC = \"slot asc\";\n\nexport function createEventReplay(options: EventReplayOptions): ReplayStream<Event, string> {\n const safetyMargin = options.safetyMargin ?? DEFAULT_SAFETY_MARGIN;\n\n // Resolve initial client - either from options or from factory\n let currentClient = resolveClient(options, \"EventReplayOptions\");\n\n const createFetchBackfill = (client: EventSource) => async ({\n startSlot,\n cursor,\n }: {\n startSlot: Slot;\n cursor?: string;\n }) => {\n const page = create(PageRequestSchema, {\n pageSize: options.pageSize ?? DEFAULT_PAGE_SIZE,\n orderBy: PAGE_ORDER_ASC,\n pageToken: cursor,\n });\n\n const baseFilter = slotLiteralFilter(\"event.slot\", startSlot);\n const mergedFilter = combineFilters(baseFilter, options.filter);\n const response = await client.listEvents(\n create(ListEventsRequestSchema, {\n filter: mergedFilter,\n page,\n }),\n );\n\n return backfillPage(response.events, response.page);\n };\n\n const createSubscribeLive = (client: EventSource) => (startSlot: Slot): AsyncIterable<Event> => {\n const mergedFilter = combineFilters(slotLiteralFilter(\"event.slot\", startSlot), options.filter);\n const request = create(StreamEventsRequestSchema, {\n filter: mergedFilter,\n });\n return mapAsyncIterable(\n client.streamEvents(request),\n (resp: StreamEventsResponse) => streamResponseToEvent(resp),\n );\n };\n\n // Reconnection handler - creates fresh client and returns new data source functions\n const onReconnect = options.clientFactory\n ? () => {\n currentClient = options.clientFactory!();\n return {\n subscribeLive: createSubscribeLive(currentClient),\n fetchBackfill: createFetchBackfill(currentClient),\n };\n }\n : undefined;\n\n return new ReplayStream<Event, string>({\n startSlot: options.startSlot,\n safetyMargin,\n fetchBackfill: createFetchBackfill(currentClient),\n subscribeLive: createSubscribeLive(currentClient),\n extractSlot: (event) => event.slot ?? 0n,\n extractKey: eventKey,\n logger: options.logger,\n resubscribeOnEnd: options.resubscribeOnEnd,\n onReconnect,\n });\n}\n\nfunction streamResponseToEvent(resp: StreamEventsResponse): Event {\n return create(EventSchema, {\n eventId: resp.eventId,\n transactionSignature: resp.signature,\n program: resp.program,\n payload: resp.payload,\n slot: resp.slot,\n callIdx: resp.callIdx,\n timestamp: resp.timestamp,\n });\n}\n\nfunction eventKey(event: Event): string {\n if (event.eventId) return event.eventId;\n const slotPart = event.slot?.toString() ?? \"0\";\n return `${slotPart}:${event.callIdx ?? 0}`;\n}\n","/**\n * Page Assembler for multi-page account updates.\n *\n * Large accounts are split into multiple AccountPage messages (4KB chunks).\n * This module buffers pages and emits complete account data when all pages\n * for a given sequence number are received.\n */\n\nimport type { AccountMeta, AccountPage } from \"@thru/proto\";\nimport type { AccountUpdate } from \"@thru/proto\";\n\n/** Standard page size for account data (4KB) */\nexport const PAGE_SIZE = 4096;\n\n/**\n * Represents a buffered page update waiting for assembly\n */\ninterface BufferedPage {\n pageIdx: number;\n pageData: Uint8Array;\n}\n\n/**\n * State for an account update being assembled from pages\n */\ninterface PendingUpdate {\n slot: bigint;\n seq: bigint;\n meta: AccountMeta;\n pages: Map<number, BufferedPage>;\n expectedPageCount: number;\n receivedAt: number;\n}\n\n/**\n * Assembled account data ready for processing\n */\nexport interface AssembledAccount {\n address: Uint8Array;\n slot: bigint;\n seq: bigint;\n meta: AccountMeta;\n data: Uint8Array;\n isDelete: boolean;\n}\n\n/**\n * Options for the PageAssembler\n */\nexport interface PageAssemblerOptions {\n /**\n * Timeout in milliseconds for incomplete page assemblies.\n * After this duration, incomplete assemblies are discarded.\n * Default: 30000 (30 seconds)\n */\n assemblyTimeout?: number;\n\n /**\n * Maximum number of pending assemblies per address.\n * Older assemblies are evicted when limit is exceeded.\n * Default: 10\n */\n maxPendingPerAddress?: number;\n}\n\n/**\n * Convert address bytes to hex string for use as map key\n */\nfunction addressToKey(address: Uint8Array): string {\n return Array.from(address)\n .map((b) => b.toString(16).padStart(2, \"0\"))\n .join(\"\");\n}\n\n/**\n * Calculate expected page count from data size\n */\nfunction calculatePageCount(dataSize: number): number {\n if (dataSize === 0) return 0;\n return Math.ceil(dataSize / PAGE_SIZE);\n}\n\n/**\n * Assembles multi-page account updates into complete account data.\n *\n * Usage:\n * ```typescript\n * const assembler = new PageAssembler();\n *\n * for await (const response of client.streamAccountUpdates(request)) {\n * if (response.message.case === \"update\") {\n * const assembled = assembler.processUpdate(address, response.message.value);\n * if (assembled) {\n * // Complete account data is ready\n * console.log(\"Assembled account:\", assembled);\n * }\n * }\n * }\n * ```\n */\nexport class PageAssembler {\n private readonly assemblyTimeout: number;\n private readonly maxPendingPerAddress: number;\n\n /**\n * Pending updates keyed by address (hex) -> seq (string) -> PendingUpdate\n */\n private pending: Map<string, Map<string, PendingUpdate>> = new Map();\n\n constructor(options: PageAssemblerOptions = {}) {\n this.assemblyTimeout = options.assemblyTimeout ?? 30000;\n this.maxPendingPerAddress = options.maxPendingPerAddress ?? 10;\n }\n\n /**\n * Process an account update and return assembled account if complete.\n *\n * @param address - Account address bytes\n * @param update - Account update from streaming response\n * @returns Assembled account if all pages received, null otherwise\n */\n processUpdate(address: Uint8Array, update: AccountUpdate): AssembledAccount | null {\n const addressKey = addressToKey(address);\n\n // Handle delete updates immediately\n if (update.delete) {\n // Delete doesn't need page assembly\n return {\n address,\n slot: BigInt(update.slot.toString()),\n seq: update.meta?.seq ? BigInt(update.meta.seq.toString()) : 0n,\n meta: update.meta!,\n data: new Uint8Array(0),\n isDelete: true,\n };\n }\n\n // Updates without meta are incomplete - we need meta to know data size\n if (!update.meta) {\n return null;\n }\n\n const seq = BigInt(update.meta.seq.toString());\n const seqKey = seq.toString();\n const slot = BigInt(update.slot.toString());\n\n // Get or create pending updates for this address\n let addressPending = this.pending.get(addressKey);\n if (!addressPending) {\n addressPending = new Map();\n this.pending.set(addressKey, addressPending);\n }\n\n // Get or create pending update for this sequence\n let pendingUpdate = addressPending.get(seqKey);\n if (!pendingUpdate) {\n const expectedPageCount = calculatePageCount(update.meta.dataSize);\n pendingUpdate = {\n slot,\n seq,\n meta: update.meta,\n pages: new Map(),\n expectedPageCount,\n receivedAt: Date.now(),\n };\n addressPending.set(seqKey, pendingUpdate);\n\n // Enforce max pending limit per address\n this.evictOldPending(addressPending);\n }\n\n // Add page if present\n if (update.page) {\n pendingUpdate.pages.set(update.page.pageIdx, {\n pageIdx: update.page.pageIdx,\n pageData: update.page.pageData,\n });\n }\n\n // Check if all pages received\n if (pendingUpdate.pages.size >= pendingUpdate.expectedPageCount) {\n // Remove from pending\n addressPending.delete(seqKey);\n if (addressPending.size === 0) {\n this.pending.delete(addressKey);\n }\n\n // Assemble data from pages\n const data = this.assemblePages(pendingUpdate);\n\n return {\n address,\n slot: pendingUpdate.slot,\n seq: pendingUpdate.seq,\n meta: pendingUpdate.meta,\n data,\n isDelete: false,\n };\n }\n\n return null;\n }\n\n /**\n * Assemble complete data from buffered pages\n */\n private assemblePages(pending: PendingUpdate): Uint8Array {\n const totalSize = pending.meta.dataSize;\n if (totalSize === 0 || pending.expectedPageCount === 0) {\n return new Uint8Array(0);\n }\n\n const result = new Uint8Array(totalSize);\n let offset = 0;\n\n // Assemble pages in order\n for (let i = 0; i < pending.expectedPageCount; i++) {\n const page = pending.pages.get(i);\n if (page) {\n result.set(page.pageData, offset);\n offset += page.pageData.length;\n }\n }\n\n return result;\n }\n\n /**\n * Evict old pending updates for an address if limit exceeded\n */\n private evictOldPending(addressPending: Map<string, PendingUpdate>): void {\n if (addressPending.size <= this.maxPendingPerAddress) {\n return;\n }\n\n // Find oldest entries to evict\n const entries = Array.from(addressPending.entries());\n entries.sort((a, b) => a[1].receivedAt - b[1].receivedAt);\n\n const toEvict = entries.length - this.maxPendingPerAddress;\n for (let i = 0; i < toEvict; i++) {\n addressPending.delete(entries[i][0]);\n }\n }\n\n /**\n * Clean up expired pending assemblies.\n * Call this periodically to prevent memory leaks.\n */\n cleanup(): number {\n const now = Date.now();\n let evicted = 0;\n\n for (const [addressKey, addressPending] of this.pending.entries()) {\n for (const [seqKey, pending] of addressPending.entries()) {\n if (now - pending.receivedAt > this.assemblyTimeout) {\n addressPending.delete(seqKey);\n evicted++;\n }\n }\n\n if (addressPending.size === 0) {\n this.pending.delete(addressKey);\n }\n }\n\n return evicted;\n }\n\n /**\n * Get current pending count for debugging\n */\n getPendingCount(): number {\n let count = 0;\n for (const addressPending of this.pending.values()) {\n count += addressPending.size;\n }\n return count;\n }\n\n /**\n * Clear all pending assemblies\n */\n clear(): void {\n this.pending.clear();\n }\n}\n","/**\n * Account Replay - streaming account state with backfill reconciliation.\n *\n * This module provides account state streaming with:\n * - Page assembly for large accounts (>4KB)\n * - Sequence number tracking for ordering\n * - Backfill reconciliation with live updates\n * - Block boundary detection via BlockFinished messages\n */\n\nimport { create } from \"@bufbuild/protobuf\";\nimport type { Account, AccountMeta, GetAccountRequest } from \"@thru/proto\";\nimport {\n AccountView,\n FilterSchema,\n FilterParamValueSchema,\n PageRequestSchema,\n PubkeySchema,\n} from \"@thru/proto\";\nimport type {\n StreamAccountUpdatesRequest,\n StreamAccountUpdatesResponse,\n ListAccountsRequest,\n BlockFinished,\n Filter,\n FilterParamValue,\n} from \"@thru/proto\";\nimport type { AccountSource } from \"./chain-client\";\nimport { PageAssembler, type AssembledAccount } from \"./page-assembler\";\nimport {\n DEFAULT_RETRY_CONFIG,\n calculateBackoff,\n delay,\n type RetryConfig,\n} from \"./retry\";\nimport type { ReplayLogger } from \"./types\";\nimport { resolveClient } from \"./types\";\nimport { NOOP_LOGGER } from \"./logger\";\n\n/**\n * Represents a complete account state ready for processing\n */\nexport interface AccountState {\n /** Account address as bytes */\n address: Uint8Array;\n /** Account address as hex string */\n addressHex: string;\n /** Slot at which this state was observed */\n slot: bigint;\n /** Sequence number for ordering updates */\n seq: bigint;\n /** Account metadata */\n meta: AccountMeta;\n /** Complete account data (assembled from pages) */\n data: Uint8Array;\n /** Whether this is a deletion */\n isDelete: boolean;\n /** Source: \"backfill\" for GetAccount during backfill, \"stream\" for live updates */\n source: \"backfill\" | \"stream\";\n}\n\n/**\n * Block finished event for detecting transaction boundaries\n */\nexport interface BlockFinishedEvent {\n slot: bigint;\n}\n\n/**\n * Union type for account replay events\n */\nexport type AccountReplayEvent =\n | { type: \"account\"; account: AccountState }\n | { type: \"blockFinished\"; block: BlockFinishedEvent };\n\n/**\n * Options for account replay (single address)\n */\nexport interface AccountReplayOptions {\n /** Account source (typically ChainClient) */\n client: AccountSource;\n\n /** Account address to stream updates for */\n address: Uint8Array;\n\n /** Account view (default: FULL for complete data) */\n view?: AccountView;\n\n /** Optional filter expression */\n filter?: {\n expression: string;\n params?: { [key: string]: { kind: { case: string; value: unknown } } };\n };\n\n /** Page assembler options */\n pageAssemblerOptions?: {\n assemblyTimeout?: number;\n maxPendingPerAddress?: number;\n };\n\n /** Cleanup interval for page assembler (default: 10000ms) */\n cleanupInterval?: number;\n}\n\n/**\n * Options for replaying accounts by owner with backfill + streaming.\n * Uses ListAccounts (META_ONLY) + GetAccount for backfill, then StreamAccountUpdates for live updates.\n */\nexport interface AccountsByOwnerReplayOptions {\n /** Account source (typically ChainClient). Optional if clientFactory provided. */\n client?: AccountSource;\n\n /** Factory to create fresh clients on reconnection. Enables robust reconnection. */\n clientFactory?: () => AccountSource;\n\n /** Program owner address - streams all accounts owned by this program */\n owner: Uint8Array;\n\n /** Account view for GetAccount calls (default: FULL for complete data) */\n view?: AccountView;\n\n /** Optional data sizes to filter (e.g., [73, 115] for TokenAccount and MintAccount) */\n dataSizes?: number[];\n\n /** Minimum last_updated_slot for resumable backfill (resume from checkpoint) */\n minUpdatedSlot?: bigint;\n\n /** Page size for ListAccounts pagination (default: 100) */\n pageSize?: number;\n\n /** Max retries for GetAccount failures (default: 3) */\n maxRetries?: number;\n\n /** Page assembler options for streaming phase */\n pageAssemblerOptions?: {\n assemblyTimeout?: number;\n maxPendingPerAddress?: number;\n };\n\n /** Cleanup interval for page assembler (default: 10000ms) */\n cleanupInterval?: number;\n\n /** Called when backfill queue is drained. Returns the highest slot seen during backfill. */\n onBackfillComplete?: (highestSlot: bigint) => void;\n\n /** Logger for debug/info/warn/error messages (default: NOOP_LOGGER) */\n logger?: ReplayLogger;\n}\n\n/**\n * Convert address bytes to hex string\n */\nfunction bytesToHex(bytes: Uint8Array): string {\n return Array.from(bytes)\n .map((b) => b.toString(16).padStart(2, \"0\"))\n .join(\"\");\n}\n\n/**\n * Convert Account snapshot to AccountState (for streaming)\n */\nfunction snapshotToState(account: Account): AccountState | null {\n if (!account.address?.value || !account.meta) {\n return null;\n }\n\n return {\n address: account.address.value,\n addressHex: bytesToHex(account.address.value),\n slot: account.versionContext?.slot ?? 0n,\n seq: BigInt(account.meta.seq.toString()),\n meta: account.meta,\n data: account.data?.data ?? new Uint8Array(0),\n isDelete: account.meta.flags?.isDeleted ?? false,\n source: \"stream\",\n };\n}\n\n/**\n * Convert AssembledAccount to AccountState (for streaming)\n */\nfunction assembledToState(assembled: AssembledAccount): AccountState {\n return {\n address: assembled.address,\n addressHex: bytesToHex(assembled.address),\n slot: assembled.slot,\n seq: assembled.seq,\n meta: assembled.meta,\n data: assembled.data,\n isDelete: assembled.isDelete,\n source: \"stream\",\n };\n}\n\n/**\n * Convert Account from GetAccount to AccountState (for backfill)\n */\nfunction getAccountToState(account: Account): AccountState | null {\n if (!account.address?.value || !account.meta) {\n return null;\n }\n\n return {\n address: account.address.value,\n addressHex: bytesToHex(account.address.value),\n slot: account.meta.lastUpdatedSlot ?? account.versionContext?.slot ?? 0n,\n seq: BigInt(account.meta.seq.toString()),\n meta: account.meta,\n data: account.data?.data ?? new Uint8Array(0),\n isDelete: account.meta.flags?.isDeleted ?? false,\n source: \"backfill\",\n };\n}\n\n/**\n * Build owner filter for ListAccounts (uses account.meta.owner, not snapshot/update prefixes)\n * Note: ListAccounts requires param name \"owner_bytes\" (not \"owner\")\n */\nfunction buildListAccountsOwnerFilter(\n owner: Uint8Array,\n dataSizes?: number[],\n minUpdatedSlot?: bigint\n): Filter {\n // ListAccounts filter uses account.meta.owner (no snapshot/update prefix)\n // Must use params.owner_bytes (required param name for ListAccounts)\n let expression = \"account.meta.owner.value == params.owner_bytes\";\n\n // Add data size filter if specified\n if (dataSizes && dataSizes.length > 0) {\n const sizeConditions = dataSizes\n .map((size) => `account.meta.data_size == uint(${size})`)\n .join(\" || \");\n expression = `(${expression}) && (${sizeConditions})`;\n }\n\n // Add minUpdatedSlot filter for resumable backfill\n if (minUpdatedSlot !== undefined && minUpdatedSlot > 0n) {\n expression = `(${expression}) && account.meta.last_updated_slot >= params.min_updated_slot`;\n }\n\n const params: { [key: string]: FilterParamValue } = {\n owner_bytes: create(FilterParamValueSchema, { kind: { case: \"bytesValue\", value: new Uint8Array(owner) } }),\n };\n\n if (minUpdatedSlot !== undefined && minUpdatedSlot > 0n) {\n params[\"min_updated_slot\"] = create(FilterParamValueSchema, { kind: { case: \"uintValue\", value: minUpdatedSlot } });\n }\n\n return create(FilterSchema, { expression, params });\n}\n\n/**\n * Create an async iterable that replays all accounts owned by a program.\n *\n * This performs hybrid backfill + streaming:\n * 1. Starts StreamAccountUpdates concurrently (yields immediately, marks addresses as \"seen\")\n * 2. ListAccounts with META_ONLY view to get addresses (cheap, no data)\n * 3. GetAccount for each address sequentially (skips if already seen from stream)\n *\n * Stream updates \"win\" - if an address is received from stream, GetAccount is skipped.\n * This provides resumable, complete account indexing with efficient use of resources.\n *\n * @param options - Replay options\n * @returns Async iterable of account replay events\n *\n * @example\n * ```typescript\n * const client = new ChainClient({ baseUrl: \"https://grpc.thru.org\" });\n *\n * for await (const event of createAccountsByOwnerReplay({\n * client,\n * owner: TOKEN_PROGRAM_ID,\n * dataSizes: [73, 115], // TokenAccount, MintAccount\n * minUpdatedSlot: checkpoint.lastProcessedSlot, // Resume from checkpoint\n * onBackfillComplete: (slot) => console.log(`Backfill queue drained at slot ${slot}`),\n * })) {\n * if (event.type === \"account\") {\n * await processAccount(event.account);\n * }\n * }\n * ```\n */\nexport async function* createAccountsByOwnerReplay(\n options: AccountsByOwnerReplayOptions\n): AsyncGenerator<AccountReplayEvent, void, undefined> {\n const {\n owner,\n view = AccountView.FULL,\n dataSizes,\n minUpdatedSlot,\n pageSize = 100,\n maxRetries = 3,\n pageAssemblerOptions,\n cleanupInterval = 10000,\n onBackfillComplete,\n clientFactory,\n logger = NOOP_LOGGER,\n } = options;\n\n // Resolve initial client - either from options or from factory\n let client = resolveClient(options, \"AccountsByOwnerReplayOptions\");\n\n // Track addresses seen from stream (these win - skip GetAccount)\n const seenFromStream = new Set<string>();\n\n // Queue of addresses to fetch via GetAccount\n const fetchQueue: Uint8Array[] = [];\n\n // Highest slot seen (for checkpoint callback)\n let highestSlotSeen = minUpdatedSlot ?? 0n;\n\n // Page assembler for streaming\n const assembler = new PageAssembler(pageAssemblerOptions);\n let cleanupTimer: ReturnType<typeof setInterval> | null = null;\n\n // Buffer for stream events\n const streamBuffer: AccountReplayEvent[] = [];\n let streamDone = false;\n let streamError: Error | null = null;\n let lastActivityTime = Date.now();\n\n try {\n // Set up periodic cleanup for page assembler\n cleanupTimer = setInterval(() => {\n assembler.cleanup();\n }, cleanupInterval);\n\n // Start streaming FIRST (concurrent with backfill)\n const streamFilter = buildOwnerFilterWithMinSlot(owner, dataSizes, minUpdatedSlot);\n const stream = client.streamAccountUpdates({ view, filter: streamFilter });\n\n // Process stream in background, buffering events\n const streamProcessor = (async () => {\n try {\n for await (const response of stream) {\n lastActivityTime = Date.now();\n const event = processResponseMulti(response, assembler);\n if (event) {\n if (event.type === \"account\") {\n // Mark as seen - don't need to GetAccount for this one\n seenFromStream.add(event.account.addressHex);\n if (event.account.slot > highestSlotSeen) {\n highestSlotSeen = event.account.slot;\n }\n }\n streamBuffer.push(event);\n }\n }\n } catch (err) {\n streamError = err as Error;\n } finally {\n streamDone = true;\n }\n })();\n\n // Helper to yield buffered stream events\n const yieldStreamBuffer = function* (): Generator<AccountReplayEvent> {\n while (streamBuffer.length > 0) {\n const event = streamBuffer.shift()!;\n if (event.type === \"account\") {\n // Ensure it's marked as seen (should already be, but belt and suspenders)\n seenFromStream.add(event.account.addressHex);\n }\n yield event;\n }\n };\n\n // ListAccounts with META_ONLY view to get addresses (no data)\n const backfillFilter = buildListAccountsOwnerFilter(owner, dataSizes, minUpdatedSlot);\n let pageToken: string | undefined;\n\n do {\n const request: Partial<ListAccountsRequest> = {\n view: AccountView.META_ONLY, // Address + metadata only, no data\n filter: backfillFilter,\n page: create(PageRequestSchema, {\n pageSize,\n pageToken,\n }),\n };\n\n const response = await client.listAccounts(request);\n\n // Queue addresses for GetAccount\n for (const account of response.accounts) {\n if (account.address?.value) {\n fetchQueue.push(account.address.value);\n }\n }\n\n pageToken = response.page?.nextPageToken;\n\n // Yield any buffered stream events between pages\n yield* yieldStreamBuffer();\n } while (pageToken);\n\n // Process fetch queue with GetAccount (sequential)\n for (const address of fetchQueue) {\n const addressHex = bytesToHex(address);\n\n // Skip if already seen from stream\n if (seenFromStream.has(addressHex)) {\n continue;\n }\n\n // Yield any buffered stream events first\n yield* yieldStreamBuffer();\n\n // Check again after processing buffer (stream may have delivered this address)\n if (seenFromStream.has(addressHex)) {\n continue;\n }\n\n // Fetch with retry\n let account: Account | null = null;\n for (let attempt = 0; attempt < maxRetries; attempt++) {\n try {\n account = await client.getAccount({\n address: create(PubkeySchema, { value: address }),\n view: AccountView.FULL,\n });\n break;\n } catch (err) {\n if (attempt === maxRetries - 1) {\n logger.error(`[backfill] failed to fetch account ${addressHex} after ${maxRetries} attempts`, { error: err });\n } else {\n // Brief delay before retry\n await new Promise(resolve => setTimeout(resolve, 100 * (attempt + 1)));\n }\n }\n }\n\n if (account) {\n const state = getAccountToState(account);\n if (state) {\n if (state.slot > highestSlotSeen) {\n highestSlotSeen = state.slot;\n }\n yield { type: \"account\", account: state };\n }\n }\n }\n\n // Signal backfill queue drained\n if (onBackfillComplete) {\n onBackfillComplete(highestSlotSeen);\n }\n\n // Streaming phase with reconnection\n const retryConfig = DEFAULT_RETRY_CONFIG;\n let retryAttempt = 0;\n let currentStream = stream;\n let currentStreamProcessor = streamProcessor;\n lastActivityTime = Date.now();\n\n // Helper to create a new stream and processor with fresh client\n const createStreamProcessor = () => {\n // Get fresh client if factory available (key fix for reconnection)\n if (clientFactory) {\n try {\n client = clientFactory();\n logger.info(\"[account-stream] created fresh client for reconnection\");\n } catch (err) {\n logger.error(\"[account-stream] failed to create fresh client\", { error: err });\n // Continue with existing client as fallback\n }\n }\n\n const newStreamFilter = buildOwnerFilterWithMinSlot(owner, dataSizes, highestSlotSeen > 0n ? highestSlotSeen : minUpdatedSlot);\n const newStream = client.streamAccountUpdates({ view, filter: newStreamFilter });\n const newProcessor = (async () => {\n try {\n for await (const response of newStream) {\n retryAttempt = 0; // Reset on successful message\n lastActivityTime = Date.now();\n const event = processResponseMulti(response, assembler);\n if (event) {\n if (event.type === \"account\") {\n seenFromStream.add(event.account.addressHex);\n if (event.account.slot > highestSlotSeen) {\n highestSlotSeen = event.account.slot;\n }\n }\n streamBuffer.push(event);\n }\n }\n } catch (err) {\n streamError = err as Error;\n } finally {\n streamDone = true;\n }\n })();\n return { stream: newStream, processor: newProcessor };\n };\n\n // Continue yielding stream events with reconnection on error\n while (true) {\n // Yield any buffered events\n const hadEvents = streamBuffer.length > 0;\n yield* yieldStreamBuffer();\n if (hadEvents) {\n lastActivityTime = Date.now();\n }\n\n // Check for idle timeout - force reconnection if no activity\n if (!streamDone && Date.now() - lastActivityTime > retryConfig.connectionTimeoutMs) {\n logger.warn(\n `[account-stream] no activity for ${retryConfig.connectionTimeoutMs}ms; forcing reconnection`\n );\n streamDone = true;\n streamError = new Error(`Operation timed out after ${retryConfig.connectionTimeoutMs}ms`);\n }\n\n // Check if stream finished (normally or with error)\n if (streamDone) {\n if (streamError) {\n // Stream error - reconnect with backoff\n const backoffMs = calculateBackoff(retryAttempt, retryConfig);\n logger.warn(\n `[account-stream] disconnected (${streamError.message}); reconnecting in ${backoffMs}ms (attempt ${retryAttempt + 1})`\n );\n await delay(backoffMs);\n retryAttempt++;\n\n // Reset state\n streamDone = false;\n streamError = null;\n streamBuffer.length = 0;\n lastActivityTime = Date.now();\n\n // Create new stream\n const { stream: newStream, processor: newProcessor } = createStreamProcessor();\n currentStream = newStream;\n currentStreamProcessor = newProcessor;\n continue;\n } else {\n // Stream ended normally (no error) - this shouldn't happen in practice\n // but if it does, reconnect to maintain live updates\n logger.warn(\"[account-stream] stream ended unexpectedly; reconnecting...\");\n streamDone = false;\n lastActivityTime = Date.now();\n const { stream: newStream, processor: newProcessor } = createStreamProcessor();\n currentStream = newStream;\n currentStreamProcessor = newProcessor;\n continue;\n }\n }\n\n // Wait a bit for more stream events\n await delay(10);\n }\n } finally {\n if (cleanupTimer) {\n clearInterval(cleanupTimer);\n }\n assembler.clear();\n }\n}\n\n/**\n * Build owner filter for streaming with minimum slot filter.\n * Only yields accounts updated at or after minSlot.\n */\nfunction buildOwnerFilterWithMinSlot(\n owner: Uint8Array,\n dataSizes?: number[],\n minSlot?: bigint\n): Filter {\n // Base filter: match owner on both snapshot and update\n let expression = \"(has(snapshot.meta.owner) && snapshot.meta.owner.value == params.owner) || (has(account_update.meta.owner) && account_update.meta.owner.value == params.owner)\";\n\n // Add data size filter if specified\n if (dataSizes && dataSizes.length > 0) {\n const sizeConditions = dataSizes\n .map((size) => `snapshot.meta.data_size == uint(${size}) || account_update.meta.data_size == uint(${size})`)\n .join(\" || \");\n expression = `(${expression}) && (${sizeConditions})`;\n }\n\n // Add slot filter for handover from backfill\n // Note: We allow snapshots through (they don't have slot field) and filter updates by slot\n // has() requires a field path, so we check has(snapshot.address) to detect snapshot messages\n if (minSlot !== undefined && minSlot > 0n) {\n // Snapshots pass through (check via has(snapshot.address)), updates must have slot >= minSlot\n expression = `(${expression}) && (has(snapshot.address) || (has(account_update.slot) && account_update.slot >= params.min_slot))`;\n }\n\n const params: { [key: string]: FilterParamValue } = {\n owner: create(FilterParamValueSchema, { kind: { case: \"bytesValue\", value: new Uint8Array(owner) } }),\n };\n\n if (minSlot !== undefined && minSlot > 0n) {\n params[\"min_slot\"] = create(FilterParamValueSchema, { kind: { case: \"uintValue\", value: minSlot } });\n }\n\n return create(FilterSchema, { expression, params });\n}\n\n/**\n * Create an async iterable for account replay with page assembly.\n *\n * This function streams account updates with proper page assembly for\n * large accounts. It handles:\n * - Initial snapshots\n * - Live updates with page assembly\n * - Block finished signals\n *\n * @param options - Account replay options\n * @returns Async iterable of account replay events\n *\n * @example\n * ```typescript\n * const client = new ChainClient({ baseUrl: \"https://grpc.thru.org\" });\n *\n * for await (const event of createAccountReplay({\n * client,\n * address: accountPubkey,\n * view: AccountView.FULL,\n * })) {\n * if (event.type === \"account\") {\n * console.log(\"Account update:\", event.account.seq);\n * } else if (event.type === \"blockFinished\") {\n * console.log(\"Block finished:\", event.block.slot);\n * }\n * }\n * ```\n */\nexport async function* createAccountReplay(\n options: AccountReplayOptions\n): AsyncGenerator<AccountReplayEvent, void, undefined> {\n const {\n client,\n address,\n view = AccountView.FULL,\n filter,\n pageAssemblerOptions,\n cleanupInterval = 10000,\n } = options;\n\n const assembler = new PageAssembler(pageAssemblerOptions);\n let cleanupTimer: ReturnType<typeof setInterval> | null = null;\n\n try {\n // Set up periodic cleanup\n cleanupTimer = setInterval(() => {\n assembler.cleanup();\n }, cleanupInterval);\n\n // Build request with address filter\n const filterParams: { [key: string]: FilterParamValue } = {\n address: create(FilterParamValueSchema, { kind: { case: \"bytesValue\", value: new Uint8Array(address) } }),\n };\n if (filter?.params) {\n for (const [key, value] of Object.entries(filter.params)) {\n filterParams[key] = create(FilterParamValueSchema, value as any);\n }\n }\n\n const request: Partial<StreamAccountUpdatesRequest> = {\n view,\n filter: create(FilterSchema, {\n expression: filter?.expression\n ? `(snapshot.address.value == params.address) && (${filter.expression})`\n : \"snapshot.address.value == params.address\",\n params: filterParams,\n }),\n };\n\n // Stream account updates\n const stream = client.streamAccountUpdates(request);\n\n for await (const response of stream) {\n const event = processResponse(response, address, assembler);\n if (event) {\n yield event;\n }\n }\n } finally {\n // Cleanup\n if (cleanupTimer) {\n clearInterval(cleanupTimer);\n }\n assembler.clear();\n }\n}\n\n/**\n * Process a streaming response and return an event if available\n */\nfunction processResponse(\n response: StreamAccountUpdatesResponse,\n address: Uint8Array,\n assembler: PageAssembler\n): AccountReplayEvent | null {\n switch (response.message.case) {\n case \"snapshot\": {\n const state = snapshotToState(response.message.value);\n if (state) {\n return { type: \"account\", account: state };\n }\n return null;\n }\n\n case \"update\": {\n const assembled = assembler.processUpdate(address, response.message.value);\n if (assembled) {\n return { type: \"account\", account: assembledToState(assembled) };\n }\n return null;\n }\n\n case \"finished\": {\n return {\n type: \"blockFinished\",\n block: { slot: BigInt(response.message.value.slot.toString()) },\n };\n }\n\n default:\n return null;\n }\n}\n\n/**\n * Process a streaming response for multi-account streams (gets address from response)\n */\nfunction processResponseMulti(\n response: StreamAccountUpdatesResponse,\n assembler: PageAssembler\n): AccountReplayEvent | null {\n switch (response.message.case) {\n case \"snapshot\": {\n const state = snapshotToState(response.message.value);\n if (state) {\n return { type: \"account\", account: state };\n }\n return null;\n }\n\n case \"update\": {\n const update = response.message.value;\n // Get address from the update message\n const address = update.address?.value;\n if (!address) {\n // No address in update, cannot process\n return null;\n }\n const assembled = assembler.processUpdate(address, update);\n if (assembled) {\n return { type: \"account\", account: assembledToState(assembled) };\n }\n return null;\n }\n\n case \"finished\": {\n return {\n type: \"blockFinished\",\n block: { slot: BigInt(response.message.value.slot.toString()) },\n };\n }\n\n default:\n return null;\n }\n}\n\n/**\n * State tracker for account sequence numbers.\n *\n * Used to track the highest sequence number seen per account address\n * to ensure updates are applied in order.\n */\nexport class AccountSeqTracker {\n private seqs: Map<string, bigint> = new Map();\n\n /**\n * Get the current sequence number for an address\n */\n getSeq(addressHex: string): bigint | undefined {\n return this.seqs.get(addressHex);\n }\n\n /**\n * Check if an update should be applied (seq > current)\n */\n shouldApply(addressHex: string, seq: bigint): boolean {\n const current = this.seqs.get(addressHex);\n return current === undefined || seq > current;\n }\n\n /**\n * Update the sequence number for an address\n * Only updates if new seq is greater than current\n */\n update(addressHex: string, seq: bigint): boolean {\n const current = this.seqs.get(addressHex);\n if (current === undefined || seq > current) {\n this.seqs.set(addressHex, seq);\n return true;\n }\n return false;\n }\n\n /**\n * Remove tracking for an address\n */\n remove(addressHex: string): void {\n this.seqs.delete(addressHex);\n }\n\n /**\n * Clear all tracking\n */\n clear(): void {\n this.seqs.clear();\n }\n\n /**\n * Get count of tracked addresses\n */\n size(): number {\n return this.seqs.size;\n }\n}\n\n/**\n * Multi-account replay manager for streaming updates from multiple accounts.\n *\n * This class manages multiple account streams and provides:\n * - Unified event stream from multiple accounts\n * - Sequence number tracking per account\n * - Automatic reconnection on errors\n */\nexport class MultiAccountReplay {\n private client: AccountSource;\n private view: AccountView;\n private seqTracker: AccountSeqTracker;\n private activeStreams: Map<string, AbortController> = new Map();\n\n constructor(options: { client: AccountSource; view?: AccountView }) {\n this.client = options.client;\n this.view = options.view ?? AccountView.FULL;\n this.seqTracker = new AccountSeqTracker();\n }\n\n /**\n * Add an account to stream updates for\n */\n async *addAccount(address: Uint8Array): AsyncGenerator<AccountReplayEvent> {\n const addressHex = bytesToHex(address);\n\n // Check if already streaming\n if (this.activeStreams.has(addressHex)) {\n return;\n }\n\n const controller = new AbortController();\n this.activeStreams.set(addressHex, controller);\n\n try {\n for await (const event of createAccountReplay({\n client: this.client,\n address,\n view: this.view,\n })) {\n // Filter by sequence number\n if (event.type === \"account\") {\n if (this.seqTracker.shouldApply(event.account.addressHex, event.account.seq)) {\n this.seqTracker.update(event.account.addressHex, event.account.seq);\n yield event;\n }\n } else {\n yield event;\n }\n }\n } finally {\n this.activeStreams.delete(addressHex);\n }\n }\n\n /**\n * Remove an account from streaming\n */\n removeAccount(address: Uint8Array): void {\n const addressHex = bytesToHex(address);\n const controller = this.activeStreams.get(addressHex);\n if (controller) {\n controller.abort();\n this.activeStreams.delete(addressHex);\n }\n this.seqTracker.remove(addressHex);\n }\n\n /**\n * Get the current sequence number for an account\n */\n getSeq(addressHex: string): bigint | undefined {\n return this.seqTracker.getSeq(addressHex);\n }\n\n /**\n * Stop all streams\n */\n stop(): void {\n for (const controller of this.activeStreams.values()) {\n controller.abort();\n }\n this.activeStreams.clear();\n this.seqTracker.clear();\n }\n}\n","import { ReplaySink, ReplaySinkContext, ReplaySinkMeta } from \"./replay-sink\";\n\n\nexport class ConsoleSink<T> implements ReplaySink<T> {\n constructor(private readonly prefix = \"ReplaySink\") {}\n\n open(meta?: ReplaySinkMeta): void {\n const suffix = meta?.stream ? ` (${meta.stream})` : \"\";\n console.info(`${this.prefix}${suffix} opened`, meta?.label ?? \"\");\n }\n\n write(item: T, ctx: ReplaySinkContext): void {\n const slotLabel = ctx.slot.toString();\n console.info(\n `${this.prefix} ${ctx.phase.toUpperCase()} slot=${slotLabel}`,\n item,\n );\n }\n\n close(err?: unknown): void {\n if (err) console.warn(`${this.prefix} closing with error`, err);\n else console.info(`${this.prefix} closed`);\n }\n}\n"]}