bufferedWriter.ts
utils/bufferedWriter.ts
No strong subsystem tag
101
Lines
2584
Bytes
2
Exports
0
Imports
10
Keywords
What this is
This page documents one file from the repository and includes its full source so you can read it without leaving the docs site.
Beginner explanation
This file is one piece of the larger system. Its name, directory, imports, and exports show where it fits. Start by reading the exports and related files first.
How it is used
Start from the exports list and related files. Those are the easiest clues for where this file fits into the system.
Expert explanation
Architecturally, this file intersects with general runtime concerns. It contains 101 lines, 0 detected imports, and 2 detected exports.
Important relationships
Detected exports
BufferedWritercreateBufferedWriter
Keywords
bufferwritefnvoidpendingoverflowcontentflushbufferbytesflushtimerwritecleartimer
Detected imports
- No import paths detected.
Source notes
This page embeds the full file contents. Small or leaf files are still indexed honestly instead of being over-explained.
Full source
type WriteFn = (content: string) => void
export type BufferedWriter = {
write: (content: string) => void
flush: () => void
dispose: () => void
}
export function createBufferedWriter({
writeFn,
flushIntervalMs = 1000,
maxBufferSize = 100,
maxBufferBytes = Infinity,
immediateMode = false,
}: {
writeFn: WriteFn
flushIntervalMs?: number
maxBufferSize?: number
maxBufferBytes?: number
immediateMode?: boolean
}): BufferedWriter {
let buffer: string[] = []
let bufferBytes = 0
let flushTimer: NodeJS.Timeout | null = null
// Batch detached by overflow that hasn't been written yet. Tracked so
// flush()/dispose() can drain it synchronously if the process exits
// before the setImmediate fires.
let pendingOverflow: string[] | null = null
function clearTimer(): void {
if (flushTimer) {
clearTimeout(flushTimer)
flushTimer = null
}
}
function flush(): void {
if (pendingOverflow) {
writeFn(pendingOverflow.join(''))
pendingOverflow = null
}
if (buffer.length === 0) return
writeFn(buffer.join(''))
buffer = []
bufferBytes = 0
clearTimer()
}
function scheduleFlush(): void {
if (!flushTimer) {
flushTimer = setTimeout(flush, flushIntervalMs)
}
}
// Detach the buffer synchronously so the caller never waits on writeFn.
// writeFn may block (e.g. errorLogSink.ts appendFileSync) — if overflow fires
// mid-render or mid-keystroke, deferring the write keeps the current tick
// short. Timer-based flushes already run outside user code paths so they
// stay synchronous.
function flushDeferred(): void {
if (pendingOverflow) {
// A previous overflow write is still queued. Coalesce into it to
// preserve ordering — writes land in a single setImmediate-ordered batch.
pendingOverflow.push(...buffer)
buffer = []
bufferBytes = 0
clearTimer()
return
}
const detached = buffer
buffer = []
bufferBytes = 0
clearTimer()
pendingOverflow = detached
setImmediate(() => {
const toWrite = pendingOverflow
pendingOverflow = null
if (toWrite) writeFn(toWrite.join(''))
})
}
return {
write(content: string): void {
if (immediateMode) {
writeFn(content)
return
}
buffer.push(content)
bufferBytes += content.length
scheduleFlush()
if (buffer.length >= maxBufferSize || bufferBytes >= maxBufferBytes) {
flushDeferred()
}
},
flush,
dispose(): void {
flush()
},
}
}