python-lsp / python-lsp-server

Fork of the python-language-server project, maintained by the Spyder IDE team and the community
MIT License
1.9k stars 197 forks source link

AttributeError: 'NoneType' object has no attribute 'line_count' #488

Closed tkrabel-db closed 8 months ago

tkrabel-db commented 10 months ago

In Databricks notebooks, we log LSP errors. One common class of errors we get is this.

[
  // Request
  {
    "jsonrpc": "2.0",
    "id": 197,
    "method": "textDocument/definition",
    "params": {
      "textDocument": {
        "uri": "command://<command_id>"
      },
      "position": {
        "line": 58,
        "character": 160
      }
    }
  },
  // Response: error
  {
    "jsonrpc": "2.0",
    "id": 197,
    "error": {
      "code": -32602,
      "message": "AttributeError: 'NoneType' object has no attribute 'line_count'",
      "data": {
        "traceback": [
          "  File \"/databricks/python3/lib/python3.10/site-packages/pylsp_jsonrpc/endpoint.py\", line 117, in consume\n    self._handle_request(message['id'], message['method'], message.get('params'))\n",
          "  File \"/databricks/python3/lib/python3.10/site-packages/pylsp_jsonrpc/endpoint.py\", line 197, in _handle_request\n    handler_result = handler(params)\n",
          "  File \"/databricks/python3/lib/python3.10/site-packages/pylsp_jsonrpc/dispatchers.py\", line 25, in handler\n    return method(**(params or {}))\n",
          "  File \"/databricks/python3/lib/python3.10/site-packages/pylsp/python_lsp.py\", line 723, in m_text_document__definition\n    return self._cell_document__definition(document, position, **_kwargs)\n",
          "  File \"/databricks/python3/lib/python3.10/site-packages/pylsp/python_lsp.py\", line 690, in _cell_document__definition\n    cell_data = notebookDocument.cell_data()\n",
          "  File \"/databricks/python3/lib/python3.10/site-packages/pylsp/workspace.py\", line 615, in cell_data\n    num_lines = cell_document.line_count\n"
        ]
      }
    },
    "result": []
  }
]

This means that the cell document doesn't seem to exist (or is not retrievable for whatever reason) at the time the number of lines are computed.

We start an IO server, so we have a thread pool to consume messages from the FE. My guess is that we have race conditions, where one thread is deleting a cell while the other still tries to access it.

ccordoba12 commented 10 months ago

We start an IO server, so we have a thread pool to consume messages from the FE

Perhaps this could be avoided if the server is fully async. Since now it works serially, I think it's not hard to encounter this kind of race conditions when the server is called from different threads.