Skip to content

Commit 8509447

Browse files
committed
doc: comprehensive rename configuration guide with examples
- Add detailed JSON configuration example for enabling pylsp-rope rename - Clarify differences between rename plugins (pylsp_rope vs rope_rename vs jedi_rename) - Include verification steps and current limitations - Add comprehensive test suite demonstrating configuration patterns - Document future benefits of using pylsp-rope's rename functionality Fixes: #29 Signed-off-by: Matěj Cepl <mcepl@cepl.eu>
1 parent aa7f929 commit 8509447

2 files changed

Lines changed: 170 additions & 9 deletions

File tree

README.md

Lines changed: 58 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -135,15 +135,64 @@ name.
135135

136136
## Configuration
137137

138-
You can enable rename support using pylsp-rope with workspace config key
139-
`pylsp.plugins.pylsp_rope.rename`.
140-
141-
Note that this differs from the config key `pylsp.plugins.rope_rename.enabled`
142-
that is used for the rope rename implementation using the python-lsp-rope's
143-
builtin `rope_rename` plugin. To avoid confusion, avoid enabling more than one
144-
python-lsp-server rename plugin. In other words, you should set both
145-
`pylsp.plugins.rope_rename.enabled = false` and `pylsp.plugins.jedi_rename.enabled = false`
146-
when pylsp-rope rename is enabled.
138+
### Enabling Rename Support
139+
140+
To enable pylsp-rope's rename functionality, add the following to your LSP configuration:
141+
142+
```json
143+
{
144+
"pylsp": {
145+
"plugins": {
146+
"pylsp_rope": {
147+
"enabled": true,
148+
"rename": true
149+
},
150+
"rope_rename": {
151+
"enabled": false
152+
},
153+
"jedi_rename": {
154+
"enabled": false
155+
}
156+
}
157+
}
158+
}
159+
```
160+
161+
**Important:** Only enable one rename plugin at a time to avoid conflicts.
162+
163+
- `pylsp_rope` = this plugin (pylsp-rope)
164+
- `rope_rename` = built-in python-lsp-server plugin
165+
- `jedi_rename` = built-in Jedi-based plugin
166+
167+
This plugin uses `pylsp.plugins.pylsp_rope.rename` (boolean), while the built-in rope rename uses `pylsp.plugins.rope_rename.enabled`.
168+
169+
### Verifying pylsp-rope Rename is Active
170+
171+
To verify that pylsp-rope is handling rename requests:
172+
173+
1. Check your LSP logs - pylsp-rope logs `"textDocument/rename: ..."`
174+
when handling rename requests
175+
2. The rename behavior uses Rope's refactoring engine, which may handle
176+
complex scenarios differently than Jedi.
177+
3. Ensure other rename plugins are disabled as shown above
178+
179+
### Current Limitations and Future Benefits
180+
181+
Currently, pylsp-rope's rename supports the same elements as the
182+
built-in python-lsp-server rename:
183+
- ✅ Variables, classes, and functions
184+
- ❌ Modules and packages (planned for a future release)
185+
186+
The main benefits of using pylsp-rope's rename include:
187+
188+
- A more mature refactoring engine (Rope)
189+
- Improved handling of complex cross-file refactoring scenarios
190+
- A foundation for future module/package renaming capabilities
191+
192+
If you only need basic variable, class, or function renaming, the
193+
built-in rename plugin is sufficient. Use pylsp-rope if you require
194+
Rope's advanced refactoring capabilities or plan to use future
195+
module/package support.
147196

148197
## Caveat
149198

test/test_rename_configuration.py

Lines changed: 112 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,112 @@
1+
"""
2+
Integration test examples showing how to configure pylsp-rope rename functionality.
3+
4+
This file demonstrates the configuration patterns that users should follow
5+
to enable and verify pylsp-rope's rename feature.
6+
"""
7+
8+
import pytest
9+
from pylsp_rope import typing
10+
from pylsp_rope.plugin import pylsp_rename, pylsp_settings
11+
from pylsp_rope.text import Position
12+
from test.conftest import create_document
13+
from test.helpers import assert_text_edits
14+
15+
16+
class TestRenameConfigurationExamples:
17+
"""Examples showing proper configuration of pylsp-rope rename."""
18+
19+
def test_default_configuration_disables_rename(self, config, workspace):
20+
"""Test that rename is disabled by default."""
21+
# Get default settings
22+
settings = pylsp_settings()
23+
assert settings["plugins"]["pylsp_rope"]["rename"] is False
24+
25+
# Verify rename returns None when disabled
26+
document = create_document(workspace, "simple_rename.py")
27+
position = Position(0, 0) # Position on "Test1"
28+
29+
response = pylsp_rename(config, workspace, document, position, "NewName")
30+
assert response is None
31+
32+
def test_enabling_rename_via_configuration(self, config, workspace):
33+
"""Example of enabling rename through configuration."""
34+
# Simulate user configuration
35+
config._plugin_settings["plugins"]["pylsp_rope"] = {"rename": True}
36+
37+
document = create_document(workspace, "simple_rename.py")
38+
line = 0
39+
pos = document.lines[line].index("Test1")
40+
position = Position(line, pos)
41+
42+
response = pylsp_rename(
43+
config, workspace, document, position, "ShouldBeRenamed"
44+
)
45+
46+
# Rename should now work
47+
assert response is not None
48+
assert typing.is_workspace_edit_with_changes(response)
49+
50+
# Verify the rename happened
51+
changes = response["changes"]
52+
doc_uri = typing.DocumentUri(document.uri)
53+
assert doc_uri in changes
54+
new_text = assert_text_edits(changes[doc_uri], target="simple_rename_result.py")
55+
assert "class ShouldBeRenamed()" in new_text
56+
57+
def test_configuration_with_other_rename_plugins_disabled(self, config):
58+
"""Example showing complete rename configuration."""
59+
settings = pylsp_settings()
60+
61+
# This is the recommended configuration pattern:
62+
config_dict = {
63+
"pylsp": {
64+
"plugins": {
65+
"pylsp_rope": {"enabled": True, "rename": True},
66+
"rope_rename": {"enabled": False},
67+
"jedi_rename": {"enabled": False},
68+
}
69+
}
70+
}
71+
72+
# Verify pylsp-rope settings match recommendation
73+
pylsp_rope_settings = settings["plugins"]["pylsp_rope"]
74+
assert pylsp_rope_settings["enabled"] is True
75+
assert (
76+
pylsp_rope_settings["rename"] is False
77+
) # Default, user should set to True
78+
79+
def test_disabling_rename_after_enabling(self, config, workspace):
80+
"""Test that rename can be dynamically disabled."""
81+
# First enable rename
82+
config._plugin_settings["plugins"]["pylsp_rope"] = {"rename": True}
83+
84+
document = create_document(workspace, "simple_rename.py")
85+
line = 0
86+
pos = document.lines[line].index("Test1")
87+
position = Position(line, pos)
88+
89+
# Rename should work
90+
response = pylsp_rename(config, workspace, document, position, "NewName")
91+
assert response is not None
92+
93+
# Now disable rename
94+
config._plugin_settings["plugins"]["pylsp_rope"] = {"rename": False}
95+
96+
# Rename should not work
97+
response = pylsp_rename(config, workspace, document, position, "AnotherName")
98+
assert response is None
99+
100+
def test_missing_configuration_key_defaults_to_disabled(self, config, workspace):
101+
"""Test that missing configuration key defaults to disabled."""
102+
# Remove the rename key entirely
103+
plugin_settings = config.plugin_settings("pylsp_rope", "test://test.py")
104+
if "rename" in plugin_settings:
105+
del plugin_settings["rename"]
106+
107+
document = create_document(workspace, "simple_rename.py")
108+
position = Position(0, 5)
109+
110+
# Should return None when key is missing
111+
response = pylsp_rename(config, workspace, document, position, "NewName")
112+
assert response is None

0 commit comments

Comments
 (0)