diff --git a/external-deps/python-lsp-server/.github/workflows/test-linux.yml b/external-deps/python-lsp-server/.github/workflows/test-linux.yml index 7a7f2f6e6e1..543744a6226 100644 --- a/external-deps/python-lsp-server/.github/workflows/test-linux.yml +++ b/external-deps/python-lsp-server/.github/workflows/test-linux.yml @@ -24,7 +24,7 @@ jobs: strategy: fail-fast: false matrix: - PYTHON_VERSION: ['3.11', '3.10', '3.9'] + PYTHON_VERSION: ['3.14', '3.13', '3.12', '3.11', '3.10', '3.9'] timeout-minutes: 10 steps: - uses: actions/cache@v4 diff --git a/external-deps/python-lsp-server/.github/workflows/test-mac.yml b/external-deps/python-lsp-server/.github/workflows/test-mac.yml index a92c82a81c9..7b06ad2685e 100644 --- a/external-deps/python-lsp-server/.github/workflows/test-mac.yml +++ b/external-deps/python-lsp-server/.github/workflows/test-mac.yml @@ -24,7 +24,7 @@ jobs: strategy: fail-fast: false matrix: - PYTHON_VERSION: ['3.11', '3.10', '3.9'] + PYTHON_VERSION: ['3.14', '3.12', '3.9'] timeout-minutes: 10 steps: - uses: actions/cache@v4 diff --git a/external-deps/python-lsp-server/.github/workflows/test-win.yml b/external-deps/python-lsp-server/.github/workflows/test-win.yml index 8ecd34293e8..fa71c5ce4f1 100644 --- a/external-deps/python-lsp-server/.github/workflows/test-win.yml +++ b/external-deps/python-lsp-server/.github/workflows/test-win.yml @@ -24,7 +24,7 @@ jobs: strategy: fail-fast: false matrix: - PYTHON_VERSION: ['3.11', '3.10', '3.9'] + PYTHON_VERSION: ['3.14', '3.12', '3.9'] timeout-minutes: 10 steps: - uses: actions/cache@v4 diff --git a/external-deps/python-lsp-server/.gitrepo b/external-deps/python-lsp-server/.gitrepo index e949e790adc..79a5e122b0f 100644 --- a/external-deps/python-lsp-server/.gitrepo +++ b/external-deps/python-lsp-server/.gitrepo @@ -4,9 +4,9 @@ ; git-subrepo command. See https://github.com/git-commands/git-subrepo#readme ; [subrepo] - remote = https://github.com/python-lsp/python-lsp-server.git - branch = develop - commit = 6a24326890964b56b8349b605ed76727f3502326 - parent = b1eb96f846d1564e689ffb1c02ccaa93b1005471 + remote = https://github.com/tomekwojcik/python-lsp-server.git + branch = allow_signature_to_hide_docstrings + commit = d5788b559c96169a4ecd7b6c26c9da8726de00c2 + parent = 0a335b48d5c91a046f0bc571d9121e5a4f1a9eac method = merge - cmdver = 0.4.3 + cmdver = 0.4.9 diff --git a/external-deps/python-lsp-server/CHANGELOG.md b/external-deps/python-lsp-server/CHANGELOG.md index d32c2d473fb..c0560df25fb 100644 --- a/external-deps/python-lsp-server/CHANGELOG.md +++ b/external-deps/python-lsp-server/CHANGELOG.md @@ -1,5 +1,16 @@ # History of changes +## Version 1.13.2 (2025/11/19) + +### Pull Requests Merged + +* [PR 683](https://github.com/python-lsp/python-lsp-server/pull/683) - Prevent showing cmd on Windows when running flake8, by [@dalthviz](https://github.com/dalthviz) +* [PR 669](https://github.com/python-lsp/python-lsp-server/pull/669) - Fix license entries in `pyproject.toml` due to pep 639, by [@ccordoba12](https://github.com/ccordoba12) + +In this release 2 pull requests were closed. + +---- + ## Version 1.13.1 (2025/08/26) ### Pull Requests Merged diff --git a/external-deps/python-lsp-server/CONFIGURATION.md b/external-deps/python-lsp-server/CONFIGURATION.md index ec2a9a6c550..53d3b2f17f8 100644 --- a/external-deps/python-lsp-server/CONFIGURATION.md +++ b/external-deps/python-lsp-server/CONFIGURATION.md @@ -77,6 +77,7 @@ This server can be configured using the `workspace/didChangeConfiguration` metho | `pylsp.rope.extensionModules` | `string` | Builtin and c-extension modules that are allowed to be imported and inspected by rope. | `null` | | `pylsp.rope.ropeFolder` | `array` of unique `string` items | The name of the folder in which rope stores project configurations and data. Pass `null` for not using such a folder at all. | `null` | | `pylsp.signature.formatter` | `string` (one of: `'black'`, `'ruff'`, `None`) | Formatter to use for reformatting signatures in docstrings. | `"black"` | +| `pylsp.signature.include_docstring` | `boolean` | Include signature docstring. | `true` | | `pylsp.signature.line_length` | `number` | Maximum line length in signatures. | `88` | This documentation was generated from `pylsp/config/schema.json`. Please do not edit this file directly. diff --git a/external-deps/python-lsp-server/pylsp/_utils.py b/external-deps/python-lsp-server/pylsp/_utils.py index dfe84b14f0d..c9eb6fb1d3d 100644 --- a/external-deps/python-lsp-server/pylsp/_utils.py +++ b/external-deps/python-lsp-server/pylsp/_utils.py @@ -315,17 +315,24 @@ def format_docstring( contents = "" if markup_kind == "markdown": - try: - value = docstring_to_markdown.convert(contents) - except docstring_to_markdown.UnknownFormatError: - # try to escape the Markdown syntax instead: - value = escape_markdown(contents) - - if signatures: - wrapped_signatures = convert_signatures_to_markdown( - signatures, config=signature_config or {} - ) - value = wrapped_signatures + "\n\n" + value + wrapped_signatures = convert_signatures_to_markdown( + signatures if signatures is not None else [], config=signature_config or {} + ) + + if contents != "": + try: + value = docstring_to_markdown.convert(contents) + except docstring_to_markdown.UnknownFormatError: + # try to escape the Markdown syntax instead: + value = escape_markdown(contents) + + if signatures: + value = wrapped_signatures + "\n\n" + value + else: + value = contents + + if signatures: + value = wrapped_signatures return {"kind": "markdown", "value": value} value = contents diff --git a/external-deps/python-lsp-server/pylsp/config/schema.json b/external-deps/python-lsp-server/pylsp/config/schema.json index a0caa38aa89..67289d960e4 100644 --- a/external-deps/python-lsp-server/pylsp/config/schema.json +++ b/external-deps/python-lsp-server/pylsp/config/schema.json @@ -530,6 +530,11 @@ "default": "black", "description": "Formatter to use for reformatting signatures in docstrings." }, + "pylsp.signature.include_docstring": { + "type": "boolean", + "default": true, + "description": "Include signature docstring." + }, "pylsp.signature.line_length": { "type": "number", "default": 88, diff --git a/external-deps/python-lsp-server/pylsp/plugins/hover.py b/external-deps/python-lsp-server/pylsp/plugins/hover.py index daaae90b9c3..a23d90364e8 100644 --- a/external-deps/python-lsp-server/pylsp/plugins/hover.py +++ b/external-deps/python-lsp-server/pylsp/plugins/hover.py @@ -41,10 +41,19 @@ def pylsp_hover(config, document, position): "", ) + include_docstring = signature_config.get("include_docstring", True) + + # raw docstring returns only doc, without signature + docstring = definition.docstring(raw=True) + if not include_docstring: + if signature: + docstring = "" + else: + docstring = docstring.strip().split("\n")[0].strip() + return { "contents": _utils.format_docstring( - # raw docstring returns only doc, without signature - definition.docstring(raw=True), + docstring, preferred_markup_kind, signatures=[signature] if signature else None, signature_config=signature_config, diff --git a/external-deps/python-lsp-server/pylsp/plugins/signature.py b/external-deps/python-lsp-server/pylsp/plugins/signature.py index 7ad5b208a73..c9a473fee73 100644 --- a/external-deps/python-lsp-server/pylsp/plugins/signature.py +++ b/external-deps/python-lsp-server/pylsp/plugins/signature.py @@ -17,6 +17,7 @@ @hookimpl def pylsp_signature_help(config, document, position): + signature_config = config.settings().get("signature", {}) code_position = _utils.position_to_jedi_linecolumn(document, position) signatures = document.jedi_script().get_signatures(**code_position) @@ -41,10 +42,15 @@ def pylsp_signature_help(config, document, position): # Docstring contains one or more lines of signature, followed by empty line, followed by docstring function_sig_lines = (docstring.split("\n\n") or [""])[0].splitlines() function_sig = " ".join([line.strip() for line in function_sig_lines]) + + signature_docstring = s.docstring(raw=True) + if not signature_config.get("include_docstring", True): + signature_docstring = "" + sig = { "label": function_sig, "documentation": _utils.format_docstring( - s.docstring(raw=True), markup_kind=preferred_markup_kind + signature_docstring, markup_kind=preferred_markup_kind ), } diff --git a/external-deps/python-lsp-server/pylsp/python_lsp.py b/external-deps/python-lsp-server/pylsp/python_lsp.py index a26406668fb..bdc072d4af5 100644 --- a/external-deps/python-lsp-server/pylsp/python_lsp.py +++ b/external-deps/python-lsp-server/pylsp/python_lsp.py @@ -4,6 +4,7 @@ import logging import os import socketserver +import sys import threading import uuid from functools import partial @@ -71,9 +72,13 @@ def shutdown_server(check_parent_process, *args): handler_class.__name__ + "Handler", (_StreamHandlerWrapper,), { - "DELEGATE_CLASS": partial( - handler_class, check_parent_process=check_parent_process - ), + # We need to wrap this in staticmethod due to the changes to + # functools.partial in Python 3.14+ + "DELEGATE_CLASS": staticmethod( + partial(handler_class, check_parent_process=check_parent_process) + ) + if sys.version_info >= (3, 14) + else partial(handler_class, check_parent_process=check_parent_process), "SHUTDOWN_CALL": partial(shutdown_server, check_parent_process), }, ) diff --git a/external-deps/python-lsp-server/test/fixtures.py b/external-deps/python-lsp-server/test/fixtures.py index dd10140c0b6..258781f97c1 100644 --- a/external-deps/python-lsp-server/test/fixtures.py +++ b/external-deps/python-lsp-server/test/fixtures.py @@ -177,3 +177,17 @@ def client_server_pair() -> None: ).result(timeout=CALL_TIMEOUT_IN_SECONDS) assert shutdown_response is None client_server_pair_obj.client._endpoint.notify("exit") + + +@pytest.fixture +def workspace_with_signature_docstring_disabled(workspace) -> None: + workspace._config.update( + { + "signature": { + **workspace._config.settings().get("signature", {}), + "include_docstring": False, + }, + } + ) + + yield workspace diff --git a/external-deps/python-lsp-server/test/plugins/test_completion.py b/external-deps/python-lsp-server/test/plugins/test_completion.py index 015d0c434f3..ae5021f571b 100644 --- a/external-deps/python-lsp-server/test/plugins/test_completion.py +++ b/external-deps/python-lsp-server/test/plugins/test_completion.py @@ -181,7 +181,7 @@ def test_jedi_completion_with_fuzzy_enabled(config, workspace) -> None: assert items - expected = "isabs(s)" + expected = "commonprefix(m)" if JEDI_VERSION < "0.19.2" else "isabs(s)" assert items[0]["label"] == expected # Test we don't throw with big character diff --git a/external-deps/python-lsp-server/test/plugins/test_flake8_lint.py b/external-deps/python-lsp-server/test/plugins/test_flake8_lint.py index d8199d63481..ad1dc4ffe73 100644 --- a/external-deps/python-lsp-server/test/plugins/test_flake8_lint.py +++ b/external-deps/python-lsp-server/test/plugins/test_flake8_lint.py @@ -126,7 +126,7 @@ def test_flake8_config_param(workspace) -> None: with patch("pylsp.plugins.flake8_lint.Popen") as popen_mock: mock_instance = popen_mock.return_value mock_instance.communicate.return_value = [b"", b""] - flake8_conf = "/tmp/some.cfg" + flake8_conf = "C:\\some.cfg" if os.name == "nt" else "/tmp/some.cfg" workspace._config.update({"plugins": {"flake8": {"config": flake8_conf}}}) _name, doc = temp_document(DOC, workspace) flake8_lint.pylsp_lint(workspace, doc) diff --git a/external-deps/python-lsp-server/test/plugins/test_hover.py b/external-deps/python-lsp-server/test/plugins/test_hover.py index b507acd2c7e..4c0d75e8698 100644 --- a/external-deps/python-lsp-server/test/plugins/test_hover.py +++ b/external-deps/python-lsp-server/test/plugins/test_hover.py @@ -143,3 +143,17 @@ def foo(): contents = pylsp_hover(doc._config, doc, cursor_pos)["contents"] assert "A docstring for foo." in contents["value"] + + +def test_hover_without_docstring(workspace_with_signature_docstring_disabled) -> None: + # Over 'main' in def main(): + hov_position = {"line": 2, "character": 6} + + doc = Document(DOC_URI, workspace_with_signature_docstring_disabled, DOC) + + contents = { + "kind": "markdown", + "value": "```python\nmain(a: float, b: float)\n```\n", + } + + assert {"contents": contents} == pylsp_hover(doc._config, doc, hov_position) diff --git a/external-deps/python-lsp-server/test/plugins/test_signature.py b/external-deps/python-lsp-server/test/plugins/test_signature.py index 4a0a84ef226..82a90fc2b77 100644 --- a/external-deps/python-lsp-server/test/plugins/test_signature.py +++ b/external-deps/python-lsp-server/test/plugins/test_signature.py @@ -104,3 +104,17 @@ def test_docstring_params(regex, doc) -> None: m = regex.match(doc) assert m.group("param") == "test" assert m.group("doc") == "parameter docstring" + + +def test_signature_without_docstring( + workspace_with_signature_docstring_disabled, +) -> None: + # Over '( ' in main( + sig_position = {"line": 10, "character": 5} + doc = Document(DOC_URI, workspace_with_signature_docstring_disabled, DOC) + + sig_info = signature.pylsp_signature_help(doc._config, doc, sig_position) + + sigs = sig_info["signatures"] + assert len(sigs) == 1 + assert sigs[0]["documentation"] == {"kind": "markdown", "value": ""}