@wonderwhy-er/desktop-commander 0.1.34 → 0.1.36
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +2 -2
- package/README.md +186 -56
- package/dist/command-manager.d.ts +1 -7
- package/dist/command-manager.js +31 -50
- package/dist/config-manager.d.ts +28 -16
- package/dist/config-manager.js +124 -189
- package/dist/config.d.ts +2 -2
- package/dist/config.js +7 -4
- package/dist/error-handlers.js +4 -0
- package/dist/handlers/edit-search-handlers.d.ts +3 -1
- package/dist/handlers/edit-search-handlers.js +9 -19
- package/dist/handlers/filesystem-handlers.d.ts +0 -4
- package/dist/handlers/filesystem-handlers.js +11 -19
- package/dist/handlers/index.d.ts +0 -1
- package/dist/handlers/index.js +0 -1
- package/dist/index.js +19 -4
- package/dist/polyform-license-src/edit/edit.d.ts +15 -0
- package/dist/polyform-license-src/edit/edit.js +163 -0
- package/dist/polyform-license-src/edit/fuzzySearch.d.ts +30 -0
- package/dist/polyform-license-src/edit/fuzzySearch.js +121 -0
- package/dist/polyform-license-src/edit/handlers.d.ts +16 -0
- package/dist/polyform-license-src/edit/handlers.js +24 -0
- package/dist/polyform-license-src/edit/index.d.ts +12 -0
- package/dist/polyform-license-src/edit/index.js +13 -0
- package/dist/polyform-license-src/edit/schemas.d.ts +25 -0
- package/dist/polyform-license-src/edit/schemas.js +16 -0
- package/dist/polyform-license-src/index.d.ts +9 -0
- package/dist/polyform-license-src/index.js +10 -0
- package/dist/sandbox/index.d.ts +9 -0
- package/dist/sandbox/index.js +50 -0
- package/dist/sandbox/mac-sandbox.d.ts +19 -0
- package/dist/sandbox/mac-sandbox.js +174 -0
- package/dist/server.js +181 -176
- package/dist/setup-claude-server.js +554 -244
- package/dist/terminal-manager.d.ts +1 -1
- package/dist/terminal-manager.js +22 -3
- package/dist/tools/config.d.ts +0 -58
- package/dist/tools/config.js +44 -107
- package/dist/tools/debug-path.d.ts +1 -0
- package/dist/tools/debug-path.js +44 -0
- package/dist/tools/edit.d.ts +8 -6
- package/dist/tools/edit.js +165 -35
- package/dist/tools/execute.js +6 -6
- package/dist/tools/filesystem-fixed.d.ts +22 -0
- package/dist/tools/filesystem-fixed.js +176 -0
- package/dist/tools/filesystem.d.ts +4 -6
- package/dist/tools/filesystem.js +157 -87
- package/dist/tools/fuzzySearch.d.ts +22 -0
- package/dist/tools/fuzzySearch.js +113 -0
- package/dist/tools/pdf-reader.d.ts +13 -0
- package/dist/tools/pdf-reader.js +214 -0
- package/dist/tools/schemas.d.ts +29 -19
- package/dist/tools/schemas.js +15 -8
- package/dist/tools/search.js +5 -4
- package/dist/utils/capture.d.ts +15 -0
- package/dist/utils/capture.js +175 -0
- package/dist/utils/withTimeout.d.ts +11 -0
- package/dist/utils/withTimeout.js +52 -0
- package/dist/utils.d.ts +15 -1
- package/dist/utils.js +174 -41
- package/dist/version.d.ts +1 -1
- package/dist/version.js +1 -1
- package/package.json +2 -3
package/LICENSE
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
MIT License
|
|
2
2
|
|
|
3
|
-
Copyright (c) 2024 Eduard Ruzga
|
|
3
|
+
Copyright (c) 2024-2025 Eduard Ruzga and Desktop Commander Contributors
|
|
4
4
|
|
|
5
5
|
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
6
|
of this software and associated documentation files (the "Software"), to deal
|
|
@@ -18,4 +18,4 @@ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
|
18
18
|
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
19
|
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
20
|
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
-
SOFTWARE.
|
|
21
|
+
SOFTWARE.
|
package/README.md
CHANGED
|
@@ -5,14 +5,17 @@
|
|
|
5
5
|
[](https://smithery.ai/server/@wonderwhy-er/desktop-commander)
|
|
6
6
|
[](https://www.buymeacoffee.com/wonderwhyer)
|
|
7
7
|
|
|
8
|
+
|
|
8
9
|
[](https://discord.gg/kQ27sNnZr7)
|
|
9
10
|
|
|
10
|
-
|
|
11
|
+
|
|
12
|
+
Work with code and text, run processes, and automate tasks, going far beyond other AI editors - without API token costs.
|
|
11
13
|
|
|
12
14
|
|
|
13
|
-

|
|
16
|
+
|
|
14
17
|
<a href="https://glama.ai/mcp/servers/zempur9oh4">
|
|
15
|
-
<img width="380" height="200" src="https://glama.ai/mcp/servers/zempur9oh4/badge" alt="
|
|
18
|
+
<img width="380" height="200" src="https://glama.ai/mcp/servers/zempur9oh4/badge" alt="Desktop Commander MCP" />
|
|
16
19
|
</a>
|
|
17
20
|
|
|
18
21
|
## Table of Contents
|
|
@@ -21,13 +24,17 @@ Short version. Four key things. Terminal commands, diff based file editing, ripg
|
|
|
21
24
|
- [Usage](#usage)
|
|
22
25
|
- [Handling Long-Running Commands](#handling-long-running-commands)
|
|
23
26
|
- [Work in Progress and TODOs](#work-in-progress-and-todos)
|
|
24
|
-
- [
|
|
27
|
+
- [Sponsors and Supporters](#sponsors-and-supporters)
|
|
28
|
+
- [Website](#website)
|
|
29
|
+
- [Media](#media)
|
|
25
30
|
- [Testimonials](#testimonials)
|
|
26
31
|
- [Frequently Asked Questions](#frequently-asked-questions)
|
|
27
32
|
- [Contributing](#contributing)
|
|
28
33
|
- [License](#license)
|
|
29
34
|
|
|
30
|
-
|
|
35
|
+
All of your AI development tools in one place.
|
|
36
|
+
Desktop Commander puts all dev tools in one chat.
|
|
37
|
+
Execute long-running terminal commands on your computer and manage processes through Model Context Protocol (MCP). Built on top of [MCP Filesystem Server](https://github.com/modelcontextprotocol/servers/tree/main/src/filesystem) to provide additional search and replace file editing capabilities.
|
|
31
38
|
|
|
32
39
|
## Features
|
|
33
40
|
|
|
@@ -35,13 +42,17 @@ This is server that allows Claude desktop app to execute long-running terminal c
|
|
|
35
42
|
- Command timeout and background execution support
|
|
36
43
|
- Process management (list and kill processes)
|
|
37
44
|
- Session management for long-running commands
|
|
45
|
+
- Server configuration management:
|
|
46
|
+
- Get/set configuration values
|
|
47
|
+
- Update multiple settings at once
|
|
48
|
+
- Dynamic configuration changes without server restart
|
|
38
49
|
- Full filesystem operations:
|
|
39
50
|
- Read/write files
|
|
40
51
|
- Create/list directories
|
|
41
52
|
- Move files/directories
|
|
42
53
|
- Search files
|
|
43
54
|
- Get file metadata
|
|
44
|
-
|
|
55
|
+
- Code editing capabilities:
|
|
45
56
|
- Surgical text replacements for small changes
|
|
46
57
|
- Full file rewrites for major changes
|
|
47
58
|
- Multiple file support
|
|
@@ -52,7 +63,7 @@ This is server that allows Claude desktop app to execute long-running terminal c
|
|
|
52
63
|
First, ensure you've downloaded and installed the [Claude Desktop app](https://claude.ai/download) and you have [npm installed](https://docs.npmjs.com/downloading-and-installing-node-js-and-npm).
|
|
53
64
|
|
|
54
65
|
### Option 1: Install through npx
|
|
55
|
-
Just run this in terminal
|
|
66
|
+
Just run this in terminal:
|
|
56
67
|
```
|
|
57
68
|
npx @wonderwhy-er/desktop-commander@latest setup
|
|
58
69
|
```
|
|
@@ -61,7 +72,7 @@ For debugging mode (allows Node.js inspector connection):
|
|
|
61
72
|
```
|
|
62
73
|
npx @wonderwhy-er/desktop-commander@latest setup --debug
|
|
63
74
|
```
|
|
64
|
-
Restart Claude if running
|
|
75
|
+
Restart Claude if running.
|
|
65
76
|
|
|
66
77
|
### Option 2: Using bash script installer (macOS)
|
|
67
78
|
For macOS users, you can use our automated bash installer which will check your Node.js version, install it if needed, and automatically configure Desktop Commander:
|
|
@@ -78,7 +89,7 @@ To install Desktop Commander for Claude Desktop automatically via [Smithery](htt
|
|
|
78
89
|
npx -y @smithery/cli install @wonderwhy-er/desktop-commander --client claude
|
|
79
90
|
```
|
|
80
91
|
|
|
81
|
-
### Option 4: Add to claude_desktop_config
|
|
92
|
+
### Option 4: Add to claude_desktop_config manually
|
|
82
93
|
Add this entry to your claude_desktop_config.json:
|
|
83
94
|
|
|
84
95
|
- On Mac: `~/Library/Application\ Support/Claude/claude_desktop_config.json`
|
|
@@ -98,16 +109,16 @@ Add this entry to your claude_desktop_config.json:
|
|
|
98
109
|
}
|
|
99
110
|
}
|
|
100
111
|
```
|
|
101
|
-
Restart Claude if running
|
|
112
|
+
Restart Claude if running.
|
|
102
113
|
|
|
103
114
|
### Option 5: Checkout locally
|
|
104
115
|
1. Clone and build:
|
|
105
116
|
```bash
|
|
106
|
-
git clone https://github.com/wonderwhy-er/
|
|
107
|
-
cd
|
|
117
|
+
git clone https://github.com/wonderwhy-er/DesktopCommanderMCP.git
|
|
118
|
+
cd DesktopCommanderMCP
|
|
108
119
|
npm run setup
|
|
109
120
|
```
|
|
110
|
-
Restart Claude if running
|
|
121
|
+
Restart Claude if running.
|
|
111
122
|
|
|
112
123
|
The setup command will:
|
|
113
124
|
- Install dependencies
|
|
@@ -117,34 +128,38 @@ The setup command will:
|
|
|
117
128
|
|
|
118
129
|
### Updating Desktop Commander
|
|
119
130
|
|
|
120
|
-
When installed through npx (Option 1) or Smithery (Option
|
|
131
|
+
When installed through npx (Option 1) or Smithery (Option 3), Desktop Commander will automatically update to the latest version whenever you restart Claude. No manual update process is needed.
|
|
121
132
|
|
|
122
133
|
For manual installations, you can update by running the setup command again.
|
|
123
134
|
|
|
124
135
|
## Usage
|
|
125
136
|
|
|
126
|
-
The server provides
|
|
127
|
-
|
|
128
|
-
###
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
137
|
+
The server provides a comprehensive set of tools organized into several categories:
|
|
138
|
+
|
|
139
|
+
### Available Tools
|
|
140
|
+
|
|
141
|
+
| Category | Tool | Description |
|
|
142
|
+
|----------|------|-------------|
|
|
143
|
+
| **Configuration** | `get_config` | Get the complete server configuration as JSON (includes blockedCommands, defaultShell, allowedDirectories) |
|
|
144
|
+
| | `set_config_value` | Set a specific configuration value by key. Available settings: <br>• `blockedCommands`: Array of shell commands that cannot be executed<br>• `defaultShell`: Shell to use for commands (e.g., bash, zsh, powershell)<br>• `allowedDirectories`: Array of filesystem paths the server can access for file operations (⚠️ terminal commands can still access files outside these directories) |
|
|
145
|
+
| **Terminal** | `execute_command` | Execute a terminal command with configurable timeout and shell selection |
|
|
146
|
+
| | `read_output` | Read new output from a running terminal session |
|
|
147
|
+
| | `force_terminate` | Force terminate a running terminal session |
|
|
148
|
+
| | `list_sessions` | List all active terminal sessions |
|
|
149
|
+
| | `list_processes` | List all running processes with detailed information |
|
|
150
|
+
| | `kill_process` | Terminate a running process by PID |
|
|
151
|
+
| **Filesystem** | `read_file` | Read contents from local filesystem or URLs (supports text and images) |
|
|
152
|
+
| | `read_multiple_files` | Read multiple files simultaneously |
|
|
153
|
+
| | `write_file` | Completely replace file contents (best for large changes) |
|
|
154
|
+
| | `create_directory` | Create a new directory or ensure it exists |
|
|
155
|
+
| | `list_directory` | Get detailed listing of files and directories |
|
|
156
|
+
| | `move_file` | Move or rename files and directories |
|
|
157
|
+
| | `search_files` | Find files by name using case-insensitive substring matching |
|
|
158
|
+
| | `search_code` | Search for text/code patterns within file contents using ripgrep |
|
|
159
|
+
| | `get_file_info` | Retrieve detailed metadata about a file or directory |
|
|
160
|
+
| **Text Editing** | `edit_block` | Apply surgical text replacements (best for changes <20% of file size) |
|
|
161
|
+
|
|
162
|
+
### Tool Usage Examples
|
|
148
163
|
|
|
149
164
|
Search/Replace Block Format:
|
|
150
165
|
```
|
|
@@ -178,6 +193,59 @@ console.log("new message");
|
|
|
178
193
|
|
|
179
194
|
For commands that may take a while:
|
|
180
195
|
|
|
196
|
+
## Configuration Management
|
|
197
|
+
|
|
198
|
+
### ⚠️ Important Security Warnings
|
|
199
|
+
|
|
200
|
+
1. **Always change configuration in a separate chat window** from where you're doing your actual work. Claude may sometimes attempt to modify configuration settings (like `allowedDirectories`) if it encounters filesystem access restrictions.
|
|
201
|
+
|
|
202
|
+
2. **The `allowedDirectories` setting currently only restricts filesystem operations**, not terminal commands. Terminal commands can still access files outside allowed directories. Full terminal sandboxing is on the roadmap.
|
|
203
|
+
|
|
204
|
+
### Configuration Tools
|
|
205
|
+
|
|
206
|
+
You can manage server configuration using the provided tools:
|
|
207
|
+
|
|
208
|
+
```javascript
|
|
209
|
+
// Get the entire config
|
|
210
|
+
get_config({})
|
|
211
|
+
|
|
212
|
+
// Set a specific config value
|
|
213
|
+
set_config_value({ "key": "defaultShell", "value": "/bin/zsh" })
|
|
214
|
+
|
|
215
|
+
// Set multiple config values using separate calls
|
|
216
|
+
set_config_value({ "key": "defaultShell", "value": "/bin/bash" })
|
|
217
|
+
set_config_value({ "key": "allowedDirectories", "value": ["/Users/username/projects"] })
|
|
218
|
+
```
|
|
219
|
+
|
|
220
|
+
The configuration is saved to `config.json` in the server's working directory and persists between server restarts.
|
|
221
|
+
|
|
222
|
+
### Best Practices
|
|
223
|
+
|
|
224
|
+
1. **Create a dedicated chat for configuration changes**: Make all your config changes in one chat, then start a new chat for your actual work.
|
|
225
|
+
|
|
226
|
+
2. **Be careful with empty `allowedDirectories`**: Setting this to an empty array (`[]`) grants access to your entire filesystem for file operations.
|
|
227
|
+
|
|
228
|
+
3. **Use specific paths**: Instead of using broad paths like `/`, specify exact directories you want to access.
|
|
229
|
+
|
|
230
|
+
4. **Always verify configuration after changes**: Use `get_config({})` to confirm your changes were applied correctly.
|
|
231
|
+
|
|
232
|
+
## Using Different Shells
|
|
233
|
+
|
|
234
|
+
You can specify which shell to use for command execution:
|
|
235
|
+
|
|
236
|
+
```javascript
|
|
237
|
+
// Using default shell (bash or system default)
|
|
238
|
+
execute_command({ "command": "echo $SHELL" })
|
|
239
|
+
|
|
240
|
+
// Using zsh specifically
|
|
241
|
+
execute_command({ "command": "echo $SHELL", "shell": "/bin/zsh" })
|
|
242
|
+
|
|
243
|
+
// Using bash specifically
|
|
244
|
+
execute_command({ "command": "echo $SHELL", "shell": "/bin/bash" })
|
|
245
|
+
```
|
|
246
|
+
|
|
247
|
+
This allows you to use shell-specific features or maintain consistent environments across commands.
|
|
248
|
+
|
|
181
249
|
1. `execute_command` returns after timeout with initial output
|
|
182
250
|
2. Command continues in background
|
|
183
251
|
3. Use `read_output` with PID to get new output
|
|
@@ -229,26 +297,90 @@ This project extends the MCP Filesystem Server to enable:
|
|
|
229
297
|
Created as part of exploring Claude MCPs: https://youtube.com/live/TlbjFDbl5Us
|
|
230
298
|
|
|
231
299
|
## DONE
|
|
300
|
+
- **29-04-2025 Telemetry Opt Out trough configuraton** - There is now setting to disable telemetry in config, ask in chat
|
|
301
|
+
- **23-04-2025 Enhanced edit functionality** - Improved format, added fuzzy search and multi-occurrence replacements, should fail less and use edit block more often
|
|
302
|
+
- **16-04-2025 Better configurations** - Improved settings for allowed paths, commands and shell environments
|
|
303
|
+
- **14-04-2025 Windows environment fixes** - Resolved issues specific to Windows platforms
|
|
304
|
+
- **14-04-2025 Linux improvements** - Enhanced compatibility with various Linux distributions
|
|
305
|
+
- **12-04-2025 Better allowed directories and blocked commands** - Improved security and path validation for file read/write and terminal command restrictions.
|
|
306
|
+
Terminal still can access files ignoring allowed directories.
|
|
307
|
+
- **11-04-2025 Shell configuration** - Added ability to configure preferred shell for command execution
|
|
232
308
|
- **07-04-2025 Added URL support** - `read_file` command can now fetch content from URLs
|
|
233
309
|
- **28-03-2025 Fixed "Watching /" JSON error** - Implemented custom stdio transport to handle non-JSON messages and prevent server crashes
|
|
234
|
-
- **25-03-2025 Better code search** ([merged](https://github.com/wonderwhy-er/
|
|
310
|
+
- **25-03-2025 Better code search** ([merged](https://github.com/wonderwhy-er/ClaudeServerCommander/pull/17)) - Enhanced code exploration with context-aware results
|
|
235
311
|
|
|
236
|
-
## Work in Progress
|
|
312
|
+
## Work in Progress/TODOs/Roadmap
|
|
237
313
|
|
|
238
|
-
The following features are currently being
|
|
314
|
+
The following features are currently being explored:
|
|
239
315
|
|
|
240
|
-
- **Better configurations** ([in progress](https://github.com/wonderwhy-er/ClaudeDesktopCommander/pull/16)) - Improved settings for allowed paths, commands and shell environment
|
|
241
|
-
- **Windows environment fixes** ([in progress](https://github.com/wonderwhy-er/ClaudeDesktopCommander/pull/13)) - Resolving issues specific to Windows platforms
|
|
242
|
-
- **Linux improvements** ([in progress](https://github.com/wonderwhy-er/ClaudeDesktopCommander/pull/12)) - Enhancing compatibility with various Linux distributions
|
|
243
316
|
- **Support for WSL** - Windows Subsystem for Linux integration
|
|
244
317
|
- **Support for SSH** - Remote server command execution
|
|
245
|
-
- **
|
|
318
|
+
- **Better file support for formats like CSV/PDF**
|
|
319
|
+
- **Terminal sandboxing for Mac/Linux/Windows for better security**
|
|
320
|
+
- **File reading modes** - For example, allow reading HTML as plain text or markdown
|
|
321
|
+
- **Interactive shell support** - ssh, node/python repl
|
|
322
|
+
- **Improve large file reading and writing**
|
|
323
|
+
|
|
324
|
+
## ❤️ Support Desktop Commander
|
|
325
|
+
|
|
326
|
+
<div align="center">
|
|
327
|
+
<h3>📢 SUPPORT THIS PROJECT</h3>
|
|
328
|
+
<p><strong>Desktop Commander MCP is free and open source, but needs your support to thrive!</strong></p>
|
|
329
|
+
|
|
330
|
+
<div style="background-color: #f8f9fa; padding: 15px; border-radius: 10px; margin: 20px 0; border: 2px solid #007bff;">
|
|
331
|
+
<p>Our philosophy is simple: we don't want you to pay for it if you're not successful. But if Desktop Commander contributes to your success, please consider contributing to ours.</p>
|
|
332
|
+
<p><strong>Ways to support:</strong></p>
|
|
333
|
+
<ul style="list-style-type: none; padding: 0;">
|
|
334
|
+
<li>🌟 <a href="https://github.com/sponsors/wonderwhy-er"><strong>GitHub Sponsors</strong></a> - Recurring support</li>
|
|
335
|
+
<li>☕ <a href="https://www.buymeacoffee.com/wonderwhyer"><strong>Buy Me A Coffee</strong></a> - One-time contributions</li>
|
|
336
|
+
<li>⭐ <a href="https://github.com/wonderwhy-er/DesktopCommanderMCP"><strong>Star on GitHub</strong></a> - Help others discover the project</li>
|
|
337
|
+
</ul>
|
|
338
|
+
</div>
|
|
339
|
+
</div>
|
|
340
|
+
|
|
341
|
+
### Supporters Hall of Fame
|
|
342
|
+
|
|
343
|
+
Generous supporters are featured here. Thank you for helping make this project possible!
|
|
344
|
+
|
|
345
|
+
<div align="center">
|
|
346
|
+
<table>
|
|
347
|
+
<tr>
|
|
348
|
+
<td align="center">
|
|
349
|
+
<a href="https://github.com/jonrichards">
|
|
350
|
+
<img src="https://github.com/jonrichards.png" width="100px;" alt="Jon Richards"/>
|
|
351
|
+
<br />
|
|
352
|
+
<sub><b>Jon Richards</b></sub>
|
|
353
|
+
</a>
|
|
354
|
+
</td>
|
|
355
|
+
<td align="center">
|
|
356
|
+
<a href="https://github.com/stepanic">
|
|
357
|
+
<img src="https://github.com/stepanic.png" width="100px;" alt="Matija Stepanic"/>
|
|
358
|
+
<br />
|
|
359
|
+
<sub><b>Matija Stepanic</b></sub>
|
|
360
|
+
</a>
|
|
361
|
+
</td>
|
|
362
|
+
</tr>
|
|
363
|
+
</table>
|
|
364
|
+
</div>
|
|
365
|
+
|
|
366
|
+
<details>
|
|
367
|
+
<summary><strong>Why your support matters</strong></summary>
|
|
368
|
+
<p>Your support allows us to:</p>
|
|
369
|
+
<ul>
|
|
370
|
+
<li>Continue active development and maintenance</li>
|
|
371
|
+
<li>Add new features and integrations</li>
|
|
372
|
+
<li>Improve compatibility across platforms</li>
|
|
373
|
+
<li>Provide better documentation and examples</li>
|
|
374
|
+
<li>Build a stronger community around the project</li>
|
|
375
|
+
</ul>
|
|
376
|
+
</details>
|
|
246
377
|
|
|
247
378
|
## Website
|
|
248
379
|
|
|
249
380
|
Visit our official website at [https://desktopcommander.app/](https://desktopcommander.app/) for the latest information, documentation, and updates.
|
|
250
381
|
|
|
251
382
|
## Media
|
|
383
|
+
|
|
252
384
|
Learn more about this project through these resources:
|
|
253
385
|
|
|
254
386
|
### Article
|
|
@@ -287,13 +419,11 @@ Claude first to keep my sanity in check, then if necessary, engage with other ID
|
|
|
287
419
|
1](https://raw.githubusercontent.com/wonderwhy-er/ClaudeComputerCommander/main/testemonials/img_4.png)
|
|
288
420
|
https://medium.com/@pharmx/you-sir-are-my-hero-62cff5836a3e](https://medium.com/@pharmx/you-sir-are-my-hero-62cff5836a3e)
|
|
289
421
|
|
|
290
|
-
## Contributing
|
|
291
|
-
|
|
292
422
|
If you find this project useful, please consider giving it a ⭐ star on GitHub! This helps others discover the project and encourages further development.
|
|
293
423
|
|
|
294
424
|
We welcome contributions from the community! Whether you've found a bug, have a feature request, or want to contribute code, here's how you can help:
|
|
295
425
|
|
|
296
|
-
- **Found a bug?** Open an issue at [github.com/wonderwhy-er/
|
|
426
|
+
- **Found a bug?** Open an issue at [github.com/wonderwhy-er/DesktopCommanderMCP/issues](https://github.com/wonderwhy-er/DesktopCommanderMCP/issues)
|
|
297
427
|
- **Have a feature idea?** Submit a feature request in the issues section
|
|
298
428
|
- **Want to contribute code?** Fork the repository, create a branch, and submit a pull request
|
|
299
429
|
- **Questions or discussions?** Start a discussion in the GitHub Discussions tab
|
|
@@ -306,7 +436,7 @@ If you find this tool valuable for your workflow, please consider [supporting th
|
|
|
306
436
|
|
|
307
437
|
Here are answers to some common questions. For a more comprehensive FAQ, see our [detailed FAQ document](FAQ.md).
|
|
308
438
|
|
|
309
|
-
### What is
|
|
439
|
+
### What is Desktop Commander?
|
|
310
440
|
It's an MCP tool that enables Claude Desktop to access your file system and terminal, turning Claude into a versatile assistant for coding, automation, codebase exploration, and more.
|
|
311
441
|
|
|
312
442
|
### How is this different from Cursor/Windsurf?
|
|
@@ -326,19 +456,19 @@ Yes, when installed through npx or Smithery, Desktop Commander automatically upd
|
|
|
326
456
|
- Making surgical code changes with precise control
|
|
327
457
|
|
|
328
458
|
### I'm having trouble installing or using the tool. Where can I get help?
|
|
329
|
-
Join our [Discord server](https://discord.gg/kQ27sNnZr7) for community support, check the [GitHub issues](https://github.com/wonderwhy-er/
|
|
459
|
+
Join our [Discord server](https://discord.gg/kQ27sNnZr7) for community support, check the [GitHub issues](https://github.com/wonderwhy-er/DesktopCommanderMCP/issues) for known problems, or review the [full FAQ](FAQ.md) for troubleshooting tips. You can also visit our [website FAQ section](https://desktopcommander.app#faq) for a more user-friendly experience. If you encounter a new issue, please consider [opening a GitHub issue](https://github.com/wonderwhy-er/DesktopCommanderMCP/issues/new) with details about your problem.
|
|
460
|
+
|
|
461
|
+
## Data Collection & Privacy
|
|
330
462
|
|
|
331
|
-
|
|
463
|
+
Desktop Commander collects limited anonymous telemetry data to help improve the tool. No personal information, file contents, file paths, or command arguments are collected.
|
|
332
464
|
|
|
333
|
-
|
|
334
|
-
- Operating system information
|
|
335
|
-
- Node.js and NPM versions
|
|
336
|
-
- Installation method and shell environment
|
|
337
|
-
- Error messages (if any occur during setup)
|
|
465
|
+
Telemetry is enabled by default. To opt out:
|
|
338
466
|
|
|
339
|
-
|
|
467
|
+
1. Open the chat and simply ask:
|
|
468
|
+
**"Disable telemetry"**
|
|
469
|
+
2. The chatbot will update your settings automatically.
|
|
340
470
|
|
|
341
|
-
|
|
471
|
+
For complete details about data collection, please see our [Privacy Policy](PRIVACY.md).
|
|
342
472
|
|
|
343
473
|
## License
|
|
344
474
|
|
|
@@ -1,14 +1,8 @@
|
|
|
1
1
|
declare class CommandManager {
|
|
2
|
-
private blockedCommands;
|
|
3
|
-
loadBlockedCommands(): Promise<void>;
|
|
4
|
-
saveBlockedCommands(): Promise<void>;
|
|
5
2
|
getBaseCommand(command: string): string;
|
|
6
3
|
extractCommands(commandString: string): string[];
|
|
7
4
|
extractBaseCommand(commandStr: string): string | null;
|
|
8
|
-
validateCommand(command: string): boolean
|
|
9
|
-
blockCommand(command: string): Promise<boolean>;
|
|
10
|
-
unblockCommand(command: string): Promise<boolean>;
|
|
11
|
-
listBlockedCommands(): string[];
|
|
5
|
+
validateCommand(command: string): Promise<boolean>;
|
|
12
6
|
}
|
|
13
7
|
export declare const commandManager: CommandManager;
|
|
14
8
|
export {};
|
package/dist/command-manager.js
CHANGED
|
@@ -1,30 +1,6 @@
|
|
|
1
|
-
import
|
|
2
|
-
import {
|
|
1
|
+
import { configManager } from './config-manager.js';
|
|
2
|
+
import { capture } from "./utils/capture.js";
|
|
3
3
|
class CommandManager {
|
|
4
|
-
constructor() {
|
|
5
|
-
this.blockedCommands = new Set();
|
|
6
|
-
}
|
|
7
|
-
async loadBlockedCommands() {
|
|
8
|
-
try {
|
|
9
|
-
const configData = await fs.readFile(CONFIG_FILE, 'utf-8');
|
|
10
|
-
const config = JSON.parse(configData);
|
|
11
|
-
this.blockedCommands = new Set(config.blockedCommands);
|
|
12
|
-
}
|
|
13
|
-
catch (error) {
|
|
14
|
-
this.blockedCommands = new Set();
|
|
15
|
-
}
|
|
16
|
-
}
|
|
17
|
-
async saveBlockedCommands() {
|
|
18
|
-
try {
|
|
19
|
-
const config = {
|
|
20
|
-
blockedCommands: Array.from(this.blockedCommands)
|
|
21
|
-
};
|
|
22
|
-
await fs.writeFile(CONFIG_FILE, JSON.stringify(config, null, 2), 'utf-8');
|
|
23
|
-
}
|
|
24
|
-
catch (error) {
|
|
25
|
-
// Handle error if needed
|
|
26
|
-
}
|
|
27
|
-
}
|
|
28
4
|
getBaseCommand(command) {
|
|
29
5
|
return command.split(' ')[0].toLowerCase().trim();
|
|
30
6
|
}
|
|
@@ -128,7 +104,9 @@ class CommandManager {
|
|
|
128
104
|
}
|
|
129
105
|
catch (error) {
|
|
130
106
|
// If anything goes wrong, log the error but return the basic command to not break execution
|
|
131
|
-
|
|
107
|
+
capture('server_request_error', {
|
|
108
|
+
error: 'Error extracting commands'
|
|
109
|
+
});
|
|
132
110
|
return [this.getBaseCommand(commandString)];
|
|
133
111
|
}
|
|
134
112
|
}
|
|
@@ -150,34 +128,37 @@ class CommandManager {
|
|
|
150
128
|
return firstToken.toLowerCase();
|
|
151
129
|
}
|
|
152
130
|
catch (error) {
|
|
153
|
-
|
|
131
|
+
capture('Error extracting base command');
|
|
154
132
|
return null;
|
|
155
133
|
}
|
|
156
134
|
}
|
|
157
|
-
validateCommand(command) {
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
135
|
+
async validateCommand(command) {
|
|
136
|
+
try {
|
|
137
|
+
// Get blocked commands from config
|
|
138
|
+
const config = await configManager.getConfig();
|
|
139
|
+
const blockedCommands = config.blockedCommands || [];
|
|
140
|
+
// Extract all commands from the command string
|
|
141
|
+
const allCommands = this.extractCommands(command);
|
|
142
|
+
// If there are no commands extracted, fall back to base command
|
|
143
|
+
if (allCommands.length === 0) {
|
|
144
|
+
const baseCommand = this.getBaseCommand(command);
|
|
145
|
+
return !blockedCommands.includes(baseCommand);
|
|
146
|
+
}
|
|
147
|
+
// Check if any of the extracted commands are in the blocked list
|
|
148
|
+
for (const cmd of allCommands) {
|
|
149
|
+
if (blockedCommands.includes(cmd)) {
|
|
150
|
+
return false; // Command is blocked
|
|
151
|
+
}
|
|
152
|
+
}
|
|
153
|
+
// No commands were blocked
|
|
154
|
+
return true;
|
|
165
155
|
}
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
command = command.toLowerCase().trim();
|
|
172
|
-
if (!this.blockedCommands.has(command)) {
|
|
173
|
-
return false;
|
|
156
|
+
catch (error) {
|
|
157
|
+
console.error('Error validating command:', error);
|
|
158
|
+
// If there's an error, default to allowing the command
|
|
159
|
+
// This is less secure but prevents blocking all commands due to config issues
|
|
160
|
+
return true;
|
|
174
161
|
}
|
|
175
|
-
this.blockedCommands.delete(command);
|
|
176
|
-
await this.saveBlockedCommands();
|
|
177
|
-
return true;
|
|
178
|
-
}
|
|
179
|
-
listBlockedCommands() {
|
|
180
|
-
return Array.from(this.blockedCommands).sort();
|
|
181
162
|
}
|
|
182
163
|
}
|
|
183
164
|
export const commandManager = new CommandManager();
|
package/dist/config-manager.d.ts
CHANGED
|
@@ -1,42 +1,54 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Interface for the server configuration
|
|
3
|
-
*/
|
|
4
1
|
export interface ServerConfig {
|
|
5
2
|
blockedCommands?: string[];
|
|
6
3
|
defaultShell?: string;
|
|
7
|
-
logLevel?: 'error' | 'warn' | 'info' | 'debug';
|
|
8
4
|
allowedDirectories?: string[];
|
|
5
|
+
telemetryEnabled?: boolean;
|
|
9
6
|
[key: string]: any;
|
|
10
7
|
}
|
|
11
8
|
/**
|
|
12
|
-
*
|
|
9
|
+
* Singleton config manager for the server
|
|
13
10
|
*/
|
|
14
|
-
|
|
11
|
+
declare class ConfigManager {
|
|
12
|
+
private configPath;
|
|
15
13
|
private config;
|
|
16
14
|
private initialized;
|
|
15
|
+
constructor();
|
|
17
16
|
/**
|
|
18
|
-
*
|
|
17
|
+
* Initialize configuration - load from disk or create default
|
|
19
18
|
*/
|
|
20
|
-
|
|
19
|
+
init(): Promise<void>;
|
|
21
20
|
/**
|
|
22
|
-
*
|
|
21
|
+
* Alias for init() to maintain backward compatibility
|
|
23
22
|
*/
|
|
24
|
-
|
|
23
|
+
loadConfig(): Promise<void>;
|
|
25
24
|
/**
|
|
26
|
-
*
|
|
25
|
+
* Create default configuration
|
|
27
26
|
*/
|
|
28
|
-
|
|
27
|
+
private getDefaultConfig;
|
|
29
28
|
/**
|
|
30
|
-
*
|
|
29
|
+
* Save config to disk
|
|
31
30
|
*/
|
|
32
|
-
|
|
31
|
+
private saveConfig;
|
|
33
32
|
/**
|
|
34
|
-
* Get the entire
|
|
33
|
+
* Get the entire config
|
|
35
34
|
*/
|
|
36
35
|
getConfig(): Promise<ServerConfig>;
|
|
36
|
+
/**
|
|
37
|
+
* Get a specific configuration value
|
|
38
|
+
*/
|
|
39
|
+
getValue(key: string): Promise<any>;
|
|
40
|
+
/**
|
|
41
|
+
* Set a specific configuration value
|
|
42
|
+
*/
|
|
43
|
+
setValue(key: string, value: any): Promise<void>;
|
|
37
44
|
/**
|
|
38
45
|
* Update multiple configuration values at once
|
|
39
46
|
*/
|
|
40
|
-
updateConfig(
|
|
47
|
+
updateConfig(updates: Partial<ServerConfig>): Promise<ServerConfig>;
|
|
48
|
+
/**
|
|
49
|
+
* Reset configuration to defaults
|
|
50
|
+
*/
|
|
51
|
+
resetConfig(): Promise<ServerConfig>;
|
|
41
52
|
}
|
|
42
53
|
export declare const configManager: ConfigManager;
|
|
54
|
+
export {};
|