readForward method
Reads records from the line boundary fromOffset to EOF. With
maxRecords/maxBytes (the jump and page-down paths) at most that
much is kept, scanned block-wise — the below-range of a deep-paged
window is never read whole; without caps (the live-tail ingest path
— an external CLI appended while the app held the window) everything
is returned, so a burst of external appends is never silently
dropped. The chunk's SessionChunk.limitOffset is the end of the
last kept record, so a capped read resumes exactly after it.
Implementation
Future<SessionChunk> readForward(
int fromOffset, {
int? maxRecords,
int? maxBytes,
}) async {
final info = await stat();
if (info == null) {
throw SessionException(
'Session not found: $path',
code: SessionErrorCode.notFound,
);
}
if (fromOffset >= info.size) {
return SessionChunk(
entries: const [],
fileSize: info.size,
fileMtimeMs: info.mtimeMs,
hasOlder: false,
limitOffset: info.size,
);
}
if (maxRecords != null || maxBytes != null) {
return _scanForwardCapped(
fromOffset,
size: info.size,
mtimeMs: info.mtimeMs,
// Literals, not `1 << 40`/`1 << 60`: dart2js shifts are 32-bit —
// 0 on web would read nothing (issue #1074).
maxRecords: maxRecords ?? 0x10000000000,
maxBytes: maxBytes ?? 0x1000000000000000,
);
}
final bytes = await _readRange(fromOffset, info.size);
final lines = _splitLines(bytes, fromOffset);
final entries = await _parseAllLines(lines);
return SessionChunk(
entries: entries,
fileSize: info.size,
fileMtimeMs: info.mtimeMs,
hasOlder: false,
limitOffset: info.size,
);
}