2f0ff5f0f7
## Summary Fixes #1154 When creating a sandbox with an `mcp` config, the JSON-serialized config is interpolated directly into a shell command wrapped in single quotes. Since `json.dumps()` / `JSON.stringify()` do not escape single quotes, any MCP config value containing a single quote (e.g., API keys, tokens, URLs) breaks out of shell quoting and allows arbitrary command execution inside the sandbox. ## Changes ### Python SDK (`sandbox_async/main.py`, `sandbox_sync/main.py`) - Use `shlex.quote()` to properly escape the JSON config string (4 locations) - `shlex.quote()` is a stdlib function designed exactly for this purpose ### JS/TS SDK (`sandbox/index.ts`) - Add a `shellQuote()` helper that escapes single quotes using the standard `'\'''` pattern (equivalent to Python's `shlex.quote()`) - Apply it to both MCP config interpolation sites (2 locations) ## Before / After **Before** (vulnerable): ``` mcp-gateway --config '{"servers": {"test": {"envs": {"KEY": "it's a value"}}}}' # ^^ breaks out ``` **After** (safe): ``` mcp-gateway --config '{"servers": {"test": {"envs": {"KEY": "it'\''s a value"}}}}' # ^^^^ properly escaped ``` ## Testing Verified escaping behavior for both Python (`shlex.quote`) and JS (`shellQuote`) with the PoC from the issue — single quotes in config values are properly escaped and no longer allow shell breakout. --------- Co-authored-by: Mish Ushakov <10400064+mishushakov@users.noreply.github.com> Co-authored-by: Claude Opus 4.7 <noreply@anthropic.com>