Repository: python-lsp/pylsp-mypy

Issue:
pylsp died whenever dmypy is enabled
It seems like pylsp gets killed whenever I enabled pylsp-mypy in dmypy/daemon mode.

```bash
$ dmypy kill
$ rm -r /tmp/log.txt .dmypy.json .mypy_cache
$ cat pylsp-mypy.cfg 
{
    "enabled": True,
    "live_mode": False,
    "dmypy": True,
    "strict": True
}
$ vim   ## using vim-lsp
:LspStatus
pylsp: exited
```

At this point, since pylsp had died, nothing that uses pylsp works.

Toggling dmypy to False seems to allow pylsp-mypy to work again and checking type errors as expected.

```bash
$ cat pylsp-mypy.cfg 
{
    "enabled": True,
    "live_mode": False,
    "dmypy": False,
    "strict": True
}
$ vim   ## using vim-lsp
$ pgrep -lf pylsp
471433 dmypy
471933 pylsp
```

I don't see any obvious errors on the pylsp log file (attached).

Any idea what might be happening here or how I can help further debug this?

----

   <details><summary>environment details</summary>

Python: 3.10

```
$ pip freeze
docstring-to-markdown==0.11
jedi==0.18.2
mypy==0.991
mypy-extensions==0.4.3
parso==0.8.3
pluggy==1.0.0
pylsp-mypy==0.6.5
python-lsp-jsonrpc==1.0.0
python-lsp-server==1.7.0
toml==0.10.2
tomli==2.0.1
typing_extensions==4.4.0
ujson==5.7.0
```
   </details>


   <details><summary>pylsp log file</summary>

```
$ cat /tmp/log.txt
2023-01-17 16:20:18,008 AEDT - INFO - pylsp.python_lsp - Starting PythonLSPServer IO language server
2023-01-17 16:20:18,151 AEDT - INFO - pylsp.config.config - Failed to load pylsp entry point 'autopep8': No module named 'pycodestyle'
2023-01-17 16:20:18,161 AEDT - INFO - pylsp.config.config - Failed to load pylsp entry point 'mccabe': No module named 'mccabe'
2023-01-17 16:20:18,163 AEDT - INFO - pylsp.config.config - Failed to load pylsp entry point 'pycodestyle': No module named 'pycodestyle'
2023-01-17 16:20:18,164 AEDT - INFO - pylsp.config.config - Failed to load pylsp entry point 'pydocstyle': No module named 'pydocstyle'
2023-01-17 16:20:18,165 AEDT - INFO - pylsp.config.config - Failed to load pylsp entry point 'pyflakes': No module named 'pyflakes'
2023-01-17 16:20:18,167 AEDT - INFO - pylsp.config.config - Failed to load pylsp entry point 'rope_autoimport': No module named 'rope'
2023-01-17 16:20:18,168 AEDT - INFO - pylsp.config.config - Failed to load pylsp entry point 'rope_completion': No module named 'rope'
2023-01-17 16:20:18,169 AEDT - INFO - pylsp.config.config - Failed to load pylsp entry point 'rope_rename': No module named 'rope'
2023-01-17 16:20:18,170 AEDT - INFO - pylsp.config.config - Failed to load pylsp entry point 'yapf': No module named 'yapf'
2023-01-17 16:20:18,203 AEDT - INFO - pylsp.config.config - Loaded pylsp plugin flake8 from <module 'pylsp.plugins.flake8_lint' from '/home/lieryan/.virtualenvs/dmypy-test/lib/python3.10/site-packages/pylsp/plugins/flake8_lint.py'>
2023-01-17 16:20:18,203 AEDT - INFO - pylsp.config.config - Loaded pylsp plugin folding from <module 'pylsp.plugins.folding' from '/home/lieryan/.virtualenvs/dmypy-test/lib/python3.10/site-packages/pylsp/plugins/folding.py'>
2023-01-17 16:20:18,203 AEDT - INFO - pylsp.config.config - Loaded pylsp plugin jedi_completion from <module 'pylsp.plugins.jedi_completion' from '/home/lieryan/.virtualenvs/dmypy-test/lib/python3.10/site-packages/pylsp/plugins/jedi_completion.py'>
2023-01-17 16:20:18,203 AEDT - INFO - pylsp.config.config - Loaded pylsp plugin jedi_definition from <module 'pylsp.plugins.definition' from '/home/lieryan/.virtualenvs/dmypy-test/lib/python3.10/site-packages/pylsp/plugins/definition.py'>
2023-01-17 16:20:18,203 AEDT - INFO - pylsp.config.config - Loaded pylsp plugin jedi_highlight from <module 'pylsp.plugins.highlight' from '/home/lieryan/.virtualenvs/dmypy-test/lib/python3.10/site-packages/pylsp/plugins/highlight.py'>
2023-01-17 16:20:18,203 AEDT - INFO - pylsp.config.config - Loaded pylsp plugin jedi_hover from <module 'pylsp.plugins.hover' from '/home/lieryan/.virtualenvs/dmypy-test/lib/python3.10/site-packages/pylsp/plugins/hover.py'>
2023-01-17 16:20:18,203 AEDT - INFO - pylsp.config.config - Loaded pylsp plugin jedi_references from <module 'pylsp.plugins.references' from '/home/lieryan/.virtualenvs/dmypy-test/lib/python3.10/site-packages/pylsp/plugins/references.py'>
2023-01-17 16:20:18,203 AEDT - INFO - pylsp.config.config - Loaded pylsp plugin jedi_rename from <module 'pylsp.plugins.jedi_rename' from '/home/lieryan/.virtualenvs/dmypy-test/lib/python3.10/site-packages/pylsp/plugins/jedi_rename.py'>
2023-01-17 16:20:18,203 AEDT - INFO - pylsp.config.config - Loaded pylsp plugin jedi_signature_help from <module 'pylsp.plugins.signature' from '/home/lieryan/.virtualenvs/dmypy-test/lib/python3.10/site-packages/pylsp/plugins/signature.py'>
2023-01-17 16:20:18,203 AEDT - INFO - pylsp.config.config - Loaded pylsp plugin jedi_symbols from <module 'pylsp.plugins.symbols' from '/home/lieryan/.virtualenvs/dmypy-test/lib/python3.10/site-packages/pylsp/plugins/symbols.py'>
2023-01-17 16:20:18,203 AEDT - INFO - pylsp.config.config - Loaded pylsp plugin preload from <module 'pylsp.plugins.preload_imports' from '/home/lieryan/.virtualenvs/dmypy-test/lib/python3.10/site-packages/pylsp/plugins/preload_imports.py'>
2023-01-17 16:20:18,203 AEDT - INFO - pylsp.config.config - Loaded pylsp plugin pylint from <module 'pylsp.plugins.pylint_lint' from '/home/lieryan/.virtualenvs/dmypy-test/lib/python3.10/site-packages/pylsp/plugins/pylint_lint.py'>
2023-01-17 16:20:18,204 AEDT - INFO - pylsp.config.config - Loaded pylsp plugin pylsp_mypy from <module 'pylsp_mypy.plugin' from '/home/lieryan/.virtualenvs/dmypy-test/lib/python3.10/site-packages/pylsp_mypy/plugin.py'>
2023-01-17 16:20:18,204 AEDT - INFO - pylsp_mypy.plugin - init workspace = /home/lieryan/tmp/dmypy-test
2023-01-17 16:20:18,204 AEDT - INFO - pylsp_mypy.plugin - mypyConfigFile = None configuration = {'enabled': True, 'live_mode': False, 'dmypy': True, 'strict': True}
2023-01-17 16:20:18,204 AEDT - INFO - pylsp.config.config - Disabled plugins: [<module 'pylsp.plugins.flake8_lint' from '/home/lieryan/.virtualenvs/dmypy-test/lib/python3.10/site-packages/pylsp/plugins/flake8_lint.py'>, <module 'pylsp.plugins.pylint_lint' from '/home/lieryan/.virtualenvs/dmypy-test/lib/python3.10/site-packages/pylsp/plugins/pylint_lint.py'>]
2023-01-17 16:20:18,208 AEDT - INFO - pylsp.python_lsp - Server capabilities: {'codeActionProvider': True, 'codeLensProvider': {'resolveProvider': False}, 'completionProvider': {'resolveProvider': True, 'triggerCharacters': ['.']}, 'documentFormattingProvider': True, 'documentHighlightProvider': True, 'documentRangeFormattingProvider': True, 'documentSymbolProvider': True, 'definitionProvider': True, 'executeCommandProvider': {'commands': []}, 'hoverProvider': True, 'referencesProvider': True, 'renameProvider': True, 'foldingRangeProvider': True, 'signatureHelpProvider': {'triggerCharacters': ['(', ',', '=']}, 'textDocumentSync': {'change': 2, 'save': {'includeText': True}, 'openClose': True}, 'workspace': {'workspaceFolders': {'supported': True, 'changeNotifications': True}}, 'experimental': {}}
2023-01-17 16:20:18,714 AEDT - INFO - pylsp_mypy.plugin - lint settings = {'enabled': True, 'live_mode': False, 'dmypy': True, 'strict': True} document.path = /home/lieryan/tmp/dmypy-test/foobar.py is_saved = True
2023-01-17 16:20:18,831 AEDT - INFO - pylsp_mypy.plugin - restarting dmypy from status: 2 message: No status file found via path
2023-01-17 16:20:19,148 AEDT - INFO - pylsp_mypy.plugin - dmypy run args = ['--status-file', '.dmypy.json', 'run', '--', '--show-column-numbers', '/home/lieryan/tmp/dmypy-test/foobar.py', '--strict'] via path
2023-01-17 16:20:20,968 AEDT - INFO - pylsp_mypy.plugin - pylsp-mypy len(diagnostics) = 1
```
       
   </details>

   <details><summary>vim-lsp config</summary>

```vim
    autocmd User lsp_setup call lsp#register_server({
        \ 'name': 'pylsp',
        \ 'cmd': {server_info->['pylsp', '-v', '--log-file', '/tmp/log.txt']},
        \ 'allowlist': ['python'],
        \ })
```
   </details>

Discussion:

Patch:
diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml
index 220c85e..075be77 100644
--- a/.pre-commit-config.yaml
+++ b/.pre-commit-config.yaml
@@ -10,6 +10,6 @@ repos:
     hooks:
       - id: rst-linter
   - repo: https://github.com/pycqa/isort
-    rev: 5.10.1
+    rev: 5.12.0
     hooks:
-      - id: isort
\ No newline at end of file
+      - id: isort
diff --git a/pylsp_mypy/plugin.py b/pylsp_mypy/plugin.py
index 4f31b90..a39ecd6 100644
--- a/pylsp_mypy/plugin.py
+++ b/pylsp_mypy/plugin.py
@@ -252,9 +252,7 @@ def get_diagnostics(
             # mypy exists on path
             # -> use mypy on path
             log.info("executing mypy args = %s on path", args)
-            completed_process = subprocess.run(
-                ["mypy", *args], stdout=subprocess.PIPE, stderr=subprocess.PIPE, **windows_flag
-            )
+            completed_process = subprocess.run(["mypy", *args], capture_output=True, **windows_flag)
             report = completed_process.stdout.decode()
             errors = completed_process.stderr.decode()
             exit_status = completed_process.returncode
@@ -275,7 +273,7 @@ def get_diagnostics(
             # -> use dmypy on path
             completed_process = subprocess.run(
                 ["dmypy", "--status-file", dmypy_status_file, "status"],
-                stderr=subprocess.PIPE,
+                capture_output=True,
                 **windows_flag,
             )
             errors = completed_process.stderr.decode()
@@ -287,7 +285,9 @@ def get_diagnostics(
                     errors.strip(),
                 )
                 subprocess.run(
-                    ["dmypy", "--status-file", dmypy_status_file, "restart"], **windows_flag
+                    ["dmypy", "--status-file", dmypy_status_file, "restart"],
+                    capture_output=True,
+                    **windows_flag,
                 )
         else:
             # dmypy does not exist on path, but must exist in the env pylsp-mypy is installed in
@@ -310,7 +310,7 @@ def get_diagnostics(
             # -> use mypy on path
             log.info("dmypy run args = %s via path", args)
             completed_process = subprocess.run(
-                ["dmypy", *args], stdout=subprocess.PIPE, stderr=subprocess.PIPE, **windows_flag
+                ["dmypy", *args], capture_output=True, **windows_flag
             )
             report = completed_process.stdout.decode()
             errors = completed_process.stderr.decode()


Test patch:
diff --git a/test/test_plugin.py b/test/test_plugin.py
index 4ddeec9..97181a5 100644
--- a/test/test_plugin.py
+++ b/test/test_plugin.py
@@ -223,7 +223,7 @@ def test_option_overrides_dmypy(last_diagnostics_monkeypatch, workspace):
         "--show-column-numbers",
         document.path,
     ]
-    m.assert_called_with(expected, stderr=-1, stdout=-1, **windows_flag)
+    m.assert_called_with(expected, capture_output=True, **windows_flag)
 
 
 def test_dmypy_status_file(tmpdir, last_diagnostics_monkeypatch, workspace):