Skip to content

Commit e464266

Browse files
committed
docs(mcp): add Windows STDIO configuration guidance
Document how to configure MCP STDIO clients on Windows where npx and other batch files require cmd.exe wrapper. Include cross-platform programmatic configuration examples and reference implementation.
1 parent 4532f64 commit e464266

File tree

1 file changed

+126
-0
lines changed

1 file changed

+126
-0
lines changed

spring-ai-docs/src/main/antora/modules/ROOT/pages/api/mcp/mcp-client-boot-starter-docs.adoc

Lines changed: 126 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -181,6 +181,132 @@ The Claude Desktop format looks like this:
181181
}
182182
----
183183

184+
=== Windows STDIO Configuration
185+
186+
IMPORTANT: On Windows, commands like `npx`, `npm`, and `node` are implemented as **batch files** (`.cmd`), not native executables. Java's `ProcessBuilder` cannot execute batch files directly and requires the `cmd.exe /c` wrapper.
187+
188+
==== Why Windows Needs Special Handling
189+
190+
When Java's `ProcessBuilder` (used internally by `StdioClientTransport`) attempts to spawn a process on Windows, it can only execute:
191+
192+
* Native executables (`.exe` files)
193+
* System commands available to `cmd.exe`
194+
195+
Windows batch files like `npx.cmd`, `npm.cmd`, and even `python.cmd` (from the Microsoft Store) require the `cmd.exe` shell to execute them.
196+
197+
==== Solution: cmd.exe Wrapper
198+
199+
Wrap batch file commands with `cmd.exe /c`:
200+
201+
**Windows Configuration:**
202+
[source,json]
203+
----
204+
{
205+
"mcpServers": {
206+
"filesystem": {
207+
"command": "cmd.exe",
208+
"args": [
209+
"/c",
210+
"npx",
211+
"-y",
212+
"@modelcontextprotocol/server-filesystem",
213+
"C:\\Users\\username\\Desktop"
214+
]
215+
}
216+
}
217+
}
218+
----
219+
220+
**Linux/macOS Configuration:**
221+
[source,json]
222+
----
223+
{
224+
"mcpServers": {
225+
"filesystem": {
226+
"command": "npx",
227+
"args": [
228+
"-y",
229+
"@modelcontextprotocol/server-filesystem",
230+
"/Users/username/Desktop"
231+
]
232+
}
233+
}
234+
}
235+
----
236+
237+
==== Cross-Platform Programmatic Configuration
238+
239+
For applications that need to work across platforms without separate configuration files, use OS detection in your Spring Boot application:
240+
241+
[source,java]
242+
----
243+
@Bean(destroyMethod = "close")
244+
@ConditionalOnMissingBean(McpSyncClient.class)
245+
public McpSyncClient mcpClient() {
246+
ServerParameters stdioParams;
247+
248+
if (isWindows()) {
249+
// Windows: cmd.exe /c npx approach
250+
var winArgs = new ArrayList<>(Arrays.asList(
251+
"/c", "npx", "-y", "@modelcontextprotocol/server-filesystem", "target"));
252+
stdioParams = ServerParameters.builder("cmd.exe")
253+
.args(winArgs)
254+
.build();
255+
} else {
256+
// Linux/Mac: direct npx approach
257+
stdioParams = ServerParameters.builder("npx")
258+
.args("-y", "@modelcontextprotocol/server-filesystem", "target")
259+
.build();
260+
}
261+
262+
return McpClient.sync(new StdioClientTransport(stdioParams, McpJsonMapper.createDefault()))
263+
.requestTimeout(Duration.ofSeconds(10))
264+
.build()
265+
.initialize();
266+
}
267+
268+
private static boolean isWindows() {
269+
return System.getProperty("os.name").toLowerCase().contains("win");
270+
}
271+
----
272+
273+
NOTE: When using programmatic configuration with `@Bean`, add `@ConditionalOnMissingBean(McpSyncClient.class)` to avoid conflicts with auto-configuration from JSON files.
274+
275+
==== Path Considerations
276+
277+
**Relative paths** (recommended for portability):
278+
[source,json]
279+
----
280+
{
281+
"command": "cmd.exe",
282+
"args": ["/c", "npx", "-y", "@modelcontextprotocol/server-filesystem", "target"]
283+
}
284+
----
285+
286+
The MCP server resolves relative paths based on the application's working directory.
287+
288+
**Absolute paths** (Windows requires backslashes or escaped forward slashes):
289+
[source,json]
290+
----
291+
{
292+
"command": "cmd.exe",
293+
"args": ["/c", "npx", "-y", "@modelcontextprotocol/server-filesystem", "C:\\Users\\username\\project\\target"]
294+
}
295+
----
296+
297+
==== Common Windows Batch Files Requiring cmd.exe
298+
299+
* `npx.cmd`, `npm.cmd` - Node package managers
300+
* `python.cmd` - Python (Microsoft Store installation)
301+
* `pip.cmd` - Python package manager
302+
* `mvn.cmd` - Maven wrapper
303+
* `gradle.cmd` - Gradle wrapper
304+
* Custom `.cmd` or `.bat` scripts
305+
306+
==== Reference Implementation
307+
308+
See link:https://github.com/spring-projects/spring-ai-examples/tree/main/model-context-protocol/filesystem[Spring AI Examples - Filesystem] for a complete cross-platform MCP client implementation that automatically detects the OS and configures the client appropriately.
309+
184310
=== Streamable-HTTP Transport Properties
185311

186312
Used for connecting to Streamable-HTTP and Stateless Streamable-HTTP MCP servers.

0 commit comments

Comments
 (0)