{"record":{"id":"68d19207db7b3c5d","repo":"block/buzz","slug":"seed-replica-member","errorCode":null,"errorMessage":"seed replica member","messagePattern":"seed replica member","errorType":"panic","errorClass":null,"httpStatus":null,"severity":"error","filePath":"crates/buzz-db/src/runtime/tests.rs","lineNumber":1689,"sourceCode":"\n    let community = Uuid::new_v4();\n    for pool in [&writer, &replica] {\n        sqlx::query(\"INSERT INTO communities (id, host) VALUES ($1, $2)\")\n            .bind(community)\n            .bind(format!(\"member-routing-{}.example\", community.simple()))\n            .execute(pool)\n            .await\n            .expect(\"insert community\");\n    }\n    let cid = CommunityId::from_uuid(community);\n    let writer_only = \"aa\".repeat(32);\n    let replica_only = \"bb\".repeat(32);\n    relay_members::add_relay_member(&writer, cid, &writer_only, \"member\", None)\n        .await\n        .expect(\"seed writer member\");\n    relay_members::add_relay_member(&replica, cid, &replica_only, \"member\", None)\n        .await\n        .expect(\"seed replica member\");\n\n    let mut db = Db::from_pools(writer.clone(), replica.clone());\n    db.fence().force_open_for_tests(chrono::Utc::now());\n\n    // Budget unset ⇒ bounded arm disabled ⇒ writer.\n    assert!(\n        db.is_relay_member(cid, &writer_only)\n            .await\n            .expect(\"gate off\"),\n        \"budget unset must answer from the writer\"\n    );\n    assert!(!db.is_relay_member(cid, &replica_only).await.unwrap());\n\n    // Budget set + fresh entry ⇒ replica.\n    db.set_replica_read_max_age_for_tests(Some(std::time::Duration::from_secs(5)));\n    assert!(\n        db.is_relay_member(cid, &replica_only)\n            .await","sourceCodeStart":1671,"sourceCodeEnd":1707,"githubUrl":"https://github.com/block/buzz/blob/dad5a33865fc81a2e55b3b60746632f615ec1e3a/crates/buzz-db/src/runtime/tests.rs#L1671-L1707","documentation":"This is `.expect(\"seed replica member\")` on `relay_members::add_relay_member(&replica, cid, &replica_only, \"member\", None)`. It seeds a different pubkey (`bb`…`bb`) into the replica so divergent rows can prove which pool served later reads. It panics if the replica insert fails — FK violation on the community row, missing `relay_members` table in the replica scratch DB, or connection failure.","triggerScenarios":"Calling `add_relay_member` on the replica scratch pool when the replica DB was never migrated, its `communities` row wasn't inserted, or the replica pool connection has dropped.","commonSituations":"Scratch DBs created without schema; the seeded community id differing between pools due to a harness bug; write attempts against a read-only/standby replica configured in a real deployment scenario; column-type mismatch after schema evolution.","solutions":["Apply migrations to the replica scratch DB before seeding.","Verify the `communities` INSERT ran on the replica (the loop covers both pools — confirm no early exit).","Surface the inner sqlx error for diagnosis instead of a bare label.","Ensure the replica scratch DB accepts writes — it's a standalone scratch DB, not a physical standby.","Re-run with fresh `mem_r` scratch DB to rule out leftover conflicting rows."],"exampleFix":"// before\nrelay_members::add_relay_member(&replica, cid, &replica_only, \"member\", None)\n    .await.expect(\"seed replica member\");\n// after\nrelay_members::add_relay_member(&replica, cid, &replica_only, \"member\", None)\n    .await.unwrap_or_else(|e| panic!(\"seed replica member failed: {e}\"));","handlingStrategy":"validation","validationCode":"// Confirm the replica scratch DB is writable and migrated before seeding\nlet ok: bool = sqlx::query_scalar(\n    \"SELECT EXISTS (SELECT 1 FROM information_schema.tables WHERE table_name='relay_members')\")\n    .fetch_one(&replica).await.unwrap_or(false);\nassert!(ok, \"replica scratch DB missing relay_members — run migrations\");","typeGuard":"async fn is_writable(pool: &sqlx::PgPool) -> bool {\n    sqlx::query(\"SELECT 1\").execute(pool).await.is_ok()\n}","tryCatchPattern":"relay_members::add_relay_member(&replica, cid, &replica_only, \"member\", None)\n    .await.unwrap_or_else(|e| panic!(\"seed replica member failed: {e}\"));","preventionTips":["Migrate the replica scratch DB before seeding","Insert the community row on the replica too (the loop must complete both pools)","Use a standalone scratch DB, not a physical standby, for write seeding","Clean conflicting rows from prior runs"],"tags":["postgres","foreign-key","test-panic","seed-data"],"backgroundTag":"postgres-insert-failed","analyzedSha":"dad5a33865fc81a2e55b3b60746632f615ec1e3a","analyzedAt":"2026-08-30T13:49:18.474Z","contentChangedAt":"2026-08-30T13:49:18.474Z","schemaVersion":2},"datasetVersion":"2026-09-14T00:17:10.932Z"}