{"record":{"id":"7b1a8974b74de6d2","repo":"astral-sh/ruff","slug":"tried-to-close-document-that-didn-t-exist-at-uri","errorCode":null,"errorMessage":"tried to close document that didn't exist at {uri}","messagePattern":"tried to close document that didn't exist at (.+?)","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"crates/ruff_server/src/session/index.rs","lineNumber":331,"sourceCode":"\n    pub(super) fn close_document(&mut self, key: &DocumentKey) -> crate::Result<()> {\n        // Notebook cells URIs are removed from the index here, instead of during\n        // `update_notebook_document`. This is because a notebook cell, as a text document,\n        // is requested to be `closed` by VS Code after the notebook gets updated.\n        // This is not documented in the LSP specification explicitly, and this assumption\n        // may need revisiting in the future as we support more editors with notebook support.\n        if let DocumentKey::NotebookCell(uri) = key {\n            if self.notebook_cells.remove(uri).is_none() {\n                tracing::warn!(\"Tried to remove a notebook cell that does not exist: {uri}\",);\n            }\n            return Ok(());\n        }\n        let Some(uri) = self.uri_for_key(key).cloned() else {\n            anyhow::bail!(\"Tried to close unavailable document `{key}`\");\n        };\n\n        let Some(_) = self.documents.remove(&uri) else {\n            anyhow::bail!(\"tried to close document that didn't exist at {uri}\")\n        };\n        Ok(())\n    }\n\n    pub(super) fn client_settings(&self, key: &DocumentKey) -> Option<Arc<ClientSettings>> {\n        let uri = self.uri_for_key(key)?;\n        let WorkspaceSettings {\n            client_settings, ..\n        } = self.settings_for_uri(uri)?;\n        Some(client_settings.clone())\n    }\n\n    fn document_controller_for_key(\n        &mut self,\n        key: &DocumentKey,\n    ) -> crate::Result<&mut DocumentController> {\n        let Some(uri) = self.uri_for_key(key).cloned() else {\n            anyhow::bail!(\"Tried to open unavailable document `{key}`\");","sourceCodeStart":313,"sourceCodeEnd":349,"githubUrl":"https://github.com/astral-sh/ruff/blob/26f38c119cac42e4d320ba08f09224fdec74af2c/crates/ruff_server/src/session/index.rs#L313-L349","documentation":"In `close_document`, after resolving the key to a URI, the server removes the document entry from `self.documents`. If the URI is known but no document is registered under it, the index is internally inconsistent and the server bails. This is a stricter, lower-level check than error 84.","triggerScenarios":"Calling `session.close_document(key, encoding)` where `uri_for_key(key)` succeeds but `self.documents.remove(&uri)` returns None — the key-to-URI mapping exists without a corresponding registered document.","commonSituations":"Race or bookkeeping bug where mappings and documents are inserted/removed out of sync; double-close where only the mapping persisted; partial initialization failure.","solutions":["Restart the Ruff server to rebuild a consistent document index","Avoid sending didClose for the same document more than once","If developing against ruff_server, check that document insertion and mapping updates are atomic in open paths"],"exampleFix":null,"handlingStrategy":"try-catch","validationCode":null,"typeGuard":null,"tryCatchPattern":"if let Err(e) = session.close_document(&key, enc) { if e.to_string().contains(\"didn't exist\") { log.warn(\"inconsistent document index; restarting server\"); restart_server(); } }","preventionTips":["Avoid double-closing documents; track open state client-side","Restart the Ruff server if you suspect desynchronized session state","When embedding ruff_server, keep key-to-URI mappings and document entries updated atomically"],"tags":["lsp","documents","state"],"backgroundTag":"document-not-open","analyzedSha":"26f38c119cac42e4d320ba08f09224fdec74af2c","analyzedAt":"2026-09-05T10:32:37.492Z","contentChangedAt":"2026-09-05T10:32:37.492Z","schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}