You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
Cast file loses header/tail (0-byte or truncated .cast) when the recording process dies abnormally - StreamWriter buffering defeats incremental writes #6
The cast file is written through a buffered StreamWriter without AutoFlush and without a flush after the header line. If the recording host process dies abnormally (window closed, crash, taskkill), the recording loses everything still in the buffer - for short recordings that means a 0-byte cast file without even the JSON header, and for long recordings a file that ends mid-line with unterminated JSON. This contradicts the documented behavior that the cast "is written incrementally" and stays playable.
Environment
Bsn.Host 0.1.0 (PowerShell Gallery)
Windows 11 10.0.26300, PowerShell 7.6.9 host
Killing the recording pwsh externally (or closing the console window) during a recording
Repro A - short recording loses everything
Start-InteractiveTranscript-Command 'ping -n 60 127.0.0.1'-Path .\x.cast
# from another window, a few seconds in:Stop-Process-Name pwsh # or close the console window
Result: x.cast is 0 bytes - the header (written by the CastWriter constructor) never reached disk because the default 1 KB character buffer was never filled and Dispose() never ran.
Repro B - long recording loses its tail
A ~75 s opencode TUI recording produced a 2.6 MB cast with 7384 events; the host was killed while the TUI was still running. The file's last line is truncated mid-JSON (Unterminated string passed in when parsing), so the final events are lost and strict parsers reject the file.
Root cause
src/Bsn.Host/src/PtyRecorder.cs, CastWriter:
writer=newStreamWriter(path,false,newUTF8Encoding(false));writer.NewLine="\n";// header written, but never flushed
StreamWriter buffers ~1 KB of characters; nothing is flushed until the buffer fills or Dispose() runs. The engine's finally block only runs on orderly termination.
Suggested fix
writer.Flush() (or writer.AutoFlush = true) immediately after writing the header line, so a valid header is always on disk.
AutoFlush = true for event lines (they are small and latency-tolerant), or at minimum flush after each event. The volume is trivial compared to correctness for an audit-oriented feature.
With per-line flushing, an abnormally terminated recording stays a valid asciicast file that simply ends at the last completed event.
zero_byte_cast_listing.txt - directory listing proving the killed ping recording produced a 0-byte .cast (the empty file itself cannot be attached to a gist, so the listing stands in for it)
D2_tail_excerpt.txt - last 300 characters of a 2.6 MB cast whose host was killed mid-session: the file ends mid-JSON with an unterminated string
Activity
soroshsabz commentedon Nov 6, 2026
Evidence artifacts: https://gist.github.com/soroshsabz/ef146d32218dee62b4b88555f8f2d2ce
zero_byte_cast_listing.txt- directory listing proving the killedpingrecording produced a 0-byte.cast(the empty file itself cannot be attached to a gist, so the listing stands in for it)D2_tail_excerpt.txt- last 300 characters of a 2.6 MB cast whose host was killed mid-session: the file ends mid-JSON with an unterminated stringDistribute issue tests into existing function-specific test files
Fix #5 #6 #7 #8: UTF-8 corruption, flush, cmd.exe mangling, redirecte…
Release Bsn.Host 0.2.1 (bug fixes for issues #5-#8) (#14)