Improve documentation for CSP and permissions types
Add detailed JSDoc comments to `McpUiResourceCsp`, `McpUiResourcePermissions`, and `McpUiResourceMeta` interfaces: - Document CSP directive mappings for `connectDomains`, `resourceDomains`, `frameDomains`, and `baseUriDomains` - Add usage examples showing typical domain patterns - Clarify Permission Policy mappings for `camera`, `microphone`, `geolocation`, and `clipboardWrite` - Explain `domain` field's host-dependent behavior with concrete examples - Document `prefersBorder` semantics including true/false/omitted behavior Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
This commit is contained in:
parent
6905aa8edc
commit
c02eb4d006
3 changed files with 293 additions and 82 deletions
88
src/generated/schema.json
generated
88
src/generated/schema.json
generated
|
|
@ -134,25 +134,25 @@
|
|||
"type": "object",
|
||||
"properties": {
|
||||
"camera": {
|
||||
"description": "Request camera access (Permission Policy `camera` feature).",
|
||||
"description": "Request camera access.\n\nMaps to Permission Policy `camera` feature.",
|
||||
"type": "object",
|
||||
"properties": {},
|
||||
"additionalProperties": false
|
||||
},
|
||||
"microphone": {
|
||||
"description": "Request microphone access (Permission Policy `microphone` feature).",
|
||||
"description": "Request microphone access.\n\nMaps to Permission Policy `microphone` feature.",
|
||||
"type": "object",
|
||||
"properties": {},
|
||||
"additionalProperties": false
|
||||
},
|
||||
"geolocation": {
|
||||
"description": "Request geolocation access (Permission Policy `geolocation` feature).",
|
||||
"description": "Request geolocation access.\n\nMaps to Permission Policy `geolocation` feature.",
|
||||
"type": "object",
|
||||
"properties": {},
|
||||
"additionalProperties": false
|
||||
},
|
||||
"clipboardWrite": {
|
||||
"description": "Request clipboard write access (Permission Policy `clipboard-write` feature).",
|
||||
"description": "Request clipboard write access.\n\nMaps to Permission Policy `clipboard-write` feature.",
|
||||
"type": "object",
|
||||
"properties": {},
|
||||
"additionalProperties": false
|
||||
|
|
@ -165,28 +165,28 @@
|
|||
"type": "object",
|
||||
"properties": {
|
||||
"connectDomains": {
|
||||
"description": "Origins for network requests (fetch/XHR/WebSocket).",
|
||||
"description": "Origins for network requests (fetch/XHR/WebSocket).\n\n- Maps to CSP `connect-src` directive\n- Empty or omitted → no external connections (secure default)",
|
||||
"type": "array",
|
||||
"items": {
|
||||
"type": "string"
|
||||
}
|
||||
},
|
||||
"resourceDomains": {
|
||||
"description": "Origins for static resources (scripts, images, styles, fonts).",
|
||||
"description": "Origins for static resources (images, scripts, stylesheets, fonts, media).\n\n- Maps to CSP `img-src`, `script-src`, `style-src`, `font-src`, `media-src` directives\n- Wildcard subdomains supported: `https://*.example.com`\n- Empty or omitted → no external resources (secure default)",
|
||||
"type": "array",
|
||||
"items": {
|
||||
"type": "string"
|
||||
}
|
||||
},
|
||||
"frameDomains": {
|
||||
"description": "Origins for nested iframes (frame-src directive).",
|
||||
"description": "Origins for nested iframes.\n\n- Maps to CSP `frame-src` directive\n- Empty or omitted → no nested iframes allowed (`frame-src 'none'`)",
|
||||
"type": "array",
|
||||
"items": {
|
||||
"type": "string"
|
||||
}
|
||||
},
|
||||
"baseUriDomains": {
|
||||
"description": "Allowed base URIs for the document (base-uri directive).",
|
||||
"description": "Allowed base URIs for the document.\n\n- Maps to CSP `base-uri` directive\n- Empty or omitted → only same origin allowed (`base-uri 'self'`)",
|
||||
"type": "array",
|
||||
"items": {
|
||||
"type": "string"
|
||||
|
|
@ -2480,25 +2480,25 @@
|
|||
"type": "object",
|
||||
"properties": {
|
||||
"camera": {
|
||||
"description": "Request camera access (Permission Policy `camera` feature).",
|
||||
"description": "Request camera access.\n\nMaps to Permission Policy `camera` feature.",
|
||||
"type": "object",
|
||||
"properties": {},
|
||||
"additionalProperties": false
|
||||
},
|
||||
"microphone": {
|
||||
"description": "Request microphone access (Permission Policy `microphone` feature).",
|
||||
"description": "Request microphone access.\n\nMaps to Permission Policy `microphone` feature.",
|
||||
"type": "object",
|
||||
"properties": {},
|
||||
"additionalProperties": false
|
||||
},
|
||||
"geolocation": {
|
||||
"description": "Request geolocation access (Permission Policy `geolocation` feature).",
|
||||
"description": "Request geolocation access.\n\nMaps to Permission Policy `geolocation` feature.",
|
||||
"type": "object",
|
||||
"properties": {},
|
||||
"additionalProperties": false
|
||||
},
|
||||
"clipboardWrite": {
|
||||
"description": "Request clipboard write access (Permission Policy `clipboard-write` feature).",
|
||||
"description": "Request clipboard write access.\n\nMaps to Permission Policy `clipboard-write` feature.",
|
||||
"type": "object",
|
||||
"properties": {},
|
||||
"additionalProperties": false
|
||||
|
|
@ -2511,28 +2511,28 @@
|
|||
"type": "object",
|
||||
"properties": {
|
||||
"connectDomains": {
|
||||
"description": "Origins for network requests (fetch/XHR/WebSocket).",
|
||||
"description": "Origins for network requests (fetch/XHR/WebSocket).\n\n- Maps to CSP `connect-src` directive\n- Empty or omitted → no external connections (secure default)",
|
||||
"type": "array",
|
||||
"items": {
|
||||
"type": "string"
|
||||
}
|
||||
},
|
||||
"resourceDomains": {
|
||||
"description": "Origins for static resources (scripts, images, styles, fonts).",
|
||||
"description": "Origins for static resources (images, scripts, stylesheets, fonts, media).\n\n- Maps to CSP `img-src`, `script-src`, `style-src`, `font-src`, `media-src` directives\n- Wildcard subdomains supported: `https://*.example.com`\n- Empty or omitted → no external resources (secure default)",
|
||||
"type": "array",
|
||||
"items": {
|
||||
"type": "string"
|
||||
}
|
||||
},
|
||||
"frameDomains": {
|
||||
"description": "Origins for nested iframes (frame-src directive).",
|
||||
"description": "Origins for nested iframes.\n\n- Maps to CSP `frame-src` directive\n- Empty or omitted → no nested iframes allowed (`frame-src 'none'`)",
|
||||
"type": "array",
|
||||
"items": {
|
||||
"type": "string"
|
||||
}
|
||||
},
|
||||
"baseUriDomains": {
|
||||
"description": "Allowed base URIs for the document (base-uri directive).",
|
||||
"description": "Allowed base URIs for the document.\n\n- Maps to CSP `base-uri` directive\n- Empty or omitted → only same origin allowed (`base-uri 'self'`)",
|
||||
"type": "array",
|
||||
"items": {
|
||||
"type": "string"
|
||||
|
|
@ -3874,28 +3874,28 @@
|
|||
"type": "object",
|
||||
"properties": {
|
||||
"connectDomains": {
|
||||
"description": "Origins for network requests (fetch/XHR/WebSocket).",
|
||||
"description": "Origins for network requests (fetch/XHR/WebSocket).\n\n- Maps to CSP `connect-src` directive\n- Empty or omitted → no external connections (secure default)",
|
||||
"type": "array",
|
||||
"items": {
|
||||
"type": "string"
|
||||
}
|
||||
},
|
||||
"resourceDomains": {
|
||||
"description": "Origins for static resources (scripts, images, styles, fonts).",
|
||||
"description": "Origins for static resources (images, scripts, stylesheets, fonts, media).\n\n- Maps to CSP `img-src`, `script-src`, `style-src`, `font-src`, `media-src` directives\n- Wildcard subdomains supported: `https://*.example.com`\n- Empty or omitted → no external resources (secure default)",
|
||||
"type": "array",
|
||||
"items": {
|
||||
"type": "string"
|
||||
}
|
||||
},
|
||||
"frameDomains": {
|
||||
"description": "Origins for nested iframes (frame-src directive).",
|
||||
"description": "Origins for nested iframes.\n\n- Maps to CSP `frame-src` directive\n- Empty or omitted → no nested iframes allowed (`frame-src 'none'`)",
|
||||
"type": "array",
|
||||
"items": {
|
||||
"type": "string"
|
||||
}
|
||||
},
|
||||
"baseUriDomains": {
|
||||
"description": "Allowed base URIs for the document (base-uri directive).",
|
||||
"description": "Allowed base URIs for the document.\n\n- Maps to CSP `base-uri` directive\n- Empty or omitted → only same origin allowed (`base-uri 'self'`)",
|
||||
"type": "array",
|
||||
"items": {
|
||||
"type": "string"
|
||||
|
|
@ -3909,32 +3909,32 @@
|
|||
"type": "object",
|
||||
"properties": {
|
||||
"csp": {
|
||||
"description": "Content Security Policy configuration.",
|
||||
"description": "Content Security Policy configuration for UI resources.",
|
||||
"type": "object",
|
||||
"properties": {
|
||||
"connectDomains": {
|
||||
"description": "Origins for network requests (fetch/XHR/WebSocket).",
|
||||
"description": "Origins for network requests (fetch/XHR/WebSocket).\n\n- Maps to CSP `connect-src` directive\n- Empty or omitted → no external connections (secure default)",
|
||||
"type": "array",
|
||||
"items": {
|
||||
"type": "string"
|
||||
}
|
||||
},
|
||||
"resourceDomains": {
|
||||
"description": "Origins for static resources (scripts, images, styles, fonts).",
|
||||
"description": "Origins for static resources (images, scripts, stylesheets, fonts, media).\n\n- Maps to CSP `img-src`, `script-src`, `style-src`, `font-src`, `media-src` directives\n- Wildcard subdomains supported: `https://*.example.com`\n- Empty or omitted → no external resources (secure default)",
|
||||
"type": "array",
|
||||
"items": {
|
||||
"type": "string"
|
||||
}
|
||||
},
|
||||
"frameDomains": {
|
||||
"description": "Origins for nested iframes (frame-src directive).",
|
||||
"description": "Origins for nested iframes.\n\n- Maps to CSP `frame-src` directive\n- Empty or omitted → no nested iframes allowed (`frame-src 'none'`)",
|
||||
"type": "array",
|
||||
"items": {
|
||||
"type": "string"
|
||||
}
|
||||
},
|
||||
"baseUriDomains": {
|
||||
"description": "Allowed base URIs for the document (base-uri directive).",
|
||||
"description": "Allowed base URIs for the document.\n\n- Maps to CSP `base-uri` directive\n- Empty or omitted → only same origin allowed (`base-uri 'self'`)",
|
||||
"type": "array",
|
||||
"items": {
|
||||
"type": "string"
|
||||
|
|
@ -3944,29 +3944,29 @@
|
|||
"additionalProperties": false
|
||||
},
|
||||
"permissions": {
|
||||
"description": "Sandbox permissions requested by the UI.",
|
||||
"description": "Sandbox permissions requested by the UI resource.",
|
||||
"type": "object",
|
||||
"properties": {
|
||||
"camera": {
|
||||
"description": "Request camera access (Permission Policy `camera` feature).",
|
||||
"description": "Request camera access.\n\nMaps to Permission Policy `camera` feature.",
|
||||
"type": "object",
|
||||
"properties": {},
|
||||
"additionalProperties": false
|
||||
},
|
||||
"microphone": {
|
||||
"description": "Request microphone access (Permission Policy `microphone` feature).",
|
||||
"description": "Request microphone access.\n\nMaps to Permission Policy `microphone` feature.",
|
||||
"type": "object",
|
||||
"properties": {},
|
||||
"additionalProperties": false
|
||||
},
|
||||
"geolocation": {
|
||||
"description": "Request geolocation access (Permission Policy `geolocation` feature).",
|
||||
"description": "Request geolocation access.\n\nMaps to Permission Policy `geolocation` feature.",
|
||||
"type": "object",
|
||||
"properties": {},
|
||||
"additionalProperties": false
|
||||
},
|
||||
"clipboardWrite": {
|
||||
"description": "Request clipboard write access (Permission Policy `clipboard-write` feature).",
|
||||
"description": "Request clipboard write access.\n\nMaps to Permission Policy `clipboard-write` feature.",
|
||||
"type": "object",
|
||||
"properties": {},
|
||||
"additionalProperties": false
|
||||
|
|
@ -3975,11 +3975,11 @@
|
|||
"additionalProperties": false
|
||||
},
|
||||
"domain": {
|
||||
"description": "Dedicated origin for view sandbox.",
|
||||
"description": "Dedicated origin for view sandbox.\n\nUseful when views need stable, dedicated origins for OAuth callbacks, CORS policies, or API key allowlists.\n\n**Host-dependent:** The format and validation rules for this field are determined by each host. Servers MUST consult host-specific documentation for the expected domain format. Common patterns include:\n- Hash-based subdomains (e.g., `{hash}.claudemcpcontent.com`)\n- URL-derived subdomains (e.g., `www-example-com.oaiusercontent.com`)\n\nIf omitted, host uses default sandbox origin (typically per-conversation).",
|
||||
"type": "string"
|
||||
},
|
||||
"prefersBorder": {
|
||||
"description": "Visual boundary preference - true if UI prefers a visible border.",
|
||||
"description": "Visual boundary preference - true if view prefers a visible border.\n\nBoolean requesting whether a visible border and background is provided by the host. Specifying an explicit value for this is recommended because hosts' defaults may vary.\n\n- `true`: request visible border + background\n- `false`: request no visible border + background\n- omitted: host decides border",
|
||||
"type": "boolean"
|
||||
}
|
||||
},
|
||||
|
|
@ -3990,25 +3990,25 @@
|
|||
"type": "object",
|
||||
"properties": {
|
||||
"camera": {
|
||||
"description": "Request camera access (Permission Policy `camera` feature).",
|
||||
"description": "Request camera access.\n\nMaps to Permission Policy `camera` feature.",
|
||||
"type": "object",
|
||||
"properties": {},
|
||||
"additionalProperties": false
|
||||
},
|
||||
"microphone": {
|
||||
"description": "Request microphone access (Permission Policy `microphone` feature).",
|
||||
"description": "Request microphone access.\n\nMaps to Permission Policy `microphone` feature.",
|
||||
"type": "object",
|
||||
"properties": {},
|
||||
"additionalProperties": false
|
||||
},
|
||||
"geolocation": {
|
||||
"description": "Request geolocation access (Permission Policy `geolocation` feature).",
|
||||
"description": "Request geolocation access.\n\nMaps to Permission Policy `geolocation` feature.",
|
||||
"type": "object",
|
||||
"properties": {},
|
||||
"additionalProperties": false
|
||||
},
|
||||
"clipboardWrite": {
|
||||
"description": "Request clipboard write access (Permission Policy `clipboard-write` feature).",
|
||||
"description": "Request clipboard write access.\n\nMaps to Permission Policy `clipboard-write` feature.",
|
||||
"type": "object",
|
||||
"properties": {},
|
||||
"additionalProperties": false
|
||||
|
|
@ -4082,28 +4082,28 @@
|
|||
"type": "object",
|
||||
"properties": {
|
||||
"connectDomains": {
|
||||
"description": "Origins for network requests (fetch/XHR/WebSocket).",
|
||||
"description": "Origins for network requests (fetch/XHR/WebSocket).\n\n- Maps to CSP `connect-src` directive\n- Empty or omitted → no external connections (secure default)",
|
||||
"type": "array",
|
||||
"items": {
|
||||
"type": "string"
|
||||
}
|
||||
},
|
||||
"resourceDomains": {
|
||||
"description": "Origins for static resources (scripts, images, styles, fonts).",
|
||||
"description": "Origins for static resources (images, scripts, stylesheets, fonts, media).\n\n- Maps to CSP `img-src`, `script-src`, `style-src`, `font-src`, `media-src` directives\n- Wildcard subdomains supported: `https://*.example.com`\n- Empty or omitted → no external resources (secure default)",
|
||||
"type": "array",
|
||||
"items": {
|
||||
"type": "string"
|
||||
}
|
||||
},
|
||||
"frameDomains": {
|
||||
"description": "Origins for nested iframes (frame-src directive).",
|
||||
"description": "Origins for nested iframes.\n\n- Maps to CSP `frame-src` directive\n- Empty or omitted → no nested iframes allowed (`frame-src 'none'`)",
|
||||
"type": "array",
|
||||
"items": {
|
||||
"type": "string"
|
||||
}
|
||||
},
|
||||
"baseUriDomains": {
|
||||
"description": "Allowed base URIs for the document (base-uri directive).",
|
||||
"description": "Allowed base URIs for the document.\n\n- Maps to CSP `base-uri` directive\n- Empty or omitted → only same origin allowed (`base-uri 'self'`)",
|
||||
"type": "array",
|
||||
"items": {
|
||||
"type": "string"
|
||||
|
|
@ -4117,25 +4117,25 @@
|
|||
"type": "object",
|
||||
"properties": {
|
||||
"camera": {
|
||||
"description": "Request camera access (Permission Policy `camera` feature).",
|
||||
"description": "Request camera access.\n\nMaps to Permission Policy `camera` feature.",
|
||||
"type": "object",
|
||||
"properties": {},
|
||||
"additionalProperties": false
|
||||
},
|
||||
"microphone": {
|
||||
"description": "Request microphone access (Permission Policy `microphone` feature).",
|
||||
"description": "Request microphone access.\n\nMaps to Permission Policy `microphone` feature.",
|
||||
"type": "object",
|
||||
"properties": {},
|
||||
"additionalProperties": false
|
||||
},
|
||||
"geolocation": {
|
||||
"description": "Request geolocation access (Permission Policy `geolocation` feature).",
|
||||
"description": "Request geolocation access.\n\nMaps to Permission Policy `geolocation` feature.",
|
||||
"type": "object",
|
||||
"properties": {},
|
||||
"additionalProperties": false
|
||||
},
|
||||
"clipboardWrite": {
|
||||
"description": "Request clipboard write access (Permission Policy `clipboard-write` feature).",
|
||||
"description": "Request clipboard write access.\n\nMaps to Permission Policy `clipboard-write` feature.",
|
||||
"type": "object",
|
||||
"properties": {},
|
||||
"additionalProperties": false
|
||||
|
|
|
|||
163
src/generated/schema.ts
generated
163
src/generated/schema.ts
generated
|
|
@ -187,61 +187,138 @@ export const McpUiSandboxProxyReadyNotificationSchema = z.object({
|
|||
|
||||
/**
|
||||
* @description Content Security Policy configuration for UI resources.
|
||||
*
|
||||
* Servers declare which external origins their UI needs to access.
|
||||
* Hosts use this to enforce appropriate CSP headers.
|
||||
*
|
||||
* > [!IMPORTANT]
|
||||
* > MCP App HTML runs in a sandboxed iframe with no same-origin server.
|
||||
* > **All** origins must be declared—including where your bundled JS/CSS is
|
||||
* > served from (`localhost` in dev, your CDN in production).
|
||||
*/
|
||||
export const McpUiResourceCspSchema = z.object({
|
||||
/** @description Origins for network requests (fetch/XHR/WebSocket). */
|
||||
/**
|
||||
* @description Origins for network requests (fetch/XHR/WebSocket).
|
||||
*
|
||||
* - Maps to CSP `connect-src` directive
|
||||
* - Empty or omitted → no external connections (secure default)
|
||||
*
|
||||
* @example
|
||||
* ```ts
|
||||
* ["https://api.weather.com", "wss://realtime.service.com"]
|
||||
* ```
|
||||
*/
|
||||
connectDomains: z
|
||||
.array(z.string())
|
||||
.optional()
|
||||
.describe("Origins for network requests (fetch/XHR/WebSocket)."),
|
||||
/** @description Origins for static resources (scripts, images, styles, fonts). */
|
||||
.describe(
|
||||
"Origins for network requests (fetch/XHR/WebSocket).\n\n- Maps to CSP `connect-src` directive\n- Empty or omitted \u2192 no external connections (secure default)",
|
||||
),
|
||||
/**
|
||||
* @description Origins for static resources (images, scripts, stylesheets, fonts, media).
|
||||
*
|
||||
* - Maps to CSP `img-src`, `script-src`, `style-src`, `font-src`, `media-src` directives
|
||||
* - Wildcard subdomains supported: `https://*.example.com`
|
||||
* - Empty or omitted → no external resources (secure default)
|
||||
*
|
||||
* @example
|
||||
* ```ts
|
||||
* ["https://cdn.jsdelivr.net", "https://*.cloudflare.com"]
|
||||
* ```
|
||||
*/
|
||||
resourceDomains: z
|
||||
.array(z.string())
|
||||
.optional()
|
||||
.describe("Origins for static resources (scripts, images, styles, fonts)."),
|
||||
/** @description Origins for nested iframes (frame-src directive). */
|
||||
.describe(
|
||||
"Origins for static resources (images, scripts, stylesheets, fonts, media).\n\n- Maps to CSP `img-src`, `script-src`, `style-src`, `font-src`, `media-src` directives\n- Wildcard subdomains supported: `https://*.example.com`\n- Empty or omitted \u2192 no external resources (secure default)",
|
||||
),
|
||||
/**
|
||||
* @description Origins for nested iframes.
|
||||
*
|
||||
* - Maps to CSP `frame-src` directive
|
||||
* - Empty or omitted → no nested iframes allowed (`frame-src 'none'`)
|
||||
*
|
||||
* @example
|
||||
* ```ts
|
||||
* ["https://www.youtube.com", "https://player.vimeo.com"]
|
||||
* ```
|
||||
*/
|
||||
frameDomains: z
|
||||
.array(z.string())
|
||||
.optional()
|
||||
.describe("Origins for nested iframes (frame-src directive)."),
|
||||
/** @description Allowed base URIs for the document (base-uri directive). */
|
||||
.describe(
|
||||
"Origins for nested iframes.\n\n- Maps to CSP `frame-src` directive\n- Empty or omitted \u2192 no nested iframes allowed (`frame-src 'none'`)",
|
||||
),
|
||||
/**
|
||||
* @description Allowed base URIs for the document.
|
||||
*
|
||||
* - Maps to CSP `base-uri` directive
|
||||
* - Empty or omitted → only same origin allowed (`base-uri 'self'`)
|
||||
*
|
||||
* @example
|
||||
* ```ts
|
||||
* ["https://cdn.example.com"]
|
||||
* ```
|
||||
*/
|
||||
baseUriDomains: z
|
||||
.array(z.string())
|
||||
.optional()
|
||||
.describe("Allowed base URIs for the document (base-uri directive)."),
|
||||
.describe(
|
||||
"Allowed base URIs for the document.\n\n- Maps to CSP `base-uri` directive\n- Empty or omitted \u2192 only same origin allowed (`base-uri 'self'`)",
|
||||
),
|
||||
});
|
||||
|
||||
/**
|
||||
* @description Sandbox permissions requested by the UI resource.
|
||||
*
|
||||
* Servers declare which browser capabilities their UI needs.
|
||||
* Hosts MAY honor these by setting appropriate iframe `allow` attributes.
|
||||
* Apps SHOULD NOT assume permissions are granted; use JS feature detection as fallback.
|
||||
*/
|
||||
export const McpUiResourcePermissionsSchema = z.object({
|
||||
/** @description Request camera access (Permission Policy `camera` feature). */
|
||||
/**
|
||||
* @description Request camera access.
|
||||
*
|
||||
* Maps to Permission Policy `camera` feature.
|
||||
*/
|
||||
camera: z
|
||||
.object({})
|
||||
.optional()
|
||||
.describe("Request camera access (Permission Policy `camera` feature)."),
|
||||
/** @description Request microphone access (Permission Policy `microphone` feature). */
|
||||
.describe(
|
||||
"Request camera access.\n\nMaps to Permission Policy `camera` feature.",
|
||||
),
|
||||
/**
|
||||
* @description Request microphone access.
|
||||
*
|
||||
* Maps to Permission Policy `microphone` feature.
|
||||
*/
|
||||
microphone: z
|
||||
.object({})
|
||||
.optional()
|
||||
.describe(
|
||||
"Request microphone access (Permission Policy `microphone` feature).",
|
||||
"Request microphone access.\n\nMaps to Permission Policy `microphone` feature.",
|
||||
),
|
||||
/** @description Request geolocation access (Permission Policy `geolocation` feature). */
|
||||
/**
|
||||
* @description Request geolocation access.
|
||||
*
|
||||
* Maps to Permission Policy `geolocation` feature.
|
||||
*/
|
||||
geolocation: z
|
||||
.object({})
|
||||
.optional()
|
||||
.describe(
|
||||
"Request geolocation access (Permission Policy `geolocation` feature).",
|
||||
"Request geolocation access.\n\nMaps to Permission Policy `geolocation` feature.",
|
||||
),
|
||||
/** @description Request clipboard write access (Permission Policy `clipboard-write` feature). */
|
||||
/**
|
||||
* @description Request clipboard write access.
|
||||
*
|
||||
* Maps to Permission Policy `clipboard-write` feature.
|
||||
*/
|
||||
clipboardWrite: z
|
||||
.object({})
|
||||
.optional()
|
||||
.describe(
|
||||
"Request clipboard write access (Permission Policy `clipboard-write` feature).",
|
||||
"Request clipboard write access.\n\nMaps to Permission Policy `clipboard-write` feature.",
|
||||
),
|
||||
});
|
||||
|
||||
|
|
@ -490,22 +567,55 @@ export const McpUiInitializedNotificationSchema = z.object({
|
|||
* @description UI Resource metadata for security and rendering configuration.
|
||||
*/
|
||||
export const McpUiResourceMetaSchema = z.object({
|
||||
/** @description Content Security Policy configuration. */
|
||||
/** @description Content Security Policy configuration for UI resources. */
|
||||
csp: McpUiResourceCspSchema.optional().describe(
|
||||
"Content Security Policy configuration.",
|
||||
"Content Security Policy configuration for UI resources.",
|
||||
),
|
||||
/** @description Sandbox permissions requested by the UI. */
|
||||
/** @description Sandbox permissions requested by the UI resource. */
|
||||
permissions: McpUiResourcePermissionsSchema.optional().describe(
|
||||
"Sandbox permissions requested by the UI.",
|
||||
"Sandbox permissions requested by the UI resource.",
|
||||
),
|
||||
/** @description Dedicated origin for view sandbox. */
|
||||
domain: z.string().optional().describe("Dedicated origin for view sandbox."),
|
||||
/** @description Visual boundary preference - true if UI prefers a visible border. */
|
||||
/**
|
||||
* @description Dedicated origin for view sandbox.
|
||||
*
|
||||
* Useful when views need stable, dedicated origins for OAuth callbacks, CORS policies, or API key allowlists.
|
||||
*
|
||||
* **Host-dependent:** The format and validation rules for this field are determined by each host. Servers MUST consult host-specific documentation for the expected domain format. Common patterns include:
|
||||
* - Hash-based subdomains (e.g., `{hash}.claudemcpcontent.com`)
|
||||
* - URL-derived subdomains (e.g., `www-example-com.oaiusercontent.com`)
|
||||
*
|
||||
* If omitted, host uses default sandbox origin (typically per-conversation).
|
||||
*
|
||||
* @example
|
||||
* ```ts
|
||||
* "a904794854a047f6.claudemcpcontent.com"
|
||||
* ```
|
||||
*
|
||||
* @example
|
||||
* ```ts
|
||||
* "www-example-com.oaiusercontent.com"
|
||||
* ```
|
||||
*/
|
||||
domain: z
|
||||
.string()
|
||||
.optional()
|
||||
.describe(
|
||||
"Dedicated origin for view sandbox.\n\nUseful when views need stable, dedicated origins for OAuth callbacks, CORS policies, or API key allowlists.\n\n**Host-dependent:** The format and validation rules for this field are determined by each host. Servers MUST consult host-specific documentation for the expected domain format. Common patterns include:\n- Hash-based subdomains (e.g., `{hash}.claudemcpcontent.com`)\n- URL-derived subdomains (e.g., `www-example-com.oaiusercontent.com`)\n\nIf omitted, host uses default sandbox origin (typically per-conversation).",
|
||||
),
|
||||
/**
|
||||
* @description Visual boundary preference - true if view prefers a visible border.
|
||||
*
|
||||
* Boolean requesting whether a visible border and background is provided by the host. Specifying an explicit value for this is recommended because hosts' defaults may vary.
|
||||
*
|
||||
* - `true`: request visible border + background
|
||||
* - `false`: request no visible border + background
|
||||
* - omitted: host decides border
|
||||
*/
|
||||
prefersBorder: z
|
||||
.boolean()
|
||||
.optional()
|
||||
.describe(
|
||||
"Visual boundary preference - true if UI prefers a visible border.",
|
||||
"Visual boundary preference - true if view prefers a visible border.\n\nBoolean requesting whether a visible border and background is provided by the host. Specifying an explicit value for this is recommended because hosts' defaults may vary.\n\n- `true`: request visible border + background\n- `false`: request no visible border + background\n- omitted: host decides border",
|
||||
),
|
||||
});
|
||||
|
||||
|
|
@ -551,7 +661,10 @@ export const McpUiToolMetaSchema = z.object({
|
|||
* URI of the UI resource to display for this tool, if any.
|
||||
* This is converted to `_meta["ui/resourceUri"]`.
|
||||
*
|
||||
* @example "ui://weather/view.html"
|
||||
* @example
|
||||
* ```ts
|
||||
* "ui://weather/view.html"
|
||||
* ```
|
||||
*/
|
||||
resourceUri: z.string().optional(),
|
||||
/**
|
||||
|
|
|
|||
|
|
@ -538,31 +538,98 @@ export interface McpUiInitializedNotification {
|
|||
|
||||
/**
|
||||
* @description Content Security Policy configuration for UI resources.
|
||||
*
|
||||
* Servers declare which external origins their UI needs to access.
|
||||
* Hosts use this to enforce appropriate CSP headers.
|
||||
*
|
||||
* > [!IMPORTANT]
|
||||
* > MCP App HTML runs in a sandboxed iframe with no same-origin server.
|
||||
* > **All** origins must be declared—including where your bundled JS/CSS is
|
||||
* > served from (`localhost` in dev, your CDN in production).
|
||||
*/
|
||||
export interface McpUiResourceCsp {
|
||||
/** @description Origins for network requests (fetch/XHR/WebSocket). */
|
||||
/**
|
||||
* @description Origins for network requests (fetch/XHR/WebSocket).
|
||||
*
|
||||
* - Maps to CSP `connect-src` directive
|
||||
* - Empty or omitted → no external connections (secure default)
|
||||
*
|
||||
* @example
|
||||
* ```ts
|
||||
* ["https://api.weather.com", "wss://realtime.service.com"]
|
||||
* ```
|
||||
*/
|
||||
connectDomains?: string[];
|
||||
/** @description Origins for static resources (scripts, images, styles, fonts). */
|
||||
/**
|
||||
* @description Origins for static resources (images, scripts, stylesheets, fonts, media).
|
||||
*
|
||||
* - Maps to CSP `img-src`, `script-src`, `style-src`, `font-src`, `media-src` directives
|
||||
* - Wildcard subdomains supported: `https://*.example.com`
|
||||
* - Empty or omitted → no external resources (secure default)
|
||||
*
|
||||
* @example
|
||||
* ```ts
|
||||
* ["https://cdn.jsdelivr.net", "https://*.cloudflare.com"]
|
||||
* ```
|
||||
*/
|
||||
resourceDomains?: string[];
|
||||
/** @description Origins for nested iframes (frame-src directive). */
|
||||
/**
|
||||
* @description Origins for nested iframes.
|
||||
*
|
||||
* - Maps to CSP `frame-src` directive
|
||||
* - Empty or omitted → no nested iframes allowed (`frame-src 'none'`)
|
||||
*
|
||||
* @example
|
||||
* ```ts
|
||||
* ["https://www.youtube.com", "https://player.vimeo.com"]
|
||||
* ```
|
||||
*/
|
||||
frameDomains?: string[];
|
||||
/** @description Allowed base URIs for the document (base-uri directive). */
|
||||
/**
|
||||
* @description Allowed base URIs for the document.
|
||||
*
|
||||
* - Maps to CSP `base-uri` directive
|
||||
* - Empty or omitted → only same origin allowed (`base-uri 'self'`)
|
||||
*
|
||||
* @example
|
||||
* ```ts
|
||||
* ["https://cdn.example.com"]
|
||||
* ```
|
||||
*/
|
||||
baseUriDomains?: string[];
|
||||
}
|
||||
|
||||
/**
|
||||
* @description Sandbox permissions requested by the UI resource.
|
||||
*
|
||||
* Servers declare which browser capabilities their UI needs.
|
||||
* Hosts MAY honor these by setting appropriate iframe `allow` attributes.
|
||||
* Apps SHOULD NOT assume permissions are granted; use JS feature detection as fallback.
|
||||
*/
|
||||
export interface McpUiResourcePermissions {
|
||||
/** @description Request camera access (Permission Policy `camera` feature). */
|
||||
/**
|
||||
* @description Request camera access.
|
||||
*
|
||||
* Maps to Permission Policy `camera` feature.
|
||||
*/
|
||||
camera?: {};
|
||||
/** @description Request microphone access (Permission Policy `microphone` feature). */
|
||||
/**
|
||||
* @description Request microphone access.
|
||||
*
|
||||
* Maps to Permission Policy `microphone` feature.
|
||||
*/
|
||||
microphone?: {};
|
||||
/** @description Request geolocation access (Permission Policy `geolocation` feature). */
|
||||
/**
|
||||
* @description Request geolocation access.
|
||||
*
|
||||
* Maps to Permission Policy `geolocation` feature.
|
||||
*/
|
||||
geolocation?: {};
|
||||
/** @description Request clipboard write access (Permission Policy `clipboard-write` feature). */
|
||||
/**
|
||||
* @description Request clipboard write access.
|
||||
*
|
||||
* Maps to Permission Policy `clipboard-write` feature.
|
||||
*/
|
||||
clipboardWrite?: {};
|
||||
}
|
||||
|
||||
|
|
@ -570,13 +637,41 @@ export interface McpUiResourcePermissions {
|
|||
* @description UI Resource metadata for security and rendering configuration.
|
||||
*/
|
||||
export interface McpUiResourceMeta {
|
||||
/** @description Content Security Policy configuration. */
|
||||
/** @description Content Security Policy configuration for UI resources. */
|
||||
csp?: McpUiResourceCsp;
|
||||
/** @description Sandbox permissions requested by the UI. */
|
||||
/** @description Sandbox permissions requested by the UI resource. */
|
||||
permissions?: McpUiResourcePermissions;
|
||||
/** @description Dedicated origin for view sandbox. */
|
||||
/**
|
||||
* @description Dedicated origin for view sandbox.
|
||||
*
|
||||
* Useful when views need stable, dedicated origins for OAuth callbacks, CORS policies, or API key allowlists.
|
||||
*
|
||||
* **Host-dependent:** The format and validation rules for this field are determined by each host. Servers MUST consult host-specific documentation for the expected domain format. Common patterns include:
|
||||
* - Hash-based subdomains (e.g., `{hash}.claudemcpcontent.com`)
|
||||
* - URL-derived subdomains (e.g., `www-example-com.oaiusercontent.com`)
|
||||
*
|
||||
* If omitted, host uses default sandbox origin (typically per-conversation).
|
||||
*
|
||||
* @example
|
||||
* ```ts
|
||||
* "a904794854a047f6.claudemcpcontent.com"
|
||||
* ```
|
||||
*
|
||||
* @example
|
||||
* ```ts
|
||||
* "www-example-com.oaiusercontent.com"
|
||||
* ```
|
||||
*/
|
||||
domain?: string;
|
||||
/** @description Visual boundary preference - true if UI prefers a visible border. */
|
||||
/**
|
||||
* @description Visual boundary preference - true if view prefers a visible border.
|
||||
*
|
||||
* Boolean requesting whether a visible border and background is provided by the host. Specifying an explicit value for this is recommended because hosts' defaults may vary.
|
||||
*
|
||||
* - `true`: request visible border + background
|
||||
* - `false`: request no visible border + background
|
||||
* - omitted: host decides border
|
||||
*/
|
||||
prefersBorder?: boolean;
|
||||
}
|
||||
|
||||
|
|
@ -621,7 +716,10 @@ export interface McpUiToolMeta {
|
|||
* URI of the UI resource to display for this tool, if any.
|
||||
* This is converted to `_meta["ui/resourceUri"]`.
|
||||
*
|
||||
* @example "ui://weather/view.html"
|
||||
* @example
|
||||
* ```ts
|
||||
* "ui://weather/view.html"
|
||||
* ```
|
||||
*/
|
||||
resourceUri?: string;
|
||||
/**
|
||||
|
|
|
|||
Loading…
Reference in a new issue