Summary
Opening a large PGN file in the client for viewing (not importing) fails with:
File too large (11503 MB, max 100 MB)
Reproduced with a megabase.pgn of ~11.5 GB.
Root cause
read_pgn_file reads the entire file into memory as a single String and rejects anything over a hardcoded 100 MB cap:
chess-client/src-tauri/src/local.rs:82-96
const MAX_FILE_SIZE: u64 = 100 * 1024 * 1024; // 100 MB
#[tauri::command]
pub async fn read_pgn_file(path: String) -> Result<String, String> {
let p = PathBuf::from(&path);
let meta = std::fs::metadata(&p).map_err(|e| format!("{path}: {e}"))?;
if meta.len() > MAX_FILE_SIZE {
return Err(format!(
"File too large ({:.0} MB, max 100 MB)",
meta.len() as f64 / 1_048_576.0
));
}
let bytes = std::fs::read(&p).map_err(|e| format!("{path}: {e}"))?;
Ok(String::from_utf8_lossy(&bytes).into_owned())
}
The 100 MB limit is a guardrail against the current read-everything-into-RAM approach — loading a multi-GB file this way would exhaust memory. So the cap itself isn't the bug; the whole-file-in-memory design is the constraint.
Notes / possible directions (for later)
- This is the view/open path, distinct from import (which already streams).
- A real fix likely means not materializing the whole file: e.g. stream/index game offsets and read games lazily as the user navigates, or page through the file, rather than returning one giant
String to the webview.
- Until then, the error message is at least accurate; could optionally point users to import for large files.
Logged from manual testing; no code changed.
Summary
Opening a large PGN file in the client for viewing (not importing) fails with:
Reproduced with a
megabase.pgnof ~11.5 GB.Root cause
read_pgn_filereads the entire file into memory as a singleStringand rejects anything over a hardcoded 100 MB cap:chess-client/src-tauri/src/local.rs:82-96The 100 MB limit is a guardrail against the current read-everything-into-RAM approach — loading a multi-GB file this way would exhaust memory. So the cap itself isn't the bug; the whole-file-in-memory design is the constraint.
Notes / possible directions (for later)
Stringto the webview.Logged from manual testing; no code changed.