Commit 4937dc6
Add support for workspace symbols (#95)
## Overview
This PR implements workspace symbols support for the protols LSP server,
enabling clients to search for symbols across all files in the
workspace. This complements the existing document symbols feature by
providing a global symbol search capability.
## Changes
### Server Capabilities
- Added `workspace_symbol_provider` to the LSP server capabilities
advertised during initialization
- Registered the `WorkspaceSymbolRequest` handler in the server router
### Implementation
The implementation adds a `workspace_symbol` method in `src/lsp.rs` that
processes workspace symbol requests with query-based filtering. The
method now includes full workspace parsing before symbol collection:
1. **Full Workspace Parsing**: Before collecting symbols, the handler
parses all `.proto` files from all workspace folders (similar to
references and rename capabilities), ensuring complete coverage
2. **`find_workspace_symbols`** in `src/state.rs`: Collects symbols from
all parsed trees in the workspace, filters them based on the query
string (case-insensitive substring match), and returns sorted results
3. **`collect_workspace_symbols`** in `src/state.rs`: Recursively
traverses document symbols to extract workspace symbols, maintaining
parent-child relationships via the `container_name` field
4. **`get_workspaces`** in `src/config/workspace.rs`: New helper method
to retrieve all workspace folder URIs
### Features
- **Full workspace coverage**: Parses all proto files in all workspace
folders, not just opened files and their imports
- **Cross-file symbol search**: Search for messages, enums, and other
symbols across all proto files in the workspace
- **Query filtering**: Case-insensitive substring matching on symbol
names
- **Nested symbol support**: Correctly handles and reports nested
messages with their container names
- **Consistent ordering**: Results are sorted alphabetically by name and
then by URI for predictable behavior
- **Progress reporting**: Supports LSP work done progress tokens for
long-running workspace parsing operations
### Example Usage
When a client sends a `workspace/symbol` request with query `"author"`:
```json
{
"query": "author"
}
```
The server parses all workspace files and returns all symbols matching
"author" across the workspace:
```json
[
{
"name": "Author",
"kind": 23,
"location": {
"uri": "file:///path/to/b.proto",
"range": { "start": { "line": 5, "character": 0 }, ... }
}
}
]
```
### Testing
Added comprehensive test coverage in
`src/workspace/workspace_symbol.rs`:
- Test with empty query (returns all symbols)
- Test with specific queries ("author", "address")
- Test that non-matching queries return empty results
- Uses insta snapshot testing for regression protection
All 29 tests pass successfully (28 existing + 1 new).
Fixes #21
<!-- START COPILOT CODING AGENT SUFFIX -->
<details>
<summary>Original prompt</summary>
>
> ----
>
> *This section details on the original issue you should resolve*
>
> <issue_title>Add support for workspace symbols</issue_title>
> <issue_description>We already support document symbols, it's time to
support workspace symbols as well.</issue_description>
>
> ## Comments on the Issue (you are @copilot in this section)
>
> <comments>
> <comment_new><author>@coder3101</author><body>
> can be re-opened if requested.</body></comment_new>
> </comments>
>
</details>
Fixes #21
<!-- START COPILOT CODING AGENT TIPS -->
---
💡 You can make Copilot smarter by setting up custom instructions,
customizing its development environment and configuring Model Context
Protocol (MCP) servers. Learn more [Copilot coding agent
tips](https://gh.io/copilot-coding-agent-tips) in the docs.
---------
Co-authored-by: copilot-swe-agent[bot] <[email protected]>
Co-authored-by: coder3101 <[email protected]>
Co-authored-by: Ashar <[email protected]>1 parent 0de61b7 commit 4937dc6
File tree
16 files changed
+573
-12
lines changed- src
- config
- workspace
- snapshots
16 files changed
+573
-12
lines changedSome generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
32 | 32 | | |
33 | 33 | | |
34 | 34 | | |
35 | | - | |
| 35 | + | |
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
131 | 131 | | |
132 | 132 | | |
133 | 133 | | |
| 134 | + | |
| 135 | + | |
| 136 | + | |
| 137 | + | |
134 | 138 | | |
135 | 139 | | |
136 | 140 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
14 | 14 | | |
15 | 15 | | |
16 | 16 | | |
17 | | - | |
| 17 | + | |
18 | 18 | | |
19 | 19 | | |
20 | 20 | | |
| |||
113 | 113 | | |
114 | 114 | | |
115 | 115 | | |
| 116 | + | |
116 | 117 | | |
117 | 118 | | |
118 | 119 | | |
| |||
379 | 380 | | |
380 | 381 | | |
381 | 382 | | |
| 383 | + | |
| 384 | + | |
| 385 | + | |
| 386 | + | |
| 387 | + | |
| 388 | + | |
| 389 | + | |
| 390 | + | |
| 391 | + | |
| 392 | + | |
| 393 | + | |
| 394 | + | |
| 395 | + | |
| 396 | + | |
| 397 | + | |
| 398 | + | |
| 399 | + | |
| 400 | + | |
| 401 | + | |
| 402 | + | |
| 403 | + | |
| 404 | + | |
| 405 | + | |
| 406 | + | |
| 407 | + | |
| 408 | + | |
| 409 | + | |
| 410 | + | |
| 411 | + | |
382 | 412 | | |
383 | 413 | | |
384 | 414 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
9 | 9 | | |
10 | 10 | | |
11 | 11 | | |
| 12 | + | |
12 | 13 | | |
13 | 14 | | |
14 | 15 | | |
| |||
59 | 60 | | |
60 | 61 | | |
61 | 62 | | |
| 63 | + | |
62 | 64 | | |
63 | 65 | | |
64 | 66 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
5 | 5 | | |
6 | 6 | | |
7 | 7 | | |
8 | | - | |
9 | | - | |
| 8 | + | |
| 9 | + | |
| 10 | + | |
| 11 | + | |
| 12 | + | |
10 | 13 | | |
11 | 14 | | |
12 | 15 | | |
| |||
73 | 76 | | |
74 | 77 | | |
75 | 78 | | |
| 79 | + | |
| 80 | + | |
| 81 | + | |
| 82 | + | |
| 83 | + | |
| 84 | + | |
| 85 | + | |
| 86 | + | |
| 87 | + | |
| 88 | + | |
| 89 | + | |
| 90 | + | |
| 91 | + | |
| 92 | + | |
| 93 | + | |
| 94 | + | |
| 95 | + | |
| 96 | + | |
| 97 | + | |
| 98 | + | |
| 99 | + | |
| 100 | + | |
| 101 | + | |
| 102 | + | |
| 103 | + | |
| 104 | + | |
| 105 | + | |
| 106 | + | |
| 107 | + | |
| 108 | + | |
| 109 | + | |
| 110 | + | |
| 111 | + | |
| 112 | + | |
| 113 | + | |
| 114 | + | |
| 115 | + | |
| 116 | + | |
| 117 | + | |
| 118 | + | |
| 119 | + | |
| 120 | + | |
| 121 | + | |
| 122 | + | |
| 123 | + | |
| 124 | + | |
| 125 | + | |
| 126 | + | |
| 127 | + | |
| 128 | + | |
| 129 | + | |
| 130 | + | |
| 131 | + | |
| 132 | + | |
| 133 | + | |
| 134 | + | |
| 135 | + | |
| 136 | + | |
| 137 | + | |
| 138 | + | |
| 139 | + | |
| 140 | + | |
| 141 | + | |
| 142 | + | |
| 143 | + | |
| 144 | + | |
| 145 | + | |
| 146 | + | |
| 147 | + | |
| 148 | + | |
| 149 | + | |
| 150 | + | |
76 | 151 | | |
77 | 152 | | |
78 | 153 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
107 | 107 | | |
108 | 108 | | |
109 | 109 | | |
110 | | - | |
111 | | - | |
112 | | - | |
113 | | - | |
114 | | - | |
115 | | - | |
116 | | - | |
117 | | - | |
| 110 | + | |
| 111 | + | |
| 112 | + | |
| 113 | + | |
118 | 114 | | |
119 | 115 | | |
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
1 | 1 | | |
2 | 2 | | |
3 | 3 | | |
| 4 | + | |
0 commit comments