{"record":{"id":"0634a16c9bb51ac6","repo":"nautechsystems/nautilus_trader","slug":"order-client-order-id-is-already-claimed-by-exec-0634a1","errorCode":null,"errorMessage":"Order {client_order_id} is already claimed by execution client {existing_client_id} and cannot be claimed by {client_id}","messagePattern":"Order (.+?) is already claimed by execution client (.+?) and cannot be claimed by (.+?)","errorType":"exception","errorClass":"anyhow::Error","httpStatus":null,"severity":"error","filePath":"crates/common/src/cache/mod.rs","lineNumber":4869,"sourceCode":"                    );\n                }\n                continue;\n            }\n\n            requested.insert(*client_order_id, *client_id);\n            ordered_claims.push((*client_order_id, *client_id));\n        }\n\n        let mut pending_claims = Vec::with_capacity(ordered_claims.len());\n        for (client_order_id, client_id) in ordered_claims {\n            if !self.orders.contains_key(&client_order_id) {\n                return Err(OrderLookupError::not_found(client_order_id).into());\n            }\n\n            match self.index.order_client.get(&client_order_id) {\n                Some(existing_client_id) if *existing_client_id == client_id => {}\n                Some(existing_client_id) => {\n                    anyhow::bail!(\n                        \"Order {client_order_id} is already claimed by execution client \\\n                         {existing_client_id} and cannot be claimed by {client_id}\"\n                    );\n                }\n                None => pending_claims.push((client_order_id, client_id)),\n            }\n        }\n\n        if pending_claims.is_empty() {\n            return Ok(());\n        }\n\n        if let Some(database) = &self.database {\n            database.index_order_clients(&pending_claims)?;\n        }\n\n        for (client_order_id, client_id) in pending_claims {\n            self.index.order_client.insert(client_order_id, client_id);","sourceCodeStart":4851,"sourceCodeEnd":4887,"githubUrl":"https://github.com/nautechsystems/nautilus_trader/blob/18893faf8b356be3320add8de2f861b0b647cf06/crates/common/src/cache/mod.rs#L4851-L4887","documentation":"A single execution-client claim fails because `index.order_client` already maps the client_order_id to a different ClientId. Only one execution client may own an order; claiming by a second client is rejected. Claims already consistent with the existing owner are no-ops, and unclaimed orders are queued into pending_claims.","triggerScenarios":"Calling the claim API for an order already claimed by another execution client; reconfiguring an exec client that previously owned orders from a prior session with a different ClientId; reconciliation handing the same order to two clients.","commonSituations":"Changing the exec client's ID in config between runs while reusing persistent order indexes; multiple adapters subscribed to overlapping venues; test setups sharing a cache across client fixtures.","solutions":["Use the existing owner client for that order (check the index before claiming).","Restore the original ClientId in config so it matches the persisted claims.","If ownership must move, release the existing claim via the intended cache path, then re-claim."],"exampleFix":null,"handlingStrategy":"validation","validationCode":"if let Some(owner) = cache.exec_client_id_for(&client_order_id) {\n    if owner != client_id { /* use the owning client or release the claim first */ }\n}","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Keep exec client IDs stable across restarts so persisted claims still match.","Check `index.order_client` before claiming an order.","Route each order to exactly one execution client."],"tags":["rust","cache","execution-client","ownership-conflict"],"backgroundTag":"duplicate-claim-conflict","analyzedSha":"18893faf8b356be3320add8de2f861b0b647cf06","analyzedAt":"2026-09-08T20:49:34.690Z","contentChangedAt":"2026-09-08T20:49:34.690Z","schemaVersion":2},"datasetVersion":"2026-09-14T05:17:10.506Z"}