From 8b09f4278c08cbcae644965bf8a089a53bd3e32c Mon Sep 17 00:00:00 2001 From: Olivier Chafik Date: Sun, 11 Jan 2026 14:32:48 +0000 Subject: [PATCH] fix: proper CSP handling in basic-host sandboxing (HTTP headers, worker-src, document.write) (#234) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * fix: Move CSP to HTTP headers + add worker-src, frameDomains, baseUriDomains, permissions Security improvements: - CSP is now set via HTTP headers in serve.ts instead of meta tags (meta tag CSP can be tampered with by same-origin content) - CSP passed as query param to sandbox.html for header-based enforcement New CSP/permissions features (borrowed from PR #158): - frameDomains: control frame-src directive for nested iframes - baseUriDomains: control base-uri directive - permissions: camera, microphone, geolocation via iframe allow attribute WebGL fix: - Use document.write() instead of srcdoc for inner iframe content (srcdoc creates opaque origin that breaks WebGL canvas updates) - Add worker-src directive with blob: support (critical for WebGL apps like CesiumJS/Three.js that use workers for tile decoding, terrain processing, image processing) 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude Opus 4.5 * refactor: Remove permissions support (defer to PR #158) Keep this PR focused on CSP security fixes only. Permissions (camera, microphone, geolocation) will be handled in #158. 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude Opus 4.5 * cleanup McpUiResourceCsp type usage / duplicate defs * fix: guard against CSP injection in domain parameters Validate CSP domain entries to reject characters that could: - Break out of CSP directives (semicolons, newlines) - Inject CSP keywords like 'unsafe-eval' (quotes) - Inject multiple sources in one entry (spaces) This prevents injection attacks where malicious domains could override the security policy. --------- Co-authored-by: Claude Opus 4.5 --- examples/basic-host/sandbox.html | 4 +- examples/basic-host/serve.ts | 86 +++++- examples/basic-host/src/implementation.ts | 24 +- examples/basic-host/src/index.tsx | 25 +- examples/basic-host/src/sandbox.ts | 54 +--- examples/basic-host/src/tamper-detection.ts | 325 ++++++++++++++++++++ specification/draft/apps.mdx | 36 ++- src/generated/schema.json | 42 +++ src/generated/schema.test.ts | 28 +- src/generated/schema.ts | 92 +++--- src/spec.types.ts | 11 +- 11 files changed, 572 insertions(+), 155 deletions(-) create mode 100644 examples/basic-host/src/tamper-detection.ts diff --git a/examples/basic-host/sandbox.html b/examples/basic-host/sandbox.html index b868e58..e0790fb 100644 --- a/examples/basic-host/sandbox.html +++ b/examples/basic-host/sandbox.html @@ -3,8 +3,8 @@ - + MCP-UI Proxy