{"record":{"id":"b3b2c4726c58cbf3","repo":"zeroclaw-labs/zeroclaw","slug":"qdrant-set-payload-failed-during-migration-statu","errorCode":null,"errorMessage":"Qdrant set payload failed during migration ({status}): {text}","messagePattern":"Qdrant set payload failed during migration \\((.+?)\\): (.+?)","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"crates/zeroclaw-memory/src/qdrant.rs","lineNumber":365,"sourceCode":"                    }]\n                }\n            });\n\n            let resp = self\n                .request(\n                    reqwest::Method::POST,\n                    &format!(\"/collections/{}/points/payload\", self.collection),\n                )\n                .query(&[(\"wait\", \"true\")])\n                .json(&body)\n                .send()\n                .await\n                .context(\"failed to set payload during Qdrant session_id migration\")?;\n\n            if !resp.status().is_success() {\n                let status = resp.status();\n                let text = resp.text().await.unwrap_or_default();\n                anyhow::bail!(\"Qdrant set payload failed during migration ({status}): {text}\");\n            }\n\n            rewritten += 1;\n        }\n\n        if rewritten > 0 {\n            ::zeroclaw_log::record!(\n                INFO,\n                ::zeroclaw_log::Event::new(module_path!(), ::zeroclaw_log::Action::Note)\n                    .with_attrs(\n                        ::serde_json::json!({\"rewritten\": rewritten, \"collection\": self.collection})\n                    ),\n                \"Normalized session_id payload values in Qdrant collection to sanitized form\"\n            );\n        }\n\n        Ok(())\n    }","sourceCodeStart":347,"sourceCodeEnd":383,"githubUrl":"https://github.com/zeroclaw-labs/zeroclaw/blob/88bb9c8533fc57ed7a03e36ca7c9ed2bf8336dcc/crates/zeroclaw-memory/src/qdrant.rs#L347-L383","documentation":"During the same startup migration, points whose session_id payload needs sanitizing are rewritten via POST /collections/{c}/points/payload (set payload). This error means the set-payload call returned non-2xx partway through; progress is lost and the whole migration retries on the next startup.","triggerScenarios":"Points deleted concurrently between scroll and set-payload (Qdrant 404 on missing point ids); 400 from a malformed filter; 429 rate limiting when many points need rewriting; collection dropped mid-migration.","commonSituations":"Two instances migrating the same collection simultaneously; Qdrant Cloud rate limits on a collection with many legacy session ids; ops tooling pruning points while agents restart.","solutions":["Retry startup — the migration re-scrolls and only rewrites points that still need it (idempotent)","429: stagger restarts or raise rate limits so bursts of set-payload calls fit","404 on point ids is benign if the points were deleted concurrently; a retry clears it","Ensure only one instance runs the migration at a time"],"exampleFix":null,"handlingStrategy":"retry","validationCode":null,"typeGuard":"fn is_migration_set_payload_error(e: &anyhow::Error) -> bool {\n    e.to_string().starts_with(\"Qdrant set payload failed during migration\")\n}","tryCatchPattern":"match memory.store(k, v).await {\n    Err(e) if is_migration_set_payload_error(&e) => { tokio::time::sleep(backoff).await; memory.store(k, v).await } // idempotent migration\n    other => other,\n}","preventionTips":["Run one migrating instance at a time","Watch for 429s on Qdrant Cloud and add start jitter","Don't prune points during agent restarts"],"tags":["qdrant","set-payload","migration","write-conflict","rust"],"backgroundTag":"qdrant-api-error","analyzedSha":"88bb9c8533fc57ed7a03e36ca7c9ed2bf8336dcc","analyzedAt":"2026-08-23T01:07:41.857Z","schemaVersion":2},"datasetVersion":"2026-08-23T08:06:27.607Z"}