{"record":{"id":"ad77756caad07a04","repo":"tursodatabase/turso","slug":"sync-server-supports-only-single-generation-mvcc-l","errorCode":null,"errorMessage":"sync_server supports only single-generation MVCC logical pulls: {revision}","messagePattern":"sync_server supports only single-generation MVCC logical pulls: (.+?)","errorType":"http","errorClass":null,"httpStatus":500,"severity":"error","filePath":"cli/sync_server.rs","lineNumber":929,"sourceCode":"        rest.split_once('?').map_or(rest, |(path, _)| path)\n    } else {\n        db_path\n    };\n    Ok(PathBuf::from(path))\n}\n\nfn parse_mvcc_revision_offset(revision: &str, legacy_default: u64) -> Result<u64> {\n    if revision.is_empty() {\n        return Ok(0);\n    }\n    if let Some((generation, offset)) = revision.split_once(\":o\") {\n        let generation = generation\n            .strip_prefix('g')\n            .ok_or_else(|| anyhow!(\"invalid MVCC pull revision generation: {revision}\"))?\n            .parse::<u64>()\n            .map_err(|err| anyhow!(\"invalid MVCC pull revision generation: {revision}: {err}\"))?;\n        if generation != 1 {\n            return Err(anyhow!(\n                \"sync_server supports only single-generation MVCC logical pulls: {revision}\"\n            ));\n        }\n        return offset\n            .parse::<u64>()\n            .map_err(|err| anyhow!(\"invalid MVCC pull revision offset: {revision}: {err}\"));\n    }\n    // Older page bootstrap responses from this test server used WAL frame\n    // numbers. Treat them as \"the page snapshot already includes the current\n    // logical log\" so the required follow-up logical pull becomes a no-op.\n    Ok(legacy_default)\n}\n\nfn scan_mvcc_log(log: &[u8]) -> Result<MvccLogSnapshot> {\n    if log.is_empty() {\n        return Ok(MvccLogSnapshot {\n            end_offset: 0,\n            crc_by_offset: vec![(0, 0)],","sourceCodeStart":911,"sourceCodeEnd":947,"githubUrl":"https://github.com/tursodatabase/turso/blob/bad083fafbefdeae9a42ec19bdaaad8918dcf411/cli/sync_server.rs#L911-L947","documentation":"The generation number parses but is not 1 — e.g. \"g2:o100\". Multi-generation logical logs exist after a production server checkpoints and rolls its log; this local server scans only single-generation 'lml3' logs (generation 1), so it refuses to serve offsets from later generations with HTTP 500.","triggerScenarios":"A client that previously synced against a production Turso endpoint (generation >= 2) is repointed at this local single-generation sync server without resetting its persisted state.","commonSituations":"Promoting a client from production to a local test server (or vice versa); long-lived test fixtures whose revisions outlive server log roll-overs.","solutions":["Reset the client database or clear its persisted revision so it re-bootstraps against this server.","Keep generation-2+ clients on the endpoint that produced the rolled log.","If this must work locally, recreate the local .db/.db-log pair so the server serves generation 1 from the start."],"exampleFix":"// before\nreq.client_revision = \"g2:o100\".to_string();\n\n// after: re-bootstrap, then adopt the returned revision\nreq.client_revision = String::new(); // response gives \"g1:o<end>\" to persist","handlingStrategy":"fallback","validationCode":null,"typeGuard":null,"tryCatchPattern":"On 500 'sync_server supports only single-generation MVCC logical pulls', clear the client revision (or reset the client db), re-bootstrap against this server, and persist the returned g1:o<end> revision; retrying a g2+ revision against this server can never succeed.","preventionTips":["Reset client sync state whenever you change sync endpoints.","Record which server (and generation) produced a persisted revision alongside the revision itself."],"tags":["mvcc","sync","revision","generation","logical-log"],"backgroundTag":"client-server-revision-mismatch","analyzedSha":"bad083fafbefdeae9a42ec19bdaaad8918dcf411","analyzedAt":"2026-08-16T23:12:11.798Z","schemaVersion":2},"datasetVersion":"2026-08-17T04:17:16.089Z"}