From ee557a45623f6565393c875b37d4ac902009641b Mon Sep 17 00:00:00 2001 From: Ido Salomon Date: Wed, 10 Dec 2025 02:41:42 +0200 Subject: [PATCH 1/7] fix: ui/message accepts message array --- specification/draft/apps.mdx | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/specification/draft/apps.mdx b/specification/draft/apps.mdx index 112fea5c..7c8d8a3b 100644 --- a/specification/draft/apps.mdx +++ b/specification/draft/apps.mdx @@ -506,10 +506,12 @@ Host SHOULD open the URL in the user's default browser or a new tab. method: "ui/message", params: { role: "user", - content: { - type: "text", - text: string - } + content: [ + { + type: "text", + text: string + } + ] } } From b31250f7cac0df51dd4a7d86b07f492a7c962f8f Mon Sep 17 00:00:00 2001 From: Ido Salomon Date: Fri, 23 Jan 2026 12:23:57 +0200 Subject: [PATCH 2/7] modality negotiation --- specification/draft/apps.mdx | 31 ++- src/app-bridge.test.ts | 335 +++++++++++++++++++++++++++++++++ src/app-bridge.ts | 32 ++++ src/app.ts | 26 +++ src/content-validation.test.ts | 173 +++++++++++++++++ src/content-validation.ts | 94 +++++++++ 6 files changed, 685 insertions(+), 6 deletions(-) create mode 100644 src/content-validation.test.ts create mode 100644 src/content-validation.ts diff --git a/specification/draft/apps.mdx b/specification/draft/apps.mdx index c82def39..9026242b 100644 --- a/specification/draft/apps.mdx +++ b/specification/draft/apps.mdx @@ -640,6 +640,25 @@ interface HostCapabilities { baseUriDomains?: string[]; }; }; + /** Supported content block modalities for ui/message requests. */ + message?: SupportedContentBlockModalities; + /** Supported content block modalities for ui/update-model-context requests. */ + updateModelContext?: SupportedContentBlockModalities; +} + +interface SupportedContentBlockModalities { + /** Host supports text content blocks. */ + text?: {}; + /** Host supports image content blocks. */ + image?: {}; + /** Host supports audio content blocks. */ + audio?: {}; + /** Host supports resource content blocks. */ + resource?: {}; + /** Host supports resource link content blocks. */ + resourceLink?: {}; + /** Host supports structured content (updateModelContext only). */ + structuredContent?: {}; } ``` @@ -926,12 +945,8 @@ Host SHOULD open the URL in the user's default browser or a new tab. method: "ui/message", params: { role: "user", - content: [ - { - type: "text", - text: string - } - ] + content: ContentBlock[] // text, image, audio, resource, resource_link + // (subject to hostCapabilities.message modalities) } } @@ -955,6 +970,8 @@ Host SHOULD open the URL in the user's default browser or a new tab. Host behavior: * Host SHOULD add the message to the conversation context, preserving the specified role. * Host MAY request user consent. +* Host SHOULD declare a `message` capability with supported modalities during initialization. +* Host MUST respond with a JSON-RPC error if any content block type in the request is not in the declared `hostCapabilities.message`. `ui/request-display-mode` - Request host to change display mode @@ -1031,6 +1048,8 @@ Host behavior: - MAY dedupe identical `ui/update-model-context` calls - If multiple updates are received before the next user message, Host SHOULD only send the last update to the model - MAY display context updates to the user +- SHOULD declare an `updateModelContext` capability with supported modalities during initialization +- MUST respond with a JSON-RPC error if any content block type or `structuredContent` in the request is not declared in `hostCapabilities.updateModelContext` #### Notifications (Host → UI) diff --git a/src/app-bridge.test.ts b/src/app-bridge.test.ts index 66d5f830..4b6f64b6 100644 --- a/src/app-bridge.test.ts +++ b/src/app-bridge.test.ts @@ -818,6 +818,341 @@ describe("App <-> AppBridge integration", () => { }); }); +describe("Content block modality validation", () => { + let app: App; + let bridge: AppBridge; + let appTransport: InMemoryTransport; + let bridgeTransport: InMemoryTransport; + + afterEach(async () => { + await appTransport.close(); + await bridgeTransport.close(); + }); + + describe("Guest-side validation (sendMessage)", () => { + it("throws when sending unsupported content type", async () => { + [appTransport, bridgeTransport] = InMemoryTransport.createLinkedPair(); + const capabilities: McpUiHostCapabilities = { + ...testHostCapabilities, + message: { text: {} }, + }; + bridge = new AppBridge( + createMockClient() as Client, + testHostInfo, + capabilities, + ); + bridge.onmessage = async () => ({}); + app = new App(testAppInfo, {}, { autoResize: false }); + + await bridge.connect(bridgeTransport); + await app.connect(appTransport); + + expect(() => + app.sendMessage({ + role: "user", + content: [ + { type: "image", data: "base64data", mimeType: "image/png" }, + ], + }), + ).toThrow("unsupported content type(s): image"); + }); + + it("allows content when modality is declared", async () => { + [appTransport, bridgeTransport] = InMemoryTransport.createLinkedPair(); + const capabilities: McpUiHostCapabilities = { + ...testHostCapabilities, + message: { text: {}, image: {} }, + }; + bridge = new AppBridge( + createMockClient() as Client, + testHostInfo, + capabilities, + ); + bridge.onmessage = async () => ({}); + app = new App(testAppInfo, {}, { autoResize: false }); + + await bridge.connect(bridgeTransport); + await app.connect(appTransport); + + const result = await app.sendMessage({ + role: "user", + content: [ + { type: "text", text: "hello" }, + { type: "image", data: "base64data", mimeType: "image/png" }, + ], + }); + expect(result).toEqual({}); + }); + + it("skips validation when message capability is not declared (backwards compat)", async () => { + [appTransport, bridgeTransport] = InMemoryTransport.createLinkedPair(); + // No message capability declared + bridge = new AppBridge( + createMockClient() as Client, + testHostInfo, + testHostCapabilities, + ); + bridge.onmessage = async () => ({}); + app = new App(testAppInfo, {}, { autoResize: false }); + + await bridge.connect(bridgeTransport); + await app.connect(appTransport); + + // Should succeed even with image content since message capability is not declared + const result = await app.sendMessage({ + role: "user", + content: [ + { type: "image", data: "base64data", mimeType: "image/png" }, + ], + }); + expect(result).toEqual({}); + }); + + it("rejects all types when message capability is empty object", async () => { + [appTransport, bridgeTransport] = InMemoryTransport.createLinkedPair(); + const capabilities: McpUiHostCapabilities = { + ...testHostCapabilities, + message: {}, + }; + bridge = new AppBridge( + createMockClient() as Client, + testHostInfo, + capabilities, + ); + bridge.onmessage = async () => ({}); + app = new App(testAppInfo, {}, { autoResize: false }); + + await bridge.connect(bridgeTransport); + await app.connect(appTransport); + + expect(() => + app.sendMessage({ + role: "user", + content: [{ type: "text", text: "hello" }], + }), + ).toThrow("unsupported content type(s): text"); + }); + + it("resource_link type maps to resourceLink modality correctly", async () => { + [appTransport, bridgeTransport] = InMemoryTransport.createLinkedPair(); + const capabilities: McpUiHostCapabilities = { + ...testHostCapabilities, + message: { resourceLink: {} }, + }; + bridge = new AppBridge( + createMockClient() as Client, + testHostInfo, + capabilities, + ); + bridge.onmessage = async () => ({}); + app = new App(testAppInfo, {}, { autoResize: false }); + + await bridge.connect(bridgeTransport); + await app.connect(appTransport); + + const result = await app.sendMessage({ + role: "user", + content: [ + { + type: "resource_link", + uri: "test://resource", + name: "Test Resource", + }, + ], + }); + expect(result).toEqual({}); + }); + }); + + describe("Guest-side validation (updateModelContext)", () => { + it("throws when sending unsupported content type", async () => { + [appTransport, bridgeTransport] = InMemoryTransport.createLinkedPair(); + const capabilities: McpUiHostCapabilities = { + ...testHostCapabilities, + updateModelContext: { text: {} }, + }; + bridge = new AppBridge( + createMockClient() as Client, + testHostInfo, + capabilities, + ); + bridge.onupdatemodelcontext = async () => ({}); + app = new App(testAppInfo, {}, { autoResize: false }); + + await bridge.connect(bridgeTransport); + await app.connect(appTransport); + + expect(() => + app.updateModelContext({ + content: [ + { type: "image", data: "base64data", mimeType: "image/png" }, + ], + }), + ).toThrow("unsupported content type(s): image"); + }); + + it("throws when sending structuredContent without capability", async () => { + [appTransport, bridgeTransport] = InMemoryTransport.createLinkedPair(); + const capabilities: McpUiHostCapabilities = { + ...testHostCapabilities, + updateModelContext: { text: {} }, + }; + bridge = new AppBridge( + createMockClient() as Client, + testHostInfo, + capabilities, + ); + bridge.onupdatemodelcontext = async () => ({}); + app = new App(testAppInfo, {}, { autoResize: false }); + + await bridge.connect(bridgeTransport); + await app.connect(appTransport); + + expect(() => + app.updateModelContext({ + structuredContent: { key: "value" }, + }), + ).toThrow("structuredContent is not supported"); + }); + + it("allows structuredContent when declared", async () => { + [appTransport, bridgeTransport] = InMemoryTransport.createLinkedPair(); + const capabilities: McpUiHostCapabilities = { + ...testHostCapabilities, + updateModelContext: { text: {}, structuredContent: {} }, + }; + bridge = new AppBridge( + createMockClient() as Client, + testHostInfo, + capabilities, + ); + bridge.onupdatemodelcontext = async () => ({}); + app = new App(testAppInfo, {}, { autoResize: false }); + + await bridge.connect(bridgeTransport); + await app.connect(appTransport); + + const result = await app.updateModelContext({ + structuredContent: { key: "value" }, + }); + expect(result).toEqual({}); + }); + + it("skips validation when updateModelContext capability is not declared", async () => { + [appTransport, bridgeTransport] = InMemoryTransport.createLinkedPair(); + bridge = new AppBridge( + createMockClient() as Client, + testHostInfo, + testHostCapabilities, + ); + bridge.onupdatemodelcontext = async () => ({}); + app = new App(testAppInfo, {}, { autoResize: false }); + + await bridge.connect(bridgeTransport); + await app.connect(appTransport); + + const result = await app.updateModelContext({ + content: [ + { type: "image", data: "base64data", mimeType: "image/png" }, + ], + structuredContent: { key: "value" }, + }); + expect(result).toEqual({}); + }); + }); + + describe("Host-side validation", () => { + it("host rejects unsupported content in onmessage", async () => { + [appTransport, bridgeTransport] = InMemoryTransport.createLinkedPair(); + const capabilities: McpUiHostCapabilities = { + ...testHostCapabilities, + message: { text: {} }, + }; + // Use null client so we don't get guest-side validation + // (the bridge still validates on the host side) + bridge = new AppBridge(null, testHostInfo, capabilities); + bridge.onmessage = async () => ({}); + + // Create app without host capabilities knowledge to bypass guest validation + app = new App(testAppInfo, {}, { autoResize: false }); + + await bridge.connect(bridgeTransport); + await app.connect(appTransport); + + // The app received capabilities during connect, so it will validate. + // To test host-side validation independently, we directly send the request. + await expect( + app.request( + { + method: "ui/message" as any, + params: { + role: "user", + content: [ + { type: "image", data: "base64data", mimeType: "image/png" }, + ], + }, + }, + EmptyResultSchema, + ), + ).rejects.toThrow("unsupported content type(s): image"); + }); + + it("host rejects unsupported content in onupdatemodelcontext", async () => { + [appTransport, bridgeTransport] = InMemoryTransport.createLinkedPair(); + const capabilities: McpUiHostCapabilities = { + ...testHostCapabilities, + updateModelContext: { text: {} }, + }; + bridge = new AppBridge(null, testHostInfo, capabilities); + bridge.onupdatemodelcontext = async () => ({}); + app = new App(testAppInfo, {}, { autoResize: false }); + + await bridge.connect(bridgeTransport); + await app.connect(appTransport); + + await expect( + app.request( + { + method: "ui/update-model-context" as any, + params: { + content: [ + { type: "audio", data: "base64", mimeType: "audio/mp3" }, + ], + }, + }, + EmptyResultSchema, + ), + ).rejects.toThrow("unsupported content type(s): audio"); + }); + + it("host rejects structuredContent when not declared", async () => { + [appTransport, bridgeTransport] = InMemoryTransport.createLinkedPair(); + const capabilities: McpUiHostCapabilities = { + ...testHostCapabilities, + updateModelContext: { text: {} }, + }; + bridge = new AppBridge(null, testHostInfo, capabilities); + bridge.onupdatemodelcontext = async () => ({}); + app = new App(testAppInfo, {}, { autoResize: false }); + + await bridge.connect(bridgeTransport); + await app.connect(appTransport); + + await expect( + app.request( + { + method: "ui/update-model-context" as any, + params: { + structuredContent: { key: "value" }, + }, + }, + EmptyResultSchema, + ), + ).rejects.toThrow("structuredContent is not supported"); + }); + }); +}); + describe("getToolUiResourceUri", () => { describe("new nested format (_meta.ui.resourceUri)", () => { it("extracts resourceUri from _meta.ui.resourceUri", () => { diff --git a/src/app-bridge.ts b/src/app-bridge.ts index fcffaf40..111ae747 100644 --- a/src/app-bridge.ts +++ b/src/app-bridge.ts @@ -79,6 +79,10 @@ import { McpUiRequestDisplayModeResult, McpUiResourcePermissions, } from "./types"; +import { + validateContentModalities, + buildValidationErrorMessage, +} from "./content-validation"; export * from "./types"; export { RESOURCE_URI_META_KEY, RESOURCE_MIME_TYPE } from "./app"; import { RESOURCE_URI_META_KEY } from "./app"; @@ -436,6 +440,18 @@ export class AppBridge extends Protocol< this.setRequestHandler( McpUiMessageRequestSchema, async (request, extra) => { + const modalities = this._capabilities.message; + if (modalities !== undefined) { + const validation = validateContentModalities( + request.params.content, + modalities, + ); + if (!validation.valid) { + throw new Error( + buildValidationErrorMessage(validation, "ui/message"), + ); + } + } return callback(request.params, extra); }, ); @@ -574,6 +590,22 @@ export class AppBridge extends Protocol< this.setRequestHandler( McpUiUpdateModelContextRequestSchema, async (request, extra) => { + const modalities = this._capabilities.updateModelContext; + if (modalities !== undefined) { + const validation = validateContentModalities( + request.params.content, + modalities, + request.params.structuredContent !== undefined, + ); + if (!validation.valid) { + throw new Error( + buildValidationErrorMessage( + validation, + "ui/update-model-context", + ), + ); + } + } return callback(request.params, extra); }, ); diff --git a/src/app.ts b/src/app.ts index 9ef0af41..67ad2402 100644 --- a/src/app.ts +++ b/src/app.ts @@ -18,6 +18,10 @@ import { } from "@modelcontextprotocol/sdk/types.js"; import { AppNotification, AppRequest, AppResult } from "./types"; import { PostMessageTransport } from "./message-transport"; +import { + validateContentModalities, + buildValidationErrorMessage, +} from "./content-validation"; import { LATEST_PROTOCOL_VERSION, McpUiAppCapabilities, @@ -621,6 +625,14 @@ export class App extends Protocol { * @see {@link McpUiMessageRequest `McpUiMessageRequest`} for request structure */ sendMessage(params: McpUiMessageRequest["params"], options?: RequestOptions) { + const modalities = this._hostCapabilities?.message; + if (modalities !== undefined) { + const result = validateContentModalities(params.content, modalities); + if (!result.valid) { + throw new Error(buildValidationErrorMessage(result, "ui/message")); + } + } + return this.request( { method: "ui/message", @@ -679,6 +691,20 @@ export class App extends Protocol { params: McpUiUpdateModelContextRequest["params"], options?: RequestOptions, ) { + const modalities = this._hostCapabilities?.updateModelContext; + if (modalities !== undefined) { + const result = validateContentModalities( + params.content, + modalities, + params.structuredContent !== undefined, + ); + if (!result.valid) { + throw new Error( + buildValidationErrorMessage(result, "ui/update-model-context"), + ); + } + } + return this.request( { method: "ui/update-model-context", diff --git a/src/content-validation.test.ts b/src/content-validation.test.ts new file mode 100644 index 00000000..b4174517 --- /dev/null +++ b/src/content-validation.test.ts @@ -0,0 +1,173 @@ +import { describe, it, expect } from "bun:test"; +import { + validateContentModalities, + buildValidationErrorMessage, +} from "./content-validation"; + +describe("validateContentModalities", () => { + it("returns valid when modalities is undefined (backwards compat)", () => { + const result = validateContentModalities( + [{ type: "text", text: "hello" }], + undefined, + ); + expect(result.valid).toBe(true); + expect(result.unsupportedTypes).toEqual([]); + expect(result.structuredContentUnsupported).toBe(false); + }); + + it("returns valid when all content types are supported", () => { + const result = validateContentModalities( + [ + { type: "text", text: "hello" }, + { type: "image", data: "base64data", mimeType: "image/png" }, + ], + { text: {}, image: {} }, + ); + expect(result.valid).toBe(true); + expect(result.unsupportedTypes).toEqual([]); + }); + + it("returns invalid with unsupported types listed", () => { + const result = validateContentModalities( + [ + { type: "text", text: "hello" }, + { type: "image", data: "base64data", mimeType: "image/png" }, + ], + { text: {} }, + ); + expect(result.valid).toBe(false); + expect(result.unsupportedTypes).toEqual(["image"]); + }); + + it("handles resource_link → resourceLink mapping", () => { + const result = validateContentModalities( + [{ type: "resource_link", uri: "test://resource", name: "test" }], + { resourceLink: {} }, + ); + expect(result.valid).toBe(true); + expect(result.unsupportedTypes).toEqual([]); + }); + + it("returns invalid when resource_link is used without resourceLink modality", () => { + const result = validateContentModalities( + [{ type: "resource_link", uri: "test://resource", name: "test" }], + { text: {} }, + ); + expect(result.valid).toBe(false); + expect(result.unsupportedTypes).toEqual(["resource_link"]); + }); + + it("detects unsupported structuredContent", () => { + const result = validateContentModalities([], { text: {} }, true); + expect(result.valid).toBe(false); + expect(result.structuredContentUnsupported).toBe(true); + }); + + it("allows structuredContent when declared", () => { + const result = validateContentModalities( + [], + { text: {}, structuredContent: {} }, + true, + ); + expect(result.valid).toBe(true); + expect(result.structuredContentUnsupported).toBe(false); + }); + + it("handles undefined content array", () => { + const result = validateContentModalities(undefined, { text: {} }); + expect(result.valid).toBe(true); + expect(result.unsupportedTypes).toEqual([]); + }); + + it("handles empty content array", () => { + const result = validateContentModalities([], { text: {} }); + expect(result.valid).toBe(true); + expect(result.unsupportedTypes).toEqual([]); + }); + + it("deduplicates unsupported type names", () => { + const result = validateContentModalities( + [ + { type: "image", data: "a", mimeType: "image/png" }, + { type: "image", data: "b", mimeType: "image/png" }, + { type: "audio", data: "c", mimeType: "audio/mp3" }, + ], + { text: {} }, + ); + expect(result.valid).toBe(false); + expect(result.unsupportedTypes).toEqual(["image", "audio"]); + }); + + it("rejects all content types when modalities is empty object", () => { + const result = validateContentModalities( + [{ type: "text", text: "hello" }], + {}, + ); + expect(result.valid).toBe(false); + expect(result.unsupportedTypes).toEqual(["text"]); + }); + + it("handles audio content type", () => { + const result = validateContentModalities( + [{ type: "audio", data: "base64", mimeType: "audio/mp3" }], + { audio: {} }, + ); + expect(result.valid).toBe(true); + }); + + it("handles resource content type", () => { + const result = validateContentModalities( + [{ type: "resource", resource: { uri: "test://r", text: "content" } }], + { resource: {} }, + ); + expect(result.valid).toBe(true); + }); + + it("returns invalid for unknown content type", () => { + const result = validateContentModalities( + [{ type: "unknown_type" } as any], + { text: {} }, + ); + expect(result.valid).toBe(false); + expect(result.unsupportedTypes).toEqual(["unknown_type"]); + }); + + it("validates both content blocks and structuredContent together", () => { + const result = validateContentModalities( + [{ type: "image", data: "data", mimeType: "image/png" }], + { text: {} }, + true, + ); + expect(result.valid).toBe(false); + expect(result.unsupportedTypes).toEqual(["image"]); + expect(result.structuredContentUnsupported).toBe(true); + }); +}); + +describe("buildValidationErrorMessage", () => { + it("builds message for unsupported content types", () => { + const msg = buildValidationErrorMessage( + { valid: false, unsupportedTypes: ["image", "audio"], structuredContentUnsupported: false }, + "ui/message", + ); + expect(msg).toBe("ui/message: unsupported content type(s): image, audio"); + }); + + it("builds message for unsupported structuredContent", () => { + const msg = buildValidationErrorMessage( + { valid: false, unsupportedTypes: [], structuredContentUnsupported: true }, + "ui/update-model-context", + ); + expect(msg).toBe("ui/update-model-context: structuredContent is not supported"); + }); + + it("builds message with both unsupported types and structuredContent", () => { + const msg = buildValidationErrorMessage( + { valid: false, unsupportedTypes: ["image"], structuredContentUnsupported: true }, + "ui/update-model-context", + ); + expect(msg).toBe( + "ui/update-model-context: unsupported content type(s): image; structuredContent is not supported", + ); + }); +}); diff --git a/src/content-validation.ts b/src/content-validation.ts new file mode 100644 index 00000000..bcfe4a13 --- /dev/null +++ b/src/content-validation.ts @@ -0,0 +1,94 @@ +import type { ContentBlock } from "@modelcontextprotocol/sdk/types.js"; +import type { McpUiSupportedContentBlockModalities } from "./types"; + +/** + * Maps a ContentBlock `type` to its corresponding modality key + * in {@link McpUiSupportedContentBlockModalities}. + */ +const CONTENT_TYPE_TO_MODALITY: Record = { + text: "text", + image: "image", + audio: "audio", + resource: "resource", + resource_link: "resourceLink", +}; + +/** + * Result of validating content blocks against supported modalities. + */ +interface ContentValidationResult { + /** Whether all content blocks (and structuredContent if provided) are supported. */ + valid: boolean; + /** Deduplicated list of unsupported content block type names. */ + unsupportedTypes: string[]; + /** Whether structuredContent was provided but not supported. */ + structuredContentUnsupported: boolean; +} + +/** + * Validate content blocks and optional structuredContent against declared modalities. + * + * Returns `{ valid: true }` if `modalities` is `undefined` (backwards compatibility: + * host did not declare the capability, so all types are allowed). + * + * @param content - Array of content blocks to validate (may be undefined/empty) + * @param modalities - Supported modalities declared by the host, or undefined to skip validation + * @param hasStructuredContent - Whether structuredContent is present in the request + * @returns Validation result with details about unsupported types + */ +export function validateContentModalities( + content: ContentBlock[] | undefined, + modalities: McpUiSupportedContentBlockModalities | undefined, + hasStructuredContent: boolean = false, +): ContentValidationResult { + // Backwards compatibility: if modalities is undefined, skip validation entirely + if (modalities === undefined) { + return { valid: true, unsupportedTypes: [], structuredContentUnsupported: false }; + } + + const unsupportedTypes = new Set(); + let structuredContentUnsupported = false; + + // Check each content block + if (content) { + for (const block of content) { + const modalityKey = CONTENT_TYPE_TO_MODALITY[(block as { type: string }).type]; + if (modalityKey === undefined || !(modalityKey in modalities)) { + unsupportedTypes.add((block as { type: string }).type); + } + } + } + + // Check structuredContent + if (hasStructuredContent && !("structuredContent" in modalities)) { + structuredContentUnsupported = true; + } + + const valid = unsupportedTypes.size === 0 && !structuredContentUnsupported; + return { + valid, + unsupportedTypes: [...unsupportedTypes], + structuredContentUnsupported, + }; +} + +/** + * Build a human-readable error message from a failed validation result. + * + * @param result - The validation result (must have `valid: false`) + * @param method - The protocol method name for context in the error message + * @returns Error message string + */ +export function buildValidationErrorMessage( + result: ContentValidationResult, + method: string, +): string { + const parts: string[] = []; + if (result.unsupportedTypes.length > 0) { + parts.push(`unsupported content type(s): ${result.unsupportedTypes.join(", ")}`); + } + if (result.structuredContentUnsupported) { + parts.push("structuredContent is not supported"); + } + return `${method}: ${parts.join("; ")}`; +} From e74ba3bdfc8ad85096bc5987490b3593c09951b2 Mon Sep 17 00:00:00 2001 From: Ido Salomon Date: Fri, 23 Jan 2026 12:24:16 +0200 Subject: [PATCH 3/7] husky --- src/app-bridge.test.ts | 8 ++------ src/content-validation.test.ts | 22 ++++++++++++++++++---- src/content-validation.ts | 18 ++++++++++++++---- 3 files changed, 34 insertions(+), 14 deletions(-) diff --git a/src/app-bridge.test.ts b/src/app-bridge.test.ts index 4b6f64b6..5ef0b4a1 100644 --- a/src/app-bridge.test.ts +++ b/src/app-bridge.test.ts @@ -901,9 +901,7 @@ describe("Content block modality validation", () => { // Should succeed even with image content since message capability is not declared const result = await app.sendMessage({ role: "user", - content: [ - { type: "image", data: "base64data", mimeType: "image/png" }, - ], + content: [{ type: "image", data: "base64data", mimeType: "image/png" }], }); expect(result).toEqual({}); }); @@ -1052,9 +1050,7 @@ describe("Content block modality validation", () => { await app.connect(appTransport); const result = await app.updateModelContext({ - content: [ - { type: "image", data: "base64data", mimeType: "image/png" }, - ], + content: [{ type: "image", data: "base64data", mimeType: "image/png" }], structuredContent: { key: "value" }, }); expect(result).toEqual({}); diff --git a/src/content-validation.test.ts b/src/content-validation.test.ts index b4174517..16e6bbf9 100644 --- a/src/content-validation.test.ts +++ b/src/content-validation.test.ts @@ -147,7 +147,11 @@ describe("validateContentModalities", () => { describe("buildValidationErrorMessage", () => { it("builds message for unsupported content types", () => { const msg = buildValidationErrorMessage( - { valid: false, unsupportedTypes: ["image", "audio"], structuredContentUnsupported: false }, + { + valid: false, + unsupportedTypes: ["image", "audio"], + structuredContentUnsupported: false, + }, "ui/message", ); expect(msg).toBe("ui/message: unsupported content type(s): image, audio"); @@ -155,15 +159,25 @@ describe("buildValidationErrorMessage", () => { it("builds message for unsupported structuredContent", () => { const msg = buildValidationErrorMessage( - { valid: false, unsupportedTypes: [], structuredContentUnsupported: true }, + { + valid: false, + unsupportedTypes: [], + structuredContentUnsupported: true, + }, "ui/update-model-context", ); - expect(msg).toBe("ui/update-model-context: structuredContent is not supported"); + expect(msg).toBe( + "ui/update-model-context: structuredContent is not supported", + ); }); it("builds message with both unsupported types and structuredContent", () => { const msg = buildValidationErrorMessage( - { valid: false, unsupportedTypes: ["image"], structuredContentUnsupported: true }, + { + valid: false, + unsupportedTypes: ["image"], + structuredContentUnsupported: true, + }, "ui/update-model-context", ); expect(msg).toBe( diff --git a/src/content-validation.ts b/src/content-validation.ts index bcfe4a13..a5bd9b63 100644 --- a/src/content-validation.ts +++ b/src/content-validation.ts @@ -5,7 +5,10 @@ import type { McpUiSupportedContentBlockModalities } from "./types"; * Maps a ContentBlock `type` to its corresponding modality key * in {@link McpUiSupportedContentBlockModalities}. */ -const CONTENT_TYPE_TO_MODALITY: Record = { +const CONTENT_TYPE_TO_MODALITY: Record< + string, + keyof McpUiSupportedContentBlockModalities | undefined +> = { text: "text", image: "image", audio: "audio", @@ -43,7 +46,11 @@ export function validateContentModalities( ): ContentValidationResult { // Backwards compatibility: if modalities is undefined, skip validation entirely if (modalities === undefined) { - return { valid: true, unsupportedTypes: [], structuredContentUnsupported: false }; + return { + valid: true, + unsupportedTypes: [], + structuredContentUnsupported: false, + }; } const unsupportedTypes = new Set(); @@ -52,7 +59,8 @@ export function validateContentModalities( // Check each content block if (content) { for (const block of content) { - const modalityKey = CONTENT_TYPE_TO_MODALITY[(block as { type: string }).type]; + const modalityKey = + CONTENT_TYPE_TO_MODALITY[(block as { type: string }).type]; if (modalityKey === undefined || !(modalityKey in modalities)) { unsupportedTypes.add((block as { type: string }).type); } @@ -85,7 +93,9 @@ export function buildValidationErrorMessage( ): string { const parts: string[] = []; if (result.unsupportedTypes.length > 0) { - parts.push(`unsupported content type(s): ${result.unsupportedTypes.join(", ")}`); + parts.push( + `unsupported content type(s): ${result.unsupportedTypes.join(", ")}`, + ); } if (result.structuredContentUnsupported) { parts.push("structuredContent is not supported"); From 901f1042b95be434ea0af460a752e6b2dfe6d0ad Mon Sep 17 00:00:00 2001 From: Ido Salomon Date: Fri, 23 Jan 2026 15:18:23 +0200 Subject: [PATCH 4/7] remove view-side validation --- src/app-bridge.test.ts | 276 ++--------------------------------------- src/app.ts | 26 ---- 2 files changed, 12 insertions(+), 290 deletions(-) diff --git a/src/app-bridge.test.ts b/src/app-bridge.test.ts index 5ef0b4a1..9df9c9a8 100644 --- a/src/app-bridge.test.ts +++ b/src/app-bridge.test.ts @@ -829,267 +829,27 @@ describe("Content block modality validation", () => { await bridgeTransport.close(); }); - describe("Guest-side validation (sendMessage)", () => { - it("throws when sending unsupported content type", async () => { + describe("Host-side validation", () => { + it("host rejects unsupported content in onmessage", async () => { [appTransport, bridgeTransport] = InMemoryTransport.createLinkedPair(); const capabilities: McpUiHostCapabilities = { ...testHostCapabilities, message: { text: {} }, }; - bridge = new AppBridge( - createMockClient() as Client, - testHostInfo, - capabilities, - ); + bridge = new AppBridge(null, testHostInfo, capabilities); bridge.onmessage = async () => ({}); app = new App(testAppInfo, {}, { autoResize: false }); await bridge.connect(bridgeTransport); await app.connect(appTransport); - expect(() => + await expect( app.sendMessage({ role: "user", content: [ { type: "image", data: "base64data", mimeType: "image/png" }, ], }), - ).toThrow("unsupported content type(s): image"); - }); - - it("allows content when modality is declared", async () => { - [appTransport, bridgeTransport] = InMemoryTransport.createLinkedPair(); - const capabilities: McpUiHostCapabilities = { - ...testHostCapabilities, - message: { text: {}, image: {} }, - }; - bridge = new AppBridge( - createMockClient() as Client, - testHostInfo, - capabilities, - ); - bridge.onmessage = async () => ({}); - app = new App(testAppInfo, {}, { autoResize: false }); - - await bridge.connect(bridgeTransport); - await app.connect(appTransport); - - const result = await app.sendMessage({ - role: "user", - content: [ - { type: "text", text: "hello" }, - { type: "image", data: "base64data", mimeType: "image/png" }, - ], - }); - expect(result).toEqual({}); - }); - - it("skips validation when message capability is not declared (backwards compat)", async () => { - [appTransport, bridgeTransport] = InMemoryTransport.createLinkedPair(); - // No message capability declared - bridge = new AppBridge( - createMockClient() as Client, - testHostInfo, - testHostCapabilities, - ); - bridge.onmessage = async () => ({}); - app = new App(testAppInfo, {}, { autoResize: false }); - - await bridge.connect(bridgeTransport); - await app.connect(appTransport); - - // Should succeed even with image content since message capability is not declared - const result = await app.sendMessage({ - role: "user", - content: [{ type: "image", data: "base64data", mimeType: "image/png" }], - }); - expect(result).toEqual({}); - }); - - it("rejects all types when message capability is empty object", async () => { - [appTransport, bridgeTransport] = InMemoryTransport.createLinkedPair(); - const capabilities: McpUiHostCapabilities = { - ...testHostCapabilities, - message: {}, - }; - bridge = new AppBridge( - createMockClient() as Client, - testHostInfo, - capabilities, - ); - bridge.onmessage = async () => ({}); - app = new App(testAppInfo, {}, { autoResize: false }); - - await bridge.connect(bridgeTransport); - await app.connect(appTransport); - - expect(() => - app.sendMessage({ - role: "user", - content: [{ type: "text", text: "hello" }], - }), - ).toThrow("unsupported content type(s): text"); - }); - - it("resource_link type maps to resourceLink modality correctly", async () => { - [appTransport, bridgeTransport] = InMemoryTransport.createLinkedPair(); - const capabilities: McpUiHostCapabilities = { - ...testHostCapabilities, - message: { resourceLink: {} }, - }; - bridge = new AppBridge( - createMockClient() as Client, - testHostInfo, - capabilities, - ); - bridge.onmessage = async () => ({}); - app = new App(testAppInfo, {}, { autoResize: false }); - - await bridge.connect(bridgeTransport); - await app.connect(appTransport); - - const result = await app.sendMessage({ - role: "user", - content: [ - { - type: "resource_link", - uri: "test://resource", - name: "Test Resource", - }, - ], - }); - expect(result).toEqual({}); - }); - }); - - describe("Guest-side validation (updateModelContext)", () => { - it("throws when sending unsupported content type", async () => { - [appTransport, bridgeTransport] = InMemoryTransport.createLinkedPair(); - const capabilities: McpUiHostCapabilities = { - ...testHostCapabilities, - updateModelContext: { text: {} }, - }; - bridge = new AppBridge( - createMockClient() as Client, - testHostInfo, - capabilities, - ); - bridge.onupdatemodelcontext = async () => ({}); - app = new App(testAppInfo, {}, { autoResize: false }); - - await bridge.connect(bridgeTransport); - await app.connect(appTransport); - - expect(() => - app.updateModelContext({ - content: [ - { type: "image", data: "base64data", mimeType: "image/png" }, - ], - }), - ).toThrow("unsupported content type(s): image"); - }); - - it("throws when sending structuredContent without capability", async () => { - [appTransport, bridgeTransport] = InMemoryTransport.createLinkedPair(); - const capabilities: McpUiHostCapabilities = { - ...testHostCapabilities, - updateModelContext: { text: {} }, - }; - bridge = new AppBridge( - createMockClient() as Client, - testHostInfo, - capabilities, - ); - bridge.onupdatemodelcontext = async () => ({}); - app = new App(testAppInfo, {}, { autoResize: false }); - - await bridge.connect(bridgeTransport); - await app.connect(appTransport); - - expect(() => - app.updateModelContext({ - structuredContent: { key: "value" }, - }), - ).toThrow("structuredContent is not supported"); - }); - - it("allows structuredContent when declared", async () => { - [appTransport, bridgeTransport] = InMemoryTransport.createLinkedPair(); - const capabilities: McpUiHostCapabilities = { - ...testHostCapabilities, - updateModelContext: { text: {}, structuredContent: {} }, - }; - bridge = new AppBridge( - createMockClient() as Client, - testHostInfo, - capabilities, - ); - bridge.onupdatemodelcontext = async () => ({}); - app = new App(testAppInfo, {}, { autoResize: false }); - - await bridge.connect(bridgeTransport); - await app.connect(appTransport); - - const result = await app.updateModelContext({ - structuredContent: { key: "value" }, - }); - expect(result).toEqual({}); - }); - - it("skips validation when updateModelContext capability is not declared", async () => { - [appTransport, bridgeTransport] = InMemoryTransport.createLinkedPair(); - bridge = new AppBridge( - createMockClient() as Client, - testHostInfo, - testHostCapabilities, - ); - bridge.onupdatemodelcontext = async () => ({}); - app = new App(testAppInfo, {}, { autoResize: false }); - - await bridge.connect(bridgeTransport); - await app.connect(appTransport); - - const result = await app.updateModelContext({ - content: [{ type: "image", data: "base64data", mimeType: "image/png" }], - structuredContent: { key: "value" }, - }); - expect(result).toEqual({}); - }); - }); - - describe("Host-side validation", () => { - it("host rejects unsupported content in onmessage", async () => { - [appTransport, bridgeTransport] = InMemoryTransport.createLinkedPair(); - const capabilities: McpUiHostCapabilities = { - ...testHostCapabilities, - message: { text: {} }, - }; - // Use null client so we don't get guest-side validation - // (the bridge still validates on the host side) - bridge = new AppBridge(null, testHostInfo, capabilities); - bridge.onmessage = async () => ({}); - - // Create app without host capabilities knowledge to bypass guest validation - app = new App(testAppInfo, {}, { autoResize: false }); - - await bridge.connect(bridgeTransport); - await app.connect(appTransport); - - // The app received capabilities during connect, so it will validate. - // To test host-side validation independently, we directly send the request. - await expect( - app.request( - { - method: "ui/message" as any, - params: { - role: "user", - content: [ - { type: "image", data: "base64data", mimeType: "image/png" }, - ], - }, - }, - EmptyResultSchema, - ), ).rejects.toThrow("unsupported content type(s): image"); }); @@ -1107,17 +867,11 @@ describe("Content block modality validation", () => { await app.connect(appTransport); await expect( - app.request( - { - method: "ui/update-model-context" as any, - params: { - content: [ - { type: "audio", data: "base64", mimeType: "audio/mp3" }, - ], - }, - }, - EmptyResultSchema, - ), + app.updateModelContext({ + content: [ + { type: "audio", data: "base64", mimeType: "audio/mp3" }, + ], + }), ).rejects.toThrow("unsupported content type(s): audio"); }); @@ -1135,15 +889,9 @@ describe("Content block modality validation", () => { await app.connect(appTransport); await expect( - app.request( - { - method: "ui/update-model-context" as any, - params: { - structuredContent: { key: "value" }, - }, - }, - EmptyResultSchema, - ), + app.updateModelContext({ + structuredContent: { key: "value" }, + }), ).rejects.toThrow("structuredContent is not supported"); }); }); diff --git a/src/app.ts b/src/app.ts index 67ad2402..9ef0af41 100644 --- a/src/app.ts +++ b/src/app.ts @@ -18,10 +18,6 @@ import { } from "@modelcontextprotocol/sdk/types.js"; import { AppNotification, AppRequest, AppResult } from "./types"; import { PostMessageTransport } from "./message-transport"; -import { - validateContentModalities, - buildValidationErrorMessage, -} from "./content-validation"; import { LATEST_PROTOCOL_VERSION, McpUiAppCapabilities, @@ -625,14 +621,6 @@ export class App extends Protocol { * @see {@link McpUiMessageRequest `McpUiMessageRequest`} for request structure */ sendMessage(params: McpUiMessageRequest["params"], options?: RequestOptions) { - const modalities = this._hostCapabilities?.message; - if (modalities !== undefined) { - const result = validateContentModalities(params.content, modalities); - if (!result.valid) { - throw new Error(buildValidationErrorMessage(result, "ui/message")); - } - } - return this.request( { method: "ui/message", @@ -691,20 +679,6 @@ export class App extends Protocol { params: McpUiUpdateModelContextRequest["params"], options?: RequestOptions, ) { - const modalities = this._hostCapabilities?.updateModelContext; - if (modalities !== undefined) { - const result = validateContentModalities( - params.content, - modalities, - params.structuredContent !== undefined, - ); - if (!result.valid) { - throw new Error( - buildValidationErrorMessage(result, "ui/update-model-context"), - ); - } - } - return this.request( { method: "ui/update-model-context", From 90e9c248e981bc1b75753a4e089b6d164a556ff5 Mon Sep 17 00:00:00 2001 From: Ido Salomon Date: Fri, 23 Jan 2026 15:18:36 +0200 Subject: [PATCH 5/7] husky --- src/app-bridge.test.ts | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/src/app-bridge.test.ts b/src/app-bridge.test.ts index 9df9c9a8..f8424aba 100644 --- a/src/app-bridge.test.ts +++ b/src/app-bridge.test.ts @@ -868,9 +868,7 @@ describe("Content block modality validation", () => { await expect( app.updateModelContext({ - content: [ - { type: "audio", data: "base64", mimeType: "audio/mp3" }, - ], + content: [{ type: "audio", data: "base64", mimeType: "audio/mp3" }], }), ).rejects.toThrow("unsupported content type(s): audio"); }); From 34697f0468cb35e2c49757bdde57a69ed5e4dfac Mon Sep 17 00:00:00 2001 From: Ido Salomon Date: Fri, 23 Jan 2026 15:21:44 +0200 Subject: [PATCH 6/7] update lock --- package-lock.json | 21 --------------------- 1 file changed, 21 deletions(-) diff --git a/package-lock.json b/package-lock.json index 74b952bd..6c94d64a 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1002,7 +1002,6 @@ "integrity": "sha512-H3mcG6ZDLTlYfaSNi0iOKkigqMFvkTKlGUYlD8GW7nNOYRrevuA46iTypPyv+06V3fEmvvazfntkBU34L0azAw==", "dev": true, "license": "MIT", - "peer": true, "dependencies": { "@babel/code-frame": "^7.28.6", "@babel/generator": "^7.28.6", @@ -3480,7 +3479,6 @@ "integrity": "sha512-Y1Cs7hhTc+a5E9Va/xwKlAJoariQyHY+5zBgCZg4PFWNYQ1nMN9sjK1zhw1gK69DuqVP++sht/1GZg1aRwmAXQ==", "dev": true, "license": "MIT", - "peer": true, "dependencies": { "@sveltejs/vite-plugin-svelte-inspector": "^4.0.1", "debug": "^4.4.1", @@ -3687,7 +3685,6 @@ "integrity": "sha512-powIePYMmC3ibL0UJ2i2s0WIbq6cg6UyVFQxSCpaPxxzAaziRfimGivjdF943sSGV6RADVbk0Nvlm5P/FB44Zg==", "dev": true, "license": "MIT", - "peer": true, "dependencies": { "undici-types": "~7.16.0" } @@ -3712,7 +3709,6 @@ "integrity": "sha512-3MbSL37jEchWZz2p2mjntRZtPt837ij10ApxKfgmXCTuHWagYg7iA5bqPw6C8BMPfwidlvfPI/fxOc42HLhcyg==", "dev": true, "license": "MIT", - "peer": true, "dependencies": { "csstype": "^3.2.2" } @@ -4115,7 +4111,6 @@ "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.15.0.tgz", "integrity": "sha512-NZyJarBfL7nWwIq+FDL6Zp/yHEhePMNnnJ0y3qfieCrmNvYct8uvtiV41UvlSe6apAfk0fY1FbWx+NwfmpvtTg==", "license": "MIT", - "peer": true, "bin": { "acorn": "bin/acorn" }, @@ -4441,7 +4436,6 @@ } ], "license": "MIT", - "peer": true, "dependencies": { "baseline-browser-mapping": "^2.9.0", "caniuse-lite": "^1.0.30001759", @@ -5153,7 +5147,6 @@ "integrity": "sha512-fmTRWbNMmsmWq6xJV8D19U/gw/bwrHfNXxrIN+HfZgnzqTHp9jOmKMhsTUjXOJnZOdZY9Q28y4yebKzqDKlxlQ==", "dev": true, "license": "ISC", - "peer": true, "engines": { "node": ">=12" } @@ -5638,7 +5631,6 @@ "resolved": "https://registry.npmjs.org/express/-/express-5.2.1.tgz", "integrity": "sha512-hIS4idWWai69NezIdRt2xFVofaF4j+6INOpJlVOLDO8zXGpUVEVzIYk12UUi2JzjEzWL3IOAxcTubgz9Po0yXw==", "license": "MIT", - "peer": true, "dependencies": { "accepts": "^2.0.0", "body-parser": "^2.2.1", @@ -7192,7 +7184,6 @@ "resolved": "https://registry.npmjs.org/preact/-/preact-10.28.2.tgz", "integrity": "sha512-lbteaWGzGHdlIuiJ0l2Jq454m6kcpI1zNje6d8MlGAFlYvP2GO4ibnat7P74Esfz4sPTdM6UxtTwh/d3pwM9JA==", "license": "MIT", - "peer": true, "funding": { "type": "opencollective", "url": "https://opencollective.com/preact" @@ -7288,7 +7279,6 @@ "resolved": "https://registry.npmjs.org/react/-/react-19.2.3.tgz", "integrity": "sha512-Ku/hhYbVjOQnXDZFv2+RibmLFGwFdeeKHFcOTlrt7xplBnya5OGn/hIRDsqDiSUcfORsDC7MPxwork8jBwsIWA==", "license": "MIT", - "peer": true, "engines": { "node": ">=0.10.0" } @@ -7387,7 +7377,6 @@ "integrity": "sha512-wDv/Ht1BNHB4upNbK74s9usvl7hObDnvVzknxqY/E/O3X6rW1U1rV1aENEfJ54eFZDTNo7zv1f5N4edCluH7+A==", "dev": true, "license": "MIT", - "peer": true, "dependencies": { "@types/estree": "1.0.8" }, @@ -7509,7 +7498,6 @@ "resolved": "https://registry.npmjs.org/seroval/-/seroval-1.3.2.tgz", "integrity": "sha512-RbcPH1n5cfwKrru7v7+zrZvjLurgHhGyso3HTyGtRivGWgYjbOmGuivCQaORNELjNONoK35nj28EoWul9sb1zQ==", "license": "MIT", - "peer": true, "engines": { "node": ">=10" } @@ -7800,7 +7788,6 @@ "resolved": "https://registry.npmjs.org/solid-js/-/solid-js-1.9.10.tgz", "integrity": "sha512-Coz956cos/EPDlhs6+jsdTxKuJDPT7B5SVIWgABwROyxjY7Xbr8wkzD68Et+NxnV7DLJ3nJdAC2r9InuV/4Jew==", "license": "MIT", - "peer": true, "dependencies": { "csstype": "^3.1.0", "seroval": "~1.3.0", @@ -7979,7 +7966,6 @@ "resolved": "https://registry.npmjs.org/svelte/-/svelte-5.46.4.tgz", "integrity": "sha512-VJwdXrmv9L8L7ZasJeWcCjoIuMRVbhuxbss0fpVnR8yorMmjNDwcjIH08vS6wmSzzzgAG5CADQ1JuXPS2nwt9w==", "license": "MIT", - "peer": true, "dependencies": { "@jridgewell/remapping": "^2.3.4", "@jridgewell/sourcemap-codec": "^1.5.0", @@ -8307,7 +8293,6 @@ "integrity": "sha512-5gTmgEY/sqK6gFXLIsQNH19lWb4ebPDLA4SdLP7dsWkIXHWlG66oPuVvXSGFPppYZz8ZDZq0dYYrbHfBCVUb1Q==", "dev": true, "license": "MIT", - "peer": true, "engines": { "node": ">=12" }, @@ -9070,7 +9055,6 @@ "integrity": "sha512-jl1vZzPDinLr9eUt3J/t7V6FgNEw9QjvBPdysz9KfQDD41fQrC2Y4vKQdiaUpFT4bXlb1RHhLpp8wtm6M5TgSw==", "devOptional": true, "license": "Apache-2.0", - "peer": true, "bin": { "tsc": "bin/tsc", "tsserver": "bin/tsserver" @@ -9164,7 +9148,6 @@ "integrity": "sha512-+Oxm7q9hDoLMyJOYfUYBuHQo+dkAloi33apOPP56pzj+vsdJDzr+j1NISE5pyaAuKL4A3UD34qd0lx5+kfKp2g==", "dev": true, "license": "MIT", - "peer": true, "dependencies": { "esbuild": "^0.25.0", "fdir": "^6.4.4", @@ -9341,7 +9324,6 @@ "integrity": "sha512-5gTmgEY/sqK6gFXLIsQNH19lWb4ebPDLA4SdLP7dsWkIXHWlG66oPuVvXSGFPppYZz8ZDZq0dYYrbHfBCVUb1Q==", "dev": true, "license": "MIT", - "peer": true, "engines": { "node": ">=12" }, @@ -9460,7 +9442,6 @@ "resolved": "https://registry.npmjs.org/vue/-/vue-3.5.26.tgz", "integrity": "sha512-SJ/NTccVyAoNUJmkM9KUqPcYlY+u8OVL1X5EW9RIs3ch5H2uERxyyIUI4MRxVCSOiEcupX9xNGde1tL9ZKpimA==", "license": "MIT", - "peer": true, "dependencies": { "@vue/compiler-dom": "3.5.26", "@vue/compiler-sfc": "3.5.26", @@ -9633,7 +9614,6 @@ "integrity": "sha512-mplynKqc1C2hTVYxd0PU2xQAc22TI1vShAYGksCCfxbn/dFwnHTNi1bvYsBTkhdUNtGIf5xNOg938rrSSYvS9A==", "dev": true, "license": "ISC", - "peer": true, "bin": { "yaml": "bin.mjs" }, @@ -9684,7 +9664,6 @@ "resolved": "https://registry.npmjs.org/zod/-/zod-4.3.5.tgz", "integrity": "sha512-k7Nwx6vuWx1IJ9Bjuf4Zt1PEllcwe7cls3VNzm4CQ1/hgtFUK2bRNG3rvnpPUhFjmqJKAKtjV576KnUkHocg/g==", "license": "MIT", - "peer": true, "funding": { "url": "https://github.com/sponsors/colinhacks" } From 94c432bcb93d8fed6c2daee3402b08ef77088255 Mon Sep 17 00:00:00 2001 From: Ido Salomon Date: Fri, 23 Jan 2026 15:41:20 +0200 Subject: [PATCH 7/7] chore: update package-lock.json to sync with dependencies Fixes npm ci failures in CI by updating lock file to match current dependency tree. Updates hono from 4.11.4 to 4.11.5 and @modelcontextprotocol/sdk to 1.25.3. --- package-lock.json | 757 +++++++++++++++++++++++----------------------- 1 file changed, 378 insertions(+), 379 deletions(-) diff --git a/package-lock.json b/package-lock.json index 6c94d64a..77ee0b9d 100644 --- a/package-lock.json +++ b/package-lock.json @@ -106,8 +106,6 @@ }, "examples/basic-host/node_modules/undici-types": { "version": "6.21.0", - "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-6.21.0.tgz", - "integrity": "sha512-iwDZqg0QAGrg9Rav5H4n0M64c3mkR59cJ6wQp+7C4nI0gsmExaedaYLNO44eT4AtBBwjbTiGPMlt2Md0T9H9JQ==", "dev": true, "license": "MIT" }, @@ -148,8 +146,6 @@ }, "examples/basic-server-preact/node_modules/undici-types": { "version": "6.21.0", - "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-6.21.0.tgz", - "integrity": "sha512-iwDZqg0QAGrg9Rav5H4n0M64c3mkR59cJ6wQp+7C4nI0gsmExaedaYLNO44eT4AtBBwjbTiGPMlt2Md0T9H9JQ==", "dev": true, "license": "MIT" }, @@ -193,8 +189,6 @@ }, "examples/basic-server-react/node_modules/undici-types": { "version": "6.21.0", - "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-6.21.0.tgz", - "integrity": "sha512-iwDZqg0QAGrg9Rav5H4n0M64c3mkR59cJ6wQp+7C4nI0gsmExaedaYLNO44eT4AtBBwjbTiGPMlt2Md0T9H9JQ==", "dev": true, "license": "MIT" }, @@ -235,8 +229,6 @@ }, "examples/basic-server-solid/node_modules/undici-types": { "version": "6.21.0", - "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-6.21.0.tgz", - "integrity": "sha512-iwDZqg0QAGrg9Rav5H4n0M64c3mkR59cJ6wQp+7C4nI0gsmExaedaYLNO44eT4AtBBwjbTiGPMlt2Md0T9H9JQ==", "dev": true, "license": "MIT" }, @@ -277,8 +269,6 @@ }, "examples/basic-server-svelte/node_modules/undici-types": { "version": "6.21.0", - "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-6.21.0.tgz", - "integrity": "sha512-iwDZqg0QAGrg9Rav5H4n0M64c3mkR59cJ6wQp+7C4nI0gsmExaedaYLNO44eT4AtBBwjbTiGPMlt2Md0T9H9JQ==", "dev": true, "license": "MIT" }, @@ -317,8 +307,6 @@ }, "examples/basic-server-vanillajs/node_modules/undici-types": { "version": "6.21.0", - "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-6.21.0.tgz", - "integrity": "sha512-iwDZqg0QAGrg9Rav5H4n0M64c3mkR59cJ6wQp+7C4nI0gsmExaedaYLNO44eT4AtBBwjbTiGPMlt2Md0T9H9JQ==", "dev": true, "license": "MIT" }, @@ -359,8 +347,6 @@ }, "examples/basic-server-vue/node_modules/undici-types": { "version": "6.21.0", - "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-6.21.0.tgz", - "integrity": "sha512-iwDZqg0QAGrg9Rav5H4n0M64c3mkR59cJ6wQp+7C4nI0gsmExaedaYLNO44eT4AtBBwjbTiGPMlt2Md0T9H9JQ==", "dev": true, "license": "MIT" }, @@ -400,8 +386,6 @@ }, "examples/budget-allocator-server/node_modules/undici-types": { "version": "6.21.0", - "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-6.21.0.tgz", - "integrity": "sha512-iwDZqg0QAGrg9Rav5H4n0M64c3mkR59cJ6wQp+7C4nI0gsmExaedaYLNO44eT4AtBBwjbTiGPMlt2Md0T9H9JQ==", "dev": true, "license": "MIT" }, @@ -445,8 +429,6 @@ }, "examples/cohort-heatmap-server/node_modules/undici-types": { "version": "6.21.0", - "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-6.21.0.tgz", - "integrity": "sha512-iwDZqg0QAGrg9Rav5H4n0M64c3mkR59cJ6wQp+7C4nI0gsmExaedaYLNO44eT4AtBBwjbTiGPMlt2Md0T9H9JQ==", "dev": true, "license": "MIT" }, @@ -486,8 +468,6 @@ }, "examples/customer-segmentation-server/node_modules/undici-types": { "version": "6.21.0", - "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-6.21.0.tgz", - "integrity": "sha512-iwDZqg0QAGrg9Rav5H4n0M64c3mkR59cJ6wQp+7C4nI0gsmExaedaYLNO44eT4AtBBwjbTiGPMlt2Md0T9H9JQ==", "dev": true, "license": "MIT" }, @@ -528,8 +508,6 @@ }, "examples/integration-server/node_modules/undici-types": { "version": "6.21.0", - "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-6.21.0.tgz", - "integrity": "sha512-iwDZqg0QAGrg9Rav5H4n0M64c3mkR59cJ6wQp+7C4nI0gsmExaedaYLNO44eT4AtBBwjbTiGPMlt2Md0T9H9JQ==", "dev": true, "license": "MIT" }, @@ -568,8 +546,6 @@ }, "examples/map-server/node_modules/undici-types": { "version": "6.21.0", - "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-6.21.0.tgz", - "integrity": "sha512-iwDZqg0QAGrg9Rav5H4n0M64c3mkR59cJ6wQp+7C4nI0gsmExaedaYLNO44eT4AtBBwjbTiGPMlt2Md0T9H9JQ==", "dev": true, "license": "MIT" }, @@ -609,8 +585,6 @@ }, "examples/pdf-server/node_modules/undici-types": { "version": "6.21.0", - "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-6.21.0.tgz", - "integrity": "sha512-iwDZqg0QAGrg9Rav5H4n0M64c3mkR59cJ6wQp+7C4nI0gsmExaedaYLNO44eT4AtBBwjbTiGPMlt2Md0T9H9JQ==", "dev": true, "license": "MIT" }, @@ -664,8 +638,6 @@ }, "examples/scenario-modeler-server/node_modules/undici-types": { "version": "6.21.0", - "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-6.21.0.tgz", - "integrity": "sha512-iwDZqg0QAGrg9Rav5H4n0M64c3mkR59cJ6wQp+7C4nI0gsmExaedaYLNO44eT4AtBBwjbTiGPMlt2Md0T9H9JQ==", "dev": true, "license": "MIT" }, @@ -704,8 +676,6 @@ }, "examples/shadertoy-server/node_modules/undici-types": { "version": "6.21.0", - "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-6.21.0.tgz", - "integrity": "sha512-iwDZqg0QAGrg9Rav5H4n0M64c3mkR59cJ6wQp+7C4nI0gsmExaedaYLNO44eT4AtBBwjbTiGPMlt2Md0T9H9JQ==", "dev": true, "license": "MIT" }, @@ -745,8 +715,6 @@ }, "examples/sheet-music-server/node_modules/undici-types": { "version": "6.21.0", - "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-6.21.0.tgz", - "integrity": "sha512-iwDZqg0QAGrg9Rav5H4n0M64c3mkR59cJ6wQp+7C4nI0gsmExaedaYLNO44eT4AtBBwjbTiGPMlt2Md0T9H9JQ==", "dev": true, "license": "MIT" }, @@ -787,8 +755,6 @@ }, "examples/system-monitor-server/node_modules/undici-types": { "version": "6.21.0", - "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-6.21.0.tgz", - "integrity": "sha512-iwDZqg0QAGrg9Rav5H4n0M64c3mkR59cJ6wQp+7C4nI0gsmExaedaYLNO44eT4AtBBwjbTiGPMlt2Md0T9H9JQ==", "dev": true, "license": "MIT" }, @@ -834,8 +800,6 @@ }, "examples/threejs-server/node_modules/undici-types": { "version": "6.21.0", - "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-6.21.0.tgz", - "integrity": "sha512-iwDZqg0QAGrg9Rav5H4n0M64c3mkR59cJ6wQp+7C4nI0gsmExaedaYLNO44eT4AtBBwjbTiGPMlt2Md0T9H9JQ==", "dev": true, "license": "MIT" }, @@ -875,15 +839,11 @@ }, "examples/transcript-server/node_modules/undici-types": { "version": "6.21.0", - "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-6.21.0.tgz", - "integrity": "sha512-iwDZqg0QAGrg9Rav5H4n0M64c3mkR59cJ6wQp+7C4nI0gsmExaedaYLNO44eT4AtBBwjbTiGPMlt2Md0T9H9JQ==", "dev": true, "license": "MIT" }, "examples/transcript-server/node_modules/zod": { "version": "3.25.76", - "resolved": "https://registry.npmjs.org/zod/-/zod-3.25.76.tgz", - "integrity": "sha512-gzUt/qt81nXsFGKIFcC3YnfEAx5NkunCfnDlvuBSSFS02bcXu4Lmea0AFIUwbLWxWPx3d9p8S5QoaujKcNQxcQ==", "license": "MIT", "funding": { "url": "https://github.com/sponsors/colinhacks" @@ -924,8 +884,6 @@ }, "examples/video-resource-server/node_modules/undici-types": { "version": "6.21.0", - "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-6.21.0.tgz", - "integrity": "sha512-iwDZqg0QAGrg9Rav5H4n0M64c3mkR59cJ6wQp+7C4nI0gsmExaedaYLNO44eT4AtBBwjbTiGPMlt2Md0T9H9JQ==", "dev": true, "license": "MIT" }, @@ -966,8 +924,6 @@ }, "examples/wiki-explorer-server/node_modules/undici-types": { "version": "6.21.0", - "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-6.21.0.tgz", - "integrity": "sha512-iwDZqg0QAGrg9Rav5H4n0M64c3mkR59cJ6wQp+7C4nI0gsmExaedaYLNO44eT4AtBBwjbTiGPMlt2Md0T9H9JQ==", "dev": true, "license": "MIT" }, @@ -2392,20 +2348,59 @@ "license": "MIT" }, "node_modules/@modelcontextprotocol/ext-apps": { - "resolved": "", - "link": true + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/@modelcontextprotocol/ext-apps/-/ext-apps-0.4.1.tgz", + "integrity": "sha512-LUw6NidwWInzWVF8OSPw/Mtdz5ES2qF+yBze2h+WRARdSbXf+agTkZLCGFtdkogI64W6mDlJnSTp/k5W+FZ84A==", + "hasInstallScript": true, + "license": "MIT", + "workspaces": [ + "examples/*" + ], + "optionalDependencies": { + "@oven/bun-darwin-aarch64": "^1.2.21", + "@oven/bun-darwin-x64": "^1.2.21", + "@oven/bun-darwin-x64-baseline": "^1.2.21", + "@oven/bun-linux-aarch64": "^1.2.21", + "@oven/bun-linux-aarch64-musl": "^1.2.21", + "@oven/bun-linux-x64": "^1.2.21", + "@oven/bun-linux-x64-baseline": "^1.2.21", + "@oven/bun-linux-x64-musl": "^1.2.21", + "@oven/bun-linux-x64-musl-baseline": "^1.2.21", + "@oven/bun-windows-x64": "^1.2.21", + "@oven/bun-windows-x64-baseline": "^1.2.21", + "@rollup/rollup-darwin-arm64": "^4.53.3", + "@rollup/rollup-darwin-x64": "^4.53.3", + "@rollup/rollup-linux-arm64-gnu": "^4.53.3", + "@rollup/rollup-linux-x64-gnu": "^4.53.3", + "@rollup/rollup-win32-arm64-msvc": "^4.53.3", + "@rollup/rollup-win32-x64-msvc": "^4.53.3" + }, + "peerDependencies": { + "@modelcontextprotocol/sdk": "^1.24.0", + "react": "^17.0.0 || ^18.0.0 || ^19.0.0", + "react-dom": "^17.0.0 || ^18.0.0 || ^19.0.0", + "zod": "^3.25.0 || ^4.0.0" + }, + "peerDependenciesMeta": { + "react": { + "optional": true + }, + "react-dom": { + "optional": true + } + } }, "node_modules/@modelcontextprotocol/ext-apps-basic-host": { "resolved": "examples/basic-host", "link": true }, "node_modules/@modelcontextprotocol/sdk": { - "version": "1.25.2", - "resolved": "https://registry.npmjs.org/@modelcontextprotocol/sdk/-/sdk-1.25.2.tgz", - "integrity": "sha512-LZFeo4F9M5qOhC/Uc1aQSrBHxMrvxett+9KLHt7OhcExtoiRN9DKgbZffMP/nxjutWDQpfMDfP3nkHI4X9ijww==", + "version": "1.25.3", + "resolved": "https://registry.npmjs.org/@modelcontextprotocol/sdk/-/sdk-1.25.3.tgz", + "integrity": "sha512-vsAMBMERybvYgKbg/l4L1rhS7VXV1c0CtyJg72vwxONVX0l4ZfKVAnZEWTQixJGTzKnELjQ59e4NbdFDALRiAQ==", "license": "MIT", "dependencies": { - "@hono/node-server": "^1.19.7", + "@hono/node-server": "^1.19.9", "ajv": "^8.17.1", "ajv-formats": "^3.0.1", "content-type": "^1.0.5", @@ -2972,13 +2967,13 @@ ] }, "node_modules/@playwright/test": { - "version": "1.57.0", - "resolved": "https://registry.npmjs.org/@playwright/test/-/test-1.57.0.tgz", - "integrity": "sha512-6TyEnHgd6SArQO8UO2OMTxshln3QMWBtPGrOCgs3wVEmQmwyuNtB10IZMfmYDE0riwNR1cu4q+pPcxMVtaG3TA==", + "version": "1.58.0", + "resolved": "https://registry.npmjs.org/@playwright/test/-/test-1.58.0.tgz", + "integrity": "sha512-fWza+Lpbj6SkQKCrU6si4iu+fD2dD3gxNHFhUPxsfXBPhnv3rRSQVd0NtBUT9Z/RhF/boCBcuUaMUSTRTopjZg==", "dev": true, "license": "Apache-2.0", "dependencies": { - "playwright": "1.57.0" + "playwright": "1.58.0" }, "bin": { "playwright": "cli.js" @@ -3072,9 +3067,9 @@ } }, "node_modules/@rollup/rollup-android-arm-eabi": { - "version": "4.55.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm-eabi/-/rollup-android-arm-eabi-4.55.1.tgz", - "integrity": "sha512-9R0DM/ykwfGIlNu6+2U09ga0WXeZ9MRC2Ter8jnz8415VbuIykVuc6bhdrbORFZANDmTDvq26mJrEVTl8TdnDg==", + "version": "4.56.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm-eabi/-/rollup-android-arm-eabi-4.56.0.tgz", + "integrity": "sha512-LNKIPA5k8PF1+jAFomGe3qN3bbIgJe/IlpDBwuVjrDKrJhVWywgnJvflMt/zkbVNLFtF1+94SljYQS6e99klnw==", "cpu": [ "arm" ], @@ -3086,9 +3081,9 @@ ] }, "node_modules/@rollup/rollup-android-arm64": { - "version": "4.55.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm64/-/rollup-android-arm64-4.55.1.tgz", - "integrity": "sha512-eFZCb1YUqhTysgW3sj/55du5cG57S7UTNtdMjCW7LwVcj3dTTcowCsC8p7uBdzKsZYa8J7IDE8lhMI+HX1vQvg==", + "version": "4.56.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm64/-/rollup-android-arm64-4.56.0.tgz", + "integrity": "sha512-lfbVUbelYqXlYiU/HApNMJzT1E87UPGvzveGg2h0ktUNlOCxKlWuJ9jtfvs1sKHdwU4fzY7Pl8sAl49/XaEk6Q==", "cpu": [ "arm64" ], @@ -3100,9 +3095,9 @@ ] }, "node_modules/@rollup/rollup-darwin-arm64": { - "version": "4.55.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-arm64/-/rollup-darwin-arm64-4.55.1.tgz", - "integrity": "sha512-p3grE2PHcQm2e8PSGZdzIhCKbMCw/xi9XvMPErPhwO17vxtvCN5FEA2mSLgmKlCjHGMQTP6phuQTYWUnKewwGg==", + "version": "4.56.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-arm64/-/rollup-darwin-arm64-4.56.0.tgz", + "integrity": "sha512-EgxD1ocWfhoD6xSOeEEwyE7tDvwTgZc8Bss7wCWe+uc7wO8G34HHCUH+Q6cHqJubxIAnQzAsyUsClt0yFLu06w==", "cpu": [ "arm64" ], @@ -3113,9 +3108,9 @@ ] }, "node_modules/@rollup/rollup-darwin-x64": { - "version": "4.55.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-x64/-/rollup-darwin-x64-4.55.1.tgz", - "integrity": "sha512-rDUjG25C9qoTm+e02Esi+aqTKSBYwVTaoS1wxcN47/Luqef57Vgp96xNANwt5npq9GDxsH7kXxNkJVEsWEOEaQ==", + "version": "4.56.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-x64/-/rollup-darwin-x64-4.56.0.tgz", + "integrity": "sha512-1vXe1vcMOssb/hOF8iv52A7feWW2xnu+c8BV4t1F//m9QVLTfNVpEdja5ia762j/UEJe2Z1jAmEqZAK42tVW3g==", "cpu": [ "x64" ], @@ -3126,9 +3121,9 @@ ] }, "node_modules/@rollup/rollup-freebsd-arm64": { - "version": "4.55.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-arm64/-/rollup-freebsd-arm64-4.55.1.tgz", - "integrity": "sha512-+JiU7Jbp5cdxekIgdte0jfcu5oqw4GCKr6i3PJTlXTCU5H5Fvtkpbs4XJHRmWNXF+hKmn4v7ogI5OQPaupJgOg==", + "version": "4.56.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-arm64/-/rollup-freebsd-arm64-4.56.0.tgz", + "integrity": "sha512-bof7fbIlvqsyv/DtaXSck4VYQ9lPtoWNFCB/JY4snlFuJREXfZnm+Ej6yaCHfQvofJDXLDMTVxWscVSuQvVWUQ==", "cpu": [ "arm64" ], @@ -3140,9 +3135,9 @@ ] }, "node_modules/@rollup/rollup-freebsd-x64": { - "version": "4.55.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-x64/-/rollup-freebsd-x64-4.55.1.tgz", - "integrity": "sha512-V5xC1tOVWtLLmr3YUk2f6EJK4qksksOYiz/TCsFHu/R+woubcLWdC9nZQmwjOAbmExBIVKsm1/wKmEy4z4u4Bw==", + "version": "4.56.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-x64/-/rollup-freebsd-x64-4.56.0.tgz", + "integrity": "sha512-KNa6lYHloW+7lTEkYGa37fpvPq+NKG/EHKM8+G/g9WDU7ls4sMqbVRV78J6LdNuVaeeK5WB9/9VAFbKxcbXKYg==", "cpu": [ "x64" ], @@ -3154,9 +3149,9 @@ ] }, "node_modules/@rollup/rollup-linux-arm-gnueabihf": { - "version": "4.55.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-gnueabihf/-/rollup-linux-arm-gnueabihf-4.55.1.tgz", - "integrity": "sha512-Rn3n+FUk2J5VWx+ywrG/HGPTD9jXNbicRtTM11e/uorplArnXZYsVifnPPqNNP5BsO3roI4n8332ukpY/zN7rQ==", + "version": "4.56.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-gnueabihf/-/rollup-linux-arm-gnueabihf-4.56.0.tgz", + "integrity": "sha512-E8jKK87uOvLrrLN28jnAAAChNq5LeCd2mGgZF+fGF5D507WlG/Noct3lP/QzQ6MrqJ5BCKNwI9ipADB6jyiq2A==", "cpu": [ "arm" ], @@ -3168,9 +3163,9 @@ ] }, "node_modules/@rollup/rollup-linux-arm-musleabihf": { - "version": "4.55.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-musleabihf/-/rollup-linux-arm-musleabihf-4.55.1.tgz", - "integrity": "sha512-grPNWydeKtc1aEdrJDWk4opD7nFtQbMmV7769hiAaYyUKCT1faPRm2av8CX1YJsZ4TLAZcg9gTR1KvEzoLjXkg==", + "version": "4.56.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-musleabihf/-/rollup-linux-arm-musleabihf-4.56.0.tgz", + "integrity": "sha512-jQosa5FMYF5Z6prEpTCCmzCXz6eKr/tCBssSmQGEeozA9tkRUty/5Vx06ibaOP9RCrW1Pvb8yp3gvZhHwTDsJw==", "cpu": [ "arm" ], @@ -3182,9 +3177,9 @@ ] }, "node_modules/@rollup/rollup-linux-arm64-gnu": { - "version": "4.55.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-gnu/-/rollup-linux-arm64-gnu-4.55.1.tgz", - "integrity": "sha512-a59mwd1k6x8tXKcUxSyISiquLwB5pX+fJW9TkWU46lCqD/GRDe9uDN31jrMmVP3feI3mhAdvcCClhV8V5MhJFQ==", + "version": "4.56.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-gnu/-/rollup-linux-arm64-gnu-4.56.0.tgz", + "integrity": "sha512-uQVoKkrC1KGEV6udrdVahASIsaF8h7iLG0U0W+Xn14ucFwi6uS539PsAr24IEF9/FoDtzMeeJXJIBo5RkbNWvQ==", "cpu": [ "arm64" ], @@ -3195,9 +3190,9 @@ ] }, "node_modules/@rollup/rollup-linux-arm64-musl": { - "version": "4.55.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-musl/-/rollup-linux-arm64-musl-4.55.1.tgz", - "integrity": "sha512-puS1MEgWX5GsHSoiAsF0TYrpomdvkaXm0CofIMG5uVkP6IBV+ZO9xhC5YEN49nsgYo1DuuMquF9+7EDBVYu4uA==", + "version": "4.56.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-musl/-/rollup-linux-arm64-musl-4.56.0.tgz", + "integrity": "sha512-vLZ1yJKLxhQLFKTs42RwTwa6zkGln+bnXc8ueFGMYmBTLfNu58sl5/eXyxRa2RarTkJbXl8TKPgfS6V5ijNqEA==", "cpu": [ "arm64" ], @@ -3209,9 +3204,9 @@ ] }, "node_modules/@rollup/rollup-linux-loong64-gnu": { - "version": "4.55.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-loong64-gnu/-/rollup-linux-loong64-gnu-4.55.1.tgz", - "integrity": "sha512-r3Wv40in+lTsULSb6nnoudVbARdOwb2u5fpeoOAZjFLznp6tDU8kd+GTHmJoqZ9lt6/Sys33KdIHUaQihFcu7g==", + "version": "4.56.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-loong64-gnu/-/rollup-linux-loong64-gnu-4.56.0.tgz", + "integrity": "sha512-FWfHOCub564kSE3xJQLLIC/hbKqHSVxy8vY75/YHHzWvbJL7aYJkdgwD/xGfUlL5UV2SB7otapLrcCj2xnF1dg==", "cpu": [ "loong64" ], @@ -3223,9 +3218,9 @@ ] }, "node_modules/@rollup/rollup-linux-loong64-musl": { - "version": "4.55.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-loong64-musl/-/rollup-linux-loong64-musl-4.55.1.tgz", - "integrity": "sha512-MR8c0+UxAlB22Fq4R+aQSPBayvYa3+9DrwG/i1TKQXFYEaoW3B5b/rkSRIypcZDdWjWnpcvxbNaAJDcSbJU3Lw==", + "version": "4.56.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-loong64-musl/-/rollup-linux-loong64-musl-4.56.0.tgz", + "integrity": "sha512-z1EkujxIh7nbrKL1lmIpqFTc/sr0u8Uk0zK/qIEFldbt6EDKWFk/pxFq3gYj4Bjn3aa9eEhYRlL3H8ZbPT1xvA==", "cpu": [ "loong64" ], @@ -3237,9 +3232,9 @@ ] }, "node_modules/@rollup/rollup-linux-ppc64-gnu": { - "version": "4.55.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-ppc64-gnu/-/rollup-linux-ppc64-gnu-4.55.1.tgz", - "integrity": "sha512-3KhoECe1BRlSYpMTeVrD4sh2Pw2xgt4jzNSZIIPLFEsnQn9gAnZagW9+VqDqAHgm1Xc77LzJOo2LdigS5qZ+gw==", + "version": "4.56.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-ppc64-gnu/-/rollup-linux-ppc64-gnu-4.56.0.tgz", + "integrity": "sha512-iNFTluqgdoQC7AIE8Q34R3AuPrJGJirj5wMUErxj22deOcY7XwZRaqYmB6ZKFHoVGqRcRd0mqO+845jAibKCkw==", "cpu": [ "ppc64" ], @@ -3251,9 +3246,9 @@ ] }, "node_modules/@rollup/rollup-linux-ppc64-musl": { - "version": "4.55.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-ppc64-musl/-/rollup-linux-ppc64-musl-4.55.1.tgz", - "integrity": "sha512-ziR1OuZx0vdYZZ30vueNZTg73alF59DicYrPViG0NEgDVN8/Jl87zkAPu4u6VjZST2llgEUjaiNl9JM6HH1Vdw==", + "version": "4.56.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-ppc64-musl/-/rollup-linux-ppc64-musl-4.56.0.tgz", + "integrity": "sha512-MtMeFVlD2LIKjp2sE2xM2slq3Zxf9zwVuw0jemsxvh1QOpHSsSzfNOTH9uYW9i1MXFxUSMmLpeVeUzoNOKBaWg==", "cpu": [ "ppc64" ], @@ -3265,9 +3260,9 @@ ] }, "node_modules/@rollup/rollup-linux-riscv64-gnu": { - "version": "4.55.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-gnu/-/rollup-linux-riscv64-gnu-4.55.1.tgz", - "integrity": "sha512-uW0Y12ih2XJRERZ4jAfKamTyIHVMPQnTZcQjme2HMVDAHY4amf5u414OqNYC+x+LzRdRcnIG1YodLrrtA8xsxw==", + "version": "4.56.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-gnu/-/rollup-linux-riscv64-gnu-4.56.0.tgz", + "integrity": "sha512-in+v6wiHdzzVhYKXIk5U74dEZHdKN9KH0Q4ANHOTvyXPG41bajYRsy7a8TPKbYPl34hU7PP7hMVHRvv/5aCSew==", "cpu": [ "riscv64" ], @@ -3279,9 +3274,9 @@ ] }, "node_modules/@rollup/rollup-linux-riscv64-musl": { - "version": "4.55.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-musl/-/rollup-linux-riscv64-musl-4.55.1.tgz", - "integrity": "sha512-u9yZ0jUkOED1BFrqu3BwMQoixvGHGZ+JhJNkNKY/hyoEgOwlqKb62qu+7UjbPSHYjiVy8kKJHvXKv5coH4wDeg==", + "version": "4.56.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-musl/-/rollup-linux-riscv64-musl-4.56.0.tgz", + "integrity": "sha512-yni2raKHB8m9NQpI9fPVwN754mn6dHQSbDTwxdr9SE0ks38DTjLMMBjrwvB5+mXrX+C0npX0CVeCUcvvvD8CNQ==", "cpu": [ "riscv64" ], @@ -3293,9 +3288,9 @@ ] }, "node_modules/@rollup/rollup-linux-s390x-gnu": { - "version": "4.55.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-s390x-gnu/-/rollup-linux-s390x-gnu-4.55.1.tgz", - "integrity": "sha512-/0PenBCmqM4ZUd0190j7J0UsQ/1nsi735iPRakO8iPciE7BQ495Y6msPzaOmvx0/pn+eJVVlZrNrSh4WSYLxNg==", + "version": "4.56.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-s390x-gnu/-/rollup-linux-s390x-gnu-4.56.0.tgz", + "integrity": "sha512-zhLLJx9nQPu7wezbxt2ut+CI4YlXi68ndEve16tPc/iwoylWS9B3FxpLS2PkmfYgDQtosah07Mj9E0khc3Y+vQ==", "cpu": [ "s390x" ], @@ -3307,9 +3302,9 @@ ] }, "node_modules/@rollup/rollup-linux-x64-gnu": { - "version": "4.55.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-gnu/-/rollup-linux-x64-gnu-4.55.1.tgz", - "integrity": "sha512-a8G4wiQxQG2BAvo+gU6XrReRRqj+pLS2NGXKm8io19goR+K8lw269eTrPkSdDTALwMmJp4th2Uh0D8J9bEV1vg==", + "version": "4.56.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-gnu/-/rollup-linux-x64-gnu-4.56.0.tgz", + "integrity": "sha512-MVC6UDp16ZSH7x4rtuJPAEoE1RwS8N4oK9DLHy3FTEdFoUTCFVzMfJl/BVJ330C+hx8FfprA5Wqx4FhZXkj2Kw==", "cpu": [ "x64" ], @@ -3320,9 +3315,9 @@ ] }, "node_modules/@rollup/rollup-linux-x64-musl": { - "version": "4.55.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-musl/-/rollup-linux-x64-musl-4.55.1.tgz", - "integrity": "sha512-bD+zjpFrMpP/hqkfEcnjXWHMw5BIghGisOKPj+2NaNDuVT+8Ds4mPf3XcPHuat1tz89WRL+1wbcxKY3WSbiT7w==", + "version": "4.56.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-musl/-/rollup-linux-x64-musl-4.56.0.tgz", + "integrity": "sha512-ZhGH1eA4Qv0lxaV00azCIS1ChedK0V32952Md3FtnxSqZTBTd6tgil4nZT5cU8B+SIw3PFYkvyR4FKo2oyZIHA==", "cpu": [ "x64" ], @@ -3334,9 +3329,9 @@ ] }, "node_modules/@rollup/rollup-openbsd-x64": { - "version": "4.55.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-openbsd-x64/-/rollup-openbsd-x64-4.55.1.tgz", - "integrity": "sha512-eLXw0dOiqE4QmvikfQ6yjgkg/xDM+MdU9YJuP4ySTibXU0oAvnEWXt7UDJmD4UkYialMfOGFPJnIHSe/kdzPxg==", + "version": "4.56.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-openbsd-x64/-/rollup-openbsd-x64-4.56.0.tgz", + "integrity": "sha512-O16XcmyDeFI9879pEcmtWvD/2nyxR9mF7Gs44lf1vGGx8Vg2DRNx11aVXBEqOQhWb92WN4z7fW/q4+2NYzCbBA==", "cpu": [ "x64" ], @@ -3348,9 +3343,9 @@ ] }, "node_modules/@rollup/rollup-openharmony-arm64": { - "version": "4.55.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-openharmony-arm64/-/rollup-openharmony-arm64-4.55.1.tgz", - "integrity": "sha512-xzm44KgEP11te3S2HCSyYf5zIzWmx3n8HDCc7EE59+lTcswEWNpvMLfd9uJvVX8LCg9QWG67Xt75AuHn4vgsXw==", + "version": "4.56.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-openharmony-arm64/-/rollup-openharmony-arm64-4.56.0.tgz", + "integrity": "sha512-LhN/Reh+7F3RCgQIRbgw8ZMwUwyqJM+8pXNT6IIJAqm2IdKkzpCh/V9EdgOMBKuebIrzswqy4ATlrDgiOwbRcQ==", "cpu": [ "arm64" ], @@ -3362,9 +3357,9 @@ ] }, "node_modules/@rollup/rollup-win32-arm64-msvc": { - "version": "4.55.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-arm64-msvc/-/rollup-win32-arm64-msvc-4.55.1.tgz", - "integrity": "sha512-yR6Bl3tMC/gBok5cz/Qi0xYnVbIxGx5Fcf/ca0eB6/6JwOY+SRUcJfI0OpeTpPls7f194as62thCt/2BjxYN8g==", + "version": "4.56.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-arm64-msvc/-/rollup-win32-arm64-msvc-4.56.0.tgz", + "integrity": "sha512-kbFsOObXp3LBULg1d3JIUQMa9Kv4UitDmpS+k0tinPBz3watcUiV2/LUDMMucA6pZO3WGE27P7DsfaN54l9ing==", "cpu": [ "arm64" ], @@ -3375,9 +3370,9 @@ ] }, "node_modules/@rollup/rollup-win32-ia32-msvc": { - "version": "4.55.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-ia32-msvc/-/rollup-win32-ia32-msvc-4.55.1.tgz", - "integrity": "sha512-3fZBidchE0eY0oFZBnekYCfg+5wAB0mbpCBuofh5mZuzIU/4jIVkbESmd2dOsFNS78b53CYv3OAtwqkZZmU5nA==", + "version": "4.56.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-ia32-msvc/-/rollup-win32-ia32-msvc-4.56.0.tgz", + "integrity": "sha512-vSSgny54D6P4vf2izbtFm/TcWYedw7f8eBrOiGGecyHyQB9q4Kqentjaj8hToe+995nob/Wv48pDqL5a62EWtg==", "cpu": [ "ia32" ], @@ -3389,9 +3384,9 @@ ] }, "node_modules/@rollup/rollup-win32-x64-gnu": { - "version": "4.55.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-gnu/-/rollup-win32-x64-gnu-4.55.1.tgz", - "integrity": "sha512-xGGY5pXj69IxKb4yv/POoocPy/qmEGhimy/FoTpTSVju3FYXUQQMFCaZZXJVidsmGxRioZAwpThl/4zX41gRKg==", + "version": "4.56.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-gnu/-/rollup-win32-x64-gnu-4.56.0.tgz", + "integrity": "sha512-FeCnkPCTHQJFbiGG49KjV5YGW/8b9rrXAM2Mz2kiIoktq2qsJxRD5giEMEOD2lPdgs72upzefaUvS+nc8E3UzQ==", "cpu": [ "x64" ], @@ -3403,9 +3398,9 @@ ] }, "node_modules/@rollup/rollup-win32-x64-msvc": { - "version": "4.55.1", - "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-msvc/-/rollup-win32-x64-msvc-4.55.1.tgz", - "integrity": "sha512-SPEpaL6DX4rmcXtnhdrQYgzQ5W2uW3SCJch88lB2zImhJRhIIK44fkUrgIV/Q8yUNfw5oyZ5vkeQsZLhCb06lw==", + "version": "4.56.0", + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-msvc/-/rollup-win32-x64-msvc-4.56.0.tgz", + "integrity": "sha512-H8AE9Ur/t0+1VXujj90w0HrSOuv0Nq9r1vSZF2t5km20NTfosQsGGUXDaKdQZzwuLts7IyL1fYT4hM95TI9c4g==", "cpu": [ "x64" ], @@ -3680,9 +3675,9 @@ "license": "MIT" }, "node_modules/@types/node": { - "version": "25.0.8", - "resolved": "https://registry.npmjs.org/@types/node/-/node-25.0.8.tgz", - "integrity": "sha512-powIePYMmC3ibL0UJ2i2s0WIbq6cg6UyVFQxSCpaPxxzAaziRfimGivjdF943sSGV6RADVbk0Nvlm5P/FB44Zg==", + "version": "25.0.10", + "resolved": "https://registry.npmjs.org/@types/node/-/node-25.0.10.tgz", + "integrity": "sha512-zWW5KPngR/yvakJgGOmZ5vTBemDoSqF3AcV/LrO5u5wTWyEAVVh+IT39G4gtyAkh3CtTZs8aX/yRM82OfzHJRg==", "dev": true, "license": "MIT", "dependencies": { @@ -3704,9 +3699,9 @@ "license": "MIT" }, "node_modules/@types/react": { - "version": "19.2.8", - "resolved": "https://registry.npmjs.org/@types/react/-/react-19.2.8.tgz", - "integrity": "sha512-3MbSL37jEchWZz2p2mjntRZtPt837ij10ApxKfgmXCTuHWagYg7iA5bqPw6C8BMPfwidlvfPI/fxOc42HLhcyg==", + "version": "19.2.9", + "resolved": "https://registry.npmjs.org/@types/react/-/react-19.2.9.tgz", + "integrity": "sha512-Lpo8kgb/igvMIPeNV2rsYKTgaORYdO1XGVZ4Qz3akwOj0ySGYMPlQWa8BaLn0G63D1aSaAQ5ldR06wCpChQCjA==", "dev": true, "license": "MIT", "dependencies": { @@ -3955,22 +3950,22 @@ } }, "node_modules/@vue/compiler-core": { - "version": "3.5.26", - "resolved": "https://registry.npmjs.org/@vue/compiler-core/-/compiler-core-3.5.26.tgz", - "integrity": "sha512-vXyI5GMfuoBCnv5ucIT7jhHKl55Y477yxP6fc4eUswjP8FG3FFVFd41eNDArR+Uk3QKn2Z85NavjaxLxOC19/w==", + "version": "3.5.27", + "resolved": "https://registry.npmjs.org/@vue/compiler-core/-/compiler-core-3.5.27.tgz", + "integrity": "sha512-gnSBQjZA+//qDZen+6a2EdHqJ68Z7uybrMf3SPjEGgG4dicklwDVmMC1AeIHxtLVPT7sn6sH1KOO+tS6gwOUeQ==", "license": "MIT", "dependencies": { "@babel/parser": "^7.28.5", - "@vue/shared": "3.5.26", + "@vue/shared": "3.5.27", "entities": "^7.0.0", "estree-walker": "^2.0.2", "source-map-js": "^1.2.1" } }, "node_modules/@vue/compiler-core/node_modules/entities": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/entities/-/entities-7.0.0.tgz", - "integrity": "sha512-FDWG5cmEYf2Z00IkYRhbFrwIwvdFKH07uV8dvNy0omp/Qb1xcyCWp2UDtcwJF4QZZvk0sLudP6/hAu42TaqVhQ==", + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/entities/-/entities-7.0.1.tgz", + "integrity": "sha512-TWrgLOFUQTH994YUyl1yT4uyavY5nNB5muff+RtWaqNVCAK408b5ZnnbNAUEWLTCpum9w6arT70i1XdQ4UeOPA==", "license": "BSD-2-Clause", "engines": { "node": ">=0.12" @@ -3980,26 +3975,26 @@ } }, "node_modules/@vue/compiler-dom": { - "version": "3.5.26", - "resolved": "https://registry.npmjs.org/@vue/compiler-dom/-/compiler-dom-3.5.26.tgz", - "integrity": "sha512-y1Tcd3eXs834QjswshSilCBnKGeQjQXB6PqFn/1nxcQw4pmG42G8lwz+FZPAZAby6gZeHSt/8LMPfZ4Rb+Bd/A==", + "version": "3.5.27", + "resolved": "https://registry.npmjs.org/@vue/compiler-dom/-/compiler-dom-3.5.27.tgz", + "integrity": "sha512-oAFea8dZgCtVVVTEC7fv3T5CbZW9BxpFzGGxC79xakTr6ooeEqmRuvQydIiDAkglZEAd09LgVf1RoDnL54fu5w==", "license": "MIT", "dependencies": { - "@vue/compiler-core": "3.5.26", - "@vue/shared": "3.5.26" + "@vue/compiler-core": "3.5.27", + "@vue/shared": "3.5.27" } }, "node_modules/@vue/compiler-sfc": { - "version": "3.5.26", - "resolved": "https://registry.npmjs.org/@vue/compiler-sfc/-/compiler-sfc-3.5.26.tgz", - "integrity": "sha512-egp69qDTSEZcf4bGOSsprUr4xI73wfrY5oRs6GSgXFTiHrWj4Y3X5Ydtip9QMqiCMCPVwLglB9GBxXtTadJ3mA==", + "version": "3.5.27", + "resolved": "https://registry.npmjs.org/@vue/compiler-sfc/-/compiler-sfc-3.5.27.tgz", + "integrity": "sha512-sHZu9QyDPeDmN/MRoshhggVOWE5WlGFStKFwu8G52swATgSny27hJRWteKDSUUzUH+wp+bmeNbhJnEAel/auUQ==", "license": "MIT", "dependencies": { "@babel/parser": "^7.28.5", - "@vue/compiler-core": "3.5.26", - "@vue/compiler-dom": "3.5.26", - "@vue/compiler-ssr": "3.5.26", - "@vue/shared": "3.5.26", + "@vue/compiler-core": "3.5.27", + "@vue/compiler-dom": "3.5.27", + "@vue/compiler-ssr": "3.5.27", + "@vue/shared": "3.5.27", "estree-walker": "^2.0.2", "magic-string": "^0.30.21", "postcss": "^8.5.6", @@ -4007,63 +4002,63 @@ } }, "node_modules/@vue/compiler-ssr": { - "version": "3.5.26", - "resolved": "https://registry.npmjs.org/@vue/compiler-ssr/-/compiler-ssr-3.5.26.tgz", - "integrity": "sha512-lZT9/Y0nSIRUPVvapFJEVDbEXruZh2IYHMk2zTtEgJSlP5gVOqeWXH54xDKAaFS4rTnDeDBQUYDtxKyoW9FwDw==", + "version": "3.5.27", + "resolved": "https://registry.npmjs.org/@vue/compiler-ssr/-/compiler-ssr-3.5.27.tgz", + "integrity": "sha512-Sj7h+JHt512fV1cTxKlYhg7qxBvack+BGncSpH+8vnN+KN95iPIcqB5rsbblX40XorP+ilO7VIKlkuu3Xq2vjw==", "license": "MIT", "dependencies": { - "@vue/compiler-dom": "3.5.26", - "@vue/shared": "3.5.26" + "@vue/compiler-dom": "3.5.27", + "@vue/shared": "3.5.27" } }, "node_modules/@vue/reactivity": { - "version": "3.5.26", - "resolved": "https://registry.npmjs.org/@vue/reactivity/-/reactivity-3.5.26.tgz", - "integrity": "sha512-9EnYB1/DIiUYYnzlnUBgwU32NNvLp/nhxLXeWRhHUEeWNTn1ECxX8aGO7RTXeX6PPcxe3LLuNBFoJbV4QZ+CFQ==", + "version": "3.5.27", + "resolved": "https://registry.npmjs.org/@vue/reactivity/-/reactivity-3.5.27.tgz", + "integrity": "sha512-vvorxn2KXfJ0nBEnj4GYshSgsyMNFnIQah/wczXlsNXt+ijhugmW+PpJ2cNPe4V6jpnBcs0MhCODKllWG+nvoQ==", "license": "MIT", "dependencies": { - "@vue/shared": "3.5.26" + "@vue/shared": "3.5.27" } }, "node_modules/@vue/runtime-core": { - "version": "3.5.26", - "resolved": "https://registry.npmjs.org/@vue/runtime-core/-/runtime-core-3.5.26.tgz", - "integrity": "sha512-xJWM9KH1kd201w5DvMDOwDHYhrdPTrAatn56oB/LRG4plEQeZRQLw0Bpwih9KYoqmzaxF0OKSn6swzYi84e1/Q==", + "version": "3.5.27", + "resolved": "https://registry.npmjs.org/@vue/runtime-core/-/runtime-core-3.5.27.tgz", + "integrity": "sha512-fxVuX/fzgzeMPn/CLQecWeDIFNt3gQVhxM0rW02Tvp/YmZfXQgcTXlakq7IMutuZ/+Ogbn+K0oct9J3JZfyk3A==", "license": "MIT", "dependencies": { - "@vue/reactivity": "3.5.26", - "@vue/shared": "3.5.26" + "@vue/reactivity": "3.5.27", + "@vue/shared": "3.5.27" } }, "node_modules/@vue/runtime-dom": { - "version": "3.5.26", - "resolved": "https://registry.npmjs.org/@vue/runtime-dom/-/runtime-dom-3.5.26.tgz", - "integrity": "sha512-XLLd/+4sPC2ZkN/6+V4O4gjJu6kSDbHAChvsyWgm1oGbdSO3efvGYnm25yCjtFm/K7rrSDvSfPDgN1pHgS4VNQ==", + "version": "3.5.27", + "resolved": "https://registry.npmjs.org/@vue/runtime-dom/-/runtime-dom-3.5.27.tgz", + "integrity": "sha512-/QnLslQgYqSJ5aUmb5F0z0caZPGHRB8LEAQ1s81vHFM5CBfnun63rxhvE/scVb/j3TbBuoZwkJyiLCkBluMpeg==", "license": "MIT", "dependencies": { - "@vue/reactivity": "3.5.26", - "@vue/runtime-core": "3.5.26", - "@vue/shared": "3.5.26", + "@vue/reactivity": "3.5.27", + "@vue/runtime-core": "3.5.27", + "@vue/shared": "3.5.27", "csstype": "^3.2.3" } }, "node_modules/@vue/server-renderer": { - "version": "3.5.26", - "resolved": "https://registry.npmjs.org/@vue/server-renderer/-/server-renderer-3.5.26.tgz", - "integrity": "sha512-TYKLXmrwWKSodyVuO1WAubucd+1XlLg4set0YoV+Hu8Lo79mp/YMwWV5mC5FgtsDxX3qo1ONrxFaTP1OQgy1uA==", + "version": "3.5.27", + "resolved": "https://registry.npmjs.org/@vue/server-renderer/-/server-renderer-3.5.27.tgz", + "integrity": "sha512-qOz/5thjeP1vAFc4+BY3Nr6wxyLhpeQgAE/8dDtKo6a6xdk+L4W46HDZgNmLOBUDEkFXV3G7pRiUqxjX0/2zWA==", "license": "MIT", "dependencies": { - "@vue/compiler-ssr": "3.5.26", - "@vue/shared": "3.5.26" + "@vue/compiler-ssr": "3.5.27", + "@vue/shared": "3.5.27" }, "peerDependencies": { - "vue": "3.5.26" + "vue": "3.5.27" } }, "node_modules/@vue/shared": { - "version": "3.5.26", - "resolved": "https://registry.npmjs.org/@vue/shared/-/shared-3.5.26.tgz", - "integrity": "sha512-7Z6/y3uFI5PRoKeorTOSXKcDj0MSasfNNltcslbFrPpcw6aXRUALq4IfJlaTRspiWIUOEZbrpM+iQGmCOiWe4A==", + "version": "3.5.27", + "resolved": "https://registry.npmjs.org/@vue/shared/-/shared-3.5.27.tgz", + "integrity": "sha512-dXr/3CgqXsJkZ0n9F3I4elY8wM9jMJpP3pvRG52r6m0tu/MsAFIe6JpXVGeNMd/D9F4hQynWT8Rfuj0bdm9kFQ==", "license": "MIT" }, "node_modules/@webgpu/types": { @@ -4329,9 +4324,9 @@ "license": "MIT" }, "node_modules/baseline-browser-mapping": { - "version": "2.9.14", - "resolved": "https://registry.npmjs.org/baseline-browser-mapping/-/baseline-browser-mapping-2.9.14.tgz", - "integrity": "sha512-B0xUquLkiGLgHhpPBqvl7GWegWBUNuujQ6kXd/r1U38ElPT6Ok8KZ8e+FpUGEc2ZoRQUzq/aUnaKFc/svWUGSg==", + "version": "2.9.17", + "resolved": "https://registry.npmjs.org/baseline-browser-mapping/-/baseline-browser-mapping-2.9.17.tgz", + "integrity": "sha512-agD0MgJFUP/4nvjqzIB29zRPUuCF7Ge6mEv9s8dHrtYD7QWXRcx75rOADE/d5ah1NI+0vkDl0yorDd5U852IQQ==", "dev": true, "license": "Apache-2.0", "bin": { @@ -4509,9 +4504,9 @@ } }, "node_modules/caniuse-lite": { - "version": "1.0.30001764", - "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001764.tgz", - "integrity": "sha512-9JGuzl2M+vPL+pz70gtMF9sHdMFbY9FJaQBi186cHKH3pSzDvzoUJUPV6fqiKIMyXbud9ZLg4F3Yza1vJ1+93g==", + "version": "1.0.30001766", + "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001766.tgz", + "integrity": "sha512-4C0lfJ0/YPjJQHagaE9x2Elb69CIqEPZeG0anQt9SIvIoOH4a4uaRl73IavyO+0qZh6MDLH//DrXThEYKHkmYA==", "dev": true, "funding": [ { @@ -4911,9 +4906,9 @@ } }, "node_modules/cors": { - "version": "2.8.5", - "resolved": "https://registry.npmjs.org/cors/-/cors-2.8.5.tgz", - "integrity": "sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g==", + "version": "2.8.6", + "resolved": "https://registry.npmjs.org/cors/-/cors-2.8.6.tgz", + "integrity": "sha512-tJtZBBHA6vjIAaF6EnIaq6laBBP9aq/Y3ouVJjEfoHbRBcHBAHYcMh/w8LDrk2PvIMMq8gmopa5D4V8RmbrxGw==", "license": "MIT", "dependencies": { "object-assign": "^4", @@ -4921,6 +4916,10 @@ }, "engines": { "node": ">= 0.10" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/express" } }, "node_modules/cross-env": { @@ -5071,9 +5070,9 @@ } }, "node_modules/d3-format": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/d3-format/-/d3-format-3.1.1.tgz", - "integrity": "sha512-ryitBnaRbXQtgZ/gU50GSn6jQRwinSCQclpakXymvLd8ytTgE5bmSfgYcUxD7XYL34qHhFDyVk71qqKsfSyvmA==", + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/d3-format/-/d3-format-3.1.2.tgz", + "integrity": "sha512-AJDdYOdnyRDV5b6ArilzCPPwc1ejkHcoyFarqlPqT7zRYjhavcT3uSrqcMvsgh2CgoPbK3RCwyHaVyxYcP2Arg==", "dev": true, "license": "ISC", "engines": { @@ -5378,9 +5377,9 @@ } }, "node_modules/electron-to-chromium": { - "version": "1.5.267", - "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.5.267.tgz", - "integrity": "sha512-0Drusm6MVRXSOJpGbaSVgcQsuB4hEkMpHXaVstcPmhu5LIedxs1xNK/nIxmQIU/RPC0+1/o0AVZfBTkTNJOdUw==", + "version": "1.5.277", + "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.5.277.tgz", + "integrity": "sha512-wKXFZw4erWmmOz5N/grBoJ2XrNJGDFMu2+W5ACHza5rHtvsqrK4gb6rnLC7XxKB9WlJ+RmyQatuEXmtm86xbnw==", "dev": true, "license": "ISC" }, @@ -5565,9 +5564,9 @@ "license": "MIT" }, "node_modules/esrap": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/esrap/-/esrap-2.2.1.tgz", - "integrity": "sha512-GiYWG34AN/4CUyaWAgunGt0Rxvr1PTMlGC0vvEov/uOQYWne2bpN03Um+k8jT+q3op33mKouP2zeJ6OlM+qeUg==", + "version": "2.2.2", + "resolved": "https://registry.npmjs.org/esrap/-/esrap-2.2.2.tgz", + "integrity": "sha512-zA6497ha+qKvoWIK+WM9NAh5ni17sKZKhbS5B3PoYbBvaYHZWoS33zmFybmyqpn07RLUxSmn+RCls2/XF+d0oQ==", "license": "MIT", "dependencies": { "@jridgewell/sourcemap-codec": "^1.4.15" @@ -5589,9 +5588,9 @@ } }, "node_modules/eventemitter3": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/eventemitter3/-/eventemitter3-5.0.1.tgz", - "integrity": "sha512-GWkBvjiSZK87ELrYOSESUYeVIc9mvLLf/nXalMOS5dYrgZq9o5OVkbZAVM06CVxYsCwH9BDZFPlQTlPA1j4ahA==", + "version": "5.0.4", + "resolved": "https://registry.npmjs.org/eventemitter3/-/eventemitter3-5.0.4.tgz", + "integrity": "sha512-mlsTRyGaPBjPedk6Bvw+aqbsXDtoAyAzm5MO7JgU+yVRyMQ5O8bD4Kcci7BS85f93veegeCPkL8R4GLClnjLFw==", "dev": true, "license": "MIT" }, @@ -6027,9 +6026,9 @@ } }, "node_modules/hono": { - "version": "4.11.4", - "resolved": "https://registry.npmjs.org/hono/-/hono-4.11.4.tgz", - "integrity": "sha512-U7tt8JsyrxSRKspfhtLET79pU8K+tInj5QZXs1jSugO1Vq5dFj3kmZsRldo29mTBfcjDRVRXrEZ6LS63Cog9ZA==", + "version": "4.11.5", + "resolved": "https://registry.npmjs.org/hono/-/hono-4.11.5.tgz", + "integrity": "sha512-WemPi9/WfyMwZs+ZUXdiwcCh9Y+m7L+8vki9MzDw3jJ+W9Lc+12HGsd368Qc1vZi1xwW8BWMMsnK5efYKPdt4g==", "license": "MIT", "peer": true, "engines": { @@ -6044,9 +6043,9 @@ "license": "MIT" }, "node_modules/htmlparser2": { - "version": "10.0.0", - "resolved": "https://registry.npmjs.org/htmlparser2/-/htmlparser2-10.0.0.tgz", - "integrity": "sha512-TwAZM+zE5Tq3lrEHvOlvwgj1XLWQCtaaibSN11Q+gGBAS7Y1uZSWwXXRe4iF6OXnaq1riyQAPFOBtYc77Mxq0g==", + "version": "10.1.0", + "resolved": "https://registry.npmjs.org/htmlparser2/-/htmlparser2-10.1.0.tgz", + "integrity": "sha512-VTZkM9GWRAtEpveh7MSF6SjjrpNVNNVJfFup7xTY3UpFtm67foy9HDVXneLtFVt4pMz5kZtgNcvCniNFb1hlEQ==", "funding": [ "https://github.com/fb55/htmlparser2?sponsor=1", { @@ -6058,14 +6057,14 @@ "dependencies": { "domelementtype": "^2.3.0", "domhandler": "^5.0.3", - "domutils": "^3.2.1", - "entities": "^6.0.0" + "domutils": "^3.2.2", + "entities": "^7.0.1" } }, "node_modules/htmlparser2/node_modules/entities": { - "version": "6.0.1", - "resolved": "https://registry.npmjs.org/entities/-/entities-6.0.1.tgz", - "integrity": "sha512-aN97NXWF6AWBTahfVOIrB/NShkzi5H7F9r1s9mD3cDj4Ko5f2qhhVoYMibXF7GlLveb/D2ioWay8lxI97Ven3g==", + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/entities/-/entities-7.0.1.tgz", + "integrity": "sha512-TWrgLOFUQTH994YUyl1yT4uyavY5nNB5muff+RtWaqNVCAK408b5ZnnbNAUEWLTCpum9w6arT70i1XdQ4UeOPA==", "license": "BSD-2-Clause", "engines": { "node": ">=0.12" @@ -6513,9 +6512,9 @@ "license": "MIT" }, "node_modules/lodash-es": { - "version": "4.17.22", - "resolved": "https://registry.npmjs.org/lodash-es/-/lodash-es-4.17.22.tgz", - "integrity": "sha512-XEawp1t0gxSi9x01glktRZ5HDy0HXqrM0x5pXQM98EaI0NxO6jVM7omDOxsuEo5UIASAnm2bRp1Jt/e0a2XU8Q==", + "version": "4.17.23", + "resolved": "https://registry.npmjs.org/lodash-es/-/lodash-es-4.17.23.tgz", + "integrity": "sha512-kVI48u3PZr38HdYz98UmfPnXl2DXrpdctLrFLCd3kOx1xUkOmpFPx7gCWWM5MPkL/fD8zb+Ph0QzjGFs4+hHWg==", "dev": true, "license": "MIT" }, @@ -7105,13 +7104,13 @@ } }, "node_modules/playwright": { - "version": "1.57.0", - "resolved": "https://registry.npmjs.org/playwright/-/playwright-1.57.0.tgz", - "integrity": "sha512-ilYQj1s8sr2ppEJ2YVadYBN0Mb3mdo9J0wQ+UuDhzYqURwSoW4n1Xs5vs7ORwgDGmyEh33tRMeS8KhdkMoLXQw==", + "version": "1.58.0", + "resolved": "https://registry.npmjs.org/playwright/-/playwright-1.58.0.tgz", + "integrity": "sha512-2SVA0sbPktiIY/MCOPX8e86ehA/e+tDNq+e5Y8qjKYti2Z/JG7xnronT/TXTIkKbYGWlCbuucZ6dziEgkoEjQQ==", "dev": true, "license": "Apache-2.0", "dependencies": { - "playwright-core": "1.57.0" + "playwright-core": "1.58.0" }, "bin": { "playwright": "cli.js" @@ -7124,9 +7123,9 @@ } }, "node_modules/playwright-core": { - "version": "1.57.0", - "resolved": "https://registry.npmjs.org/playwright-core/-/playwright-core-1.57.0.tgz", - "integrity": "sha512-agTcKlMw/mjBWOnD6kFZttAAGHgi/Nw0CZ2o6JqWSbMlI219lAFLZZCyqByTsvVAJq5XA5H8cA6PrvBRpBWEuQ==", + "version": "1.58.0", + "resolved": "https://registry.npmjs.org/playwright-core/-/playwright-core-1.58.0.tgz", + "integrity": "sha512-aaoB1RWrdNi3//rOeKuMiS65UCcgOVljU46At6eFcOFPFHWtd2weHRRow6z/n+Lec0Lvu0k9ZPKJSjPugikirw==", "dev": true, "license": "Apache-2.0", "bin": { @@ -7190,9 +7189,9 @@ } }, "node_modules/prettier": { - "version": "3.7.4", - "resolved": "https://registry.npmjs.org/prettier/-/prettier-3.7.4.tgz", - "integrity": "sha512-v6UNi1+3hSlVvv8fSaoUbggEM5VErKmmpGA7Pl3HF8V6uKY7rvClBOJlH6yNwQtfTueNkGVpOv/mtWL9L4bgRA==", + "version": "3.8.1", + "resolved": "https://registry.npmjs.org/prettier/-/prettier-3.8.1.tgz", + "integrity": "sha512-UOnG6LftzbdaHZcKoPFtOcCKztrQ57WkHDeRD9t/PTQtmT0NHSeWWepj6pS0z/N7+08BHFDQVUrfmfMRcZwbMg==", "dev": true, "license": "MIT", "bin": { @@ -7372,9 +7371,9 @@ "license": "MIT" }, "node_modules/rollup": { - "version": "4.55.1", - "resolved": "https://registry.npmjs.org/rollup/-/rollup-4.55.1.tgz", - "integrity": "sha512-wDv/Ht1BNHB4upNbK74s9usvl7hObDnvVzknxqY/E/O3X6rW1U1rV1aENEfJ54eFZDTNo7zv1f5N4edCluH7+A==", + "version": "4.56.0", + "resolved": "https://registry.npmjs.org/rollup/-/rollup-4.56.0.tgz", + "integrity": "sha512-9FwVqlgUHzbXtDg9RCMgodF3Ua4Na6Gau+Sdt9vyCN4RhHfVKX2DCHy3BjMLTDd47ITDhYAnTwGulWTblJSDLg==", "dev": true, "license": "MIT", "dependencies": { @@ -7388,31 +7387,31 @@ "npm": ">=8.0.0" }, "optionalDependencies": { - "@rollup/rollup-android-arm-eabi": "4.55.1", - "@rollup/rollup-android-arm64": "4.55.1", - "@rollup/rollup-darwin-arm64": "4.55.1", - "@rollup/rollup-darwin-x64": "4.55.1", - "@rollup/rollup-freebsd-arm64": "4.55.1", - "@rollup/rollup-freebsd-x64": "4.55.1", - "@rollup/rollup-linux-arm-gnueabihf": "4.55.1", - "@rollup/rollup-linux-arm-musleabihf": "4.55.1", - "@rollup/rollup-linux-arm64-gnu": "4.55.1", - "@rollup/rollup-linux-arm64-musl": "4.55.1", - "@rollup/rollup-linux-loong64-gnu": "4.55.1", - "@rollup/rollup-linux-loong64-musl": "4.55.1", - "@rollup/rollup-linux-ppc64-gnu": "4.55.1", - "@rollup/rollup-linux-ppc64-musl": "4.55.1", - "@rollup/rollup-linux-riscv64-gnu": "4.55.1", - "@rollup/rollup-linux-riscv64-musl": "4.55.1", - "@rollup/rollup-linux-s390x-gnu": "4.55.1", - "@rollup/rollup-linux-x64-gnu": "4.55.1", - "@rollup/rollup-linux-x64-musl": "4.55.1", - "@rollup/rollup-openbsd-x64": "4.55.1", - "@rollup/rollup-openharmony-arm64": "4.55.1", - "@rollup/rollup-win32-arm64-msvc": "4.55.1", - "@rollup/rollup-win32-ia32-msvc": "4.55.1", - "@rollup/rollup-win32-x64-gnu": "4.55.1", - "@rollup/rollup-win32-x64-msvc": "4.55.1", + "@rollup/rollup-android-arm-eabi": "4.56.0", + "@rollup/rollup-android-arm64": "4.56.0", + "@rollup/rollup-darwin-arm64": "4.56.0", + "@rollup/rollup-darwin-x64": "4.56.0", + "@rollup/rollup-freebsd-arm64": "4.56.0", + "@rollup/rollup-freebsd-x64": "4.56.0", + "@rollup/rollup-linux-arm-gnueabihf": "4.56.0", + "@rollup/rollup-linux-arm-musleabihf": "4.56.0", + "@rollup/rollup-linux-arm64-gnu": "4.56.0", + "@rollup/rollup-linux-arm64-musl": "4.56.0", + "@rollup/rollup-linux-loong64-gnu": "4.56.0", + "@rollup/rollup-linux-loong64-musl": "4.56.0", + "@rollup/rollup-linux-ppc64-gnu": "4.56.0", + "@rollup/rollup-linux-ppc64-musl": "4.56.0", + "@rollup/rollup-linux-riscv64-gnu": "4.56.0", + "@rollup/rollup-linux-riscv64-musl": "4.56.0", + "@rollup/rollup-linux-s390x-gnu": "4.56.0", + "@rollup/rollup-linux-x64-gnu": "4.56.0", + "@rollup/rollup-linux-x64-musl": "4.56.0", + "@rollup/rollup-openbsd-x64": "4.56.0", + "@rollup/rollup-openharmony-arm64": "4.56.0", + "@rollup/rollup-win32-arm64-msvc": "4.56.0", + "@rollup/rollup-win32-ia32-msvc": "4.56.0", + "@rollup/rollup-win32-x64-gnu": "4.56.0", + "@rollup/rollup-win32-x64-msvc": "4.56.0", "fsevents": "~2.3.2" } }, @@ -7962,9 +7961,9 @@ } }, "node_modules/svelte": { - "version": "5.46.4", - "resolved": "https://registry.npmjs.org/svelte/-/svelte-5.46.4.tgz", - "integrity": "sha512-VJwdXrmv9L8L7ZasJeWcCjoIuMRVbhuxbss0fpVnR8yorMmjNDwcjIH08vS6wmSzzzgAG5CADQ1JuXPS2nwt9w==", + "version": "5.48.0", + "resolved": "https://registry.npmjs.org/svelte/-/svelte-5.48.0.tgz", + "integrity": "sha512-+NUe82VoFP1RQViZI/esojx70eazGF4u0O/9ucqZ4rPcOZD+n5EVp17uYsqwdzjUjZyTpGKunHbDziW6AIAVkQ==", "license": "MIT", "dependencies": { "@jridgewell/remapping": "^2.3.4", @@ -7988,9 +7987,9 @@ } }, "node_modules/systeminformation": { - "version": "5.30.3", - "resolved": "https://registry.npmjs.org/systeminformation/-/systeminformation-5.30.3.tgz", - "integrity": "sha512-NgHJUpA+y7j4asLQa9jgBt+Eb2piyQIXQ+YjOyd2K0cHNwbNJ6I06F5afOqOiaCuV/wrEyGrb0olg4aFLlJD+A==", + "version": "5.30.5", + "resolved": "https://registry.npmjs.org/systeminformation/-/systeminformation-5.30.5.tgz", + "integrity": "sha512-DpWmpCckhwR3hG+6udb6/aQB7PpiqVnvSljrjbKxNSvTRsGsg7NVE3/vouoYf96xgwMxXFKcS4Ux+cnkFwYM7A==", "license": "MIT", "os": [ "darwin", @@ -8014,214 +8013,214 @@ } }, "node_modules/text-camel-case": { - "version": "1.2.9", - "resolved": "https://registry.npmjs.org/text-camel-case/-/text-camel-case-1.2.9.tgz", - "integrity": "sha512-wKYs9SgRxYizJE1mneR7BbLNlGw2IYzJAS8XwkWIry0CTbO1gvvPkFsx5Z1/hr+VqUaBqx9q3yKd30HpZLdMsQ==", + "version": "1.2.10", + "resolved": "https://registry.npmjs.org/text-camel-case/-/text-camel-case-1.2.10.tgz", + "integrity": "sha512-KNrWeZzQT+gh73V1LnmgTkjK7V+tMRjLCc6VrGwkqbiRdnGVIWBUgIvVnvnaVCxIvZ/2Ke8DCmgPirlQcCqD3Q==", "dev": true, "license": "MIT", "dependencies": { - "text-pascal-case": "1.2.9" + "text-pascal-case": "1.2.10" } }, "node_modules/text-capital-case": { - "version": "1.2.9", - "resolved": "https://registry.npmjs.org/text-capital-case/-/text-capital-case-1.2.9.tgz", - "integrity": "sha512-X5zV8U8pxtq2xS2t46lgAWqZdDbgWMKq03MQSNwY2CJdQCsdTNh144E2Q/q9wBxWzSBUXn+jRc9kF+Gs8/pGhA==", + "version": "1.2.10", + "resolved": "https://registry.npmjs.org/text-capital-case/-/text-capital-case-1.2.10.tgz", + "integrity": "sha512-yvViUJKSSQcRO58je224bhPHg/Hij9MEY43zuKShtFzrPwW/fOAarUJ5UkTMSB81AOO1m8q+JiFdxMF4etKZbA==", "dev": true, "license": "MIT", "dependencies": { - "text-no-case": "1.2.9", - "text-upper-case-first": "1.2.9" + "text-no-case": "1.2.10", + "text-upper-case-first": "1.2.10" } }, "node_modules/text-case": { - "version": "1.2.9", - "resolved": "https://registry.npmjs.org/text-case/-/text-case-1.2.9.tgz", - "integrity": "sha512-zZVdA8rMcjx9zhekdUuOPZShc25UTV7W8/ddKbgbPtfCEvIiToPtWiSd2lXLSuiGMovNhJ4+Tw49xll9o9ts+Q==", - "dev": true, - "license": "MIT", - "dependencies": { - "text-camel-case": "1.2.9", - "text-capital-case": "1.2.9", - "text-constant-case": "1.2.9", - "text-dot-case": "1.2.9", - "text-header-case": "1.2.9", - "text-is-lower-case": "1.2.9", - "text-is-upper-case": "1.2.9", - "text-kebab-case": "1.2.9", - "text-lower-case": "1.2.9", - "text-lower-case-first": "1.2.9", - "text-no-case": "1.2.9", - "text-param-case": "1.2.9", - "text-pascal-case": "1.2.9", - "text-path-case": "1.2.9", - "text-sentence-case": "1.2.9", - "text-snake-case": "1.2.9", - "text-swap-case": "1.2.9", - "text-title-case": "1.2.9", - "text-upper-case": "1.2.9", - "text-upper-case-first": "1.2.9" + "version": "1.2.10", + "resolved": "https://registry.npmjs.org/text-case/-/text-case-1.2.10.tgz", + "integrity": "sha512-5bY3Ks/u7OJ5YO69iyXrG5Xf2wUZeyko7U78nPUnYoSeuNeAfA5uAix5hTspfkl6smm3yCBObrex+kFvzeIcJg==", + "dev": true, + "license": "MIT", + "dependencies": { + "text-camel-case": "1.2.10", + "text-capital-case": "1.2.10", + "text-constant-case": "1.2.10", + "text-dot-case": "1.2.10", + "text-header-case": "1.2.10", + "text-is-lower-case": "1.2.10", + "text-is-upper-case": "1.2.10", + "text-kebab-case": "1.2.10", + "text-lower-case": "1.2.10", + "text-lower-case-first": "1.2.10", + "text-no-case": "1.2.10", + "text-param-case": "1.2.10", + "text-pascal-case": "1.2.10", + "text-path-case": "1.2.10", + "text-sentence-case": "1.2.10", + "text-snake-case": "1.2.10", + "text-swap-case": "1.2.10", + "text-title-case": "1.2.10", + "text-upper-case": "1.2.10", + "text-upper-case-first": "1.2.10" } }, "node_modules/text-constant-case": { - "version": "1.2.9", - "resolved": "https://registry.npmjs.org/text-constant-case/-/text-constant-case-1.2.9.tgz", - "integrity": "sha512-Vosm6nC7Gag+JFakJHwqS9AXRNgl07j5KZ7srU9cYuKRzYwrxzeJ4RpEogRBNHw7CfmOm0j5FGEznblWtu7pIw==", + "version": "1.2.10", + "resolved": "https://registry.npmjs.org/text-constant-case/-/text-constant-case-1.2.10.tgz", + "integrity": "sha512-/OfU798O2wrwKN9kQf71WhJeAlklGnbby0Tupp+Ez9NXymW+6oF9LWDRTkN+OreTmHucdvp4WQd6O5Rah5zj8A==", "dev": true, "license": "MIT", "dependencies": { - "text-no-case": "1.2.9", - "text-upper-case": "1.2.9" + "text-no-case": "1.2.10", + "text-upper-case": "1.2.10" } }, "node_modules/text-dot-case": { - "version": "1.2.9", - "resolved": "https://registry.npmjs.org/text-dot-case/-/text-dot-case-1.2.9.tgz", - "integrity": "sha512-N83hsnvGdSO9q9AfNSB9Cy1LFDNN2MCx53LcxtaPoDWPUTk47fv0JlvIY1tgY0wyzCiThF03kVj3jworvAOScA==", + "version": "1.2.10", + "resolved": "https://registry.npmjs.org/text-dot-case/-/text-dot-case-1.2.10.tgz", + "integrity": "sha512-vf4xguy5y6e39RlDZeWZFMDf2mNkR23VTSVb9e68dUSpfJscG9/1YWWpW3n8TinzQxBZlsn5sT5olL33MvvQXw==", "dev": true, "license": "MIT", "dependencies": { - "text-no-case": "1.2.9" + "text-no-case": "1.2.10" } }, "node_modules/text-header-case": { - "version": "1.2.9", - "resolved": "https://registry.npmjs.org/text-header-case/-/text-header-case-1.2.9.tgz", - "integrity": "sha512-TqryEKcYisQAfWLbtT3xPnZlMZ/mySO1uS+LUg+B0eNuqgETrSzVpXIUj5E6Zf/EyJHgpZf4VndbAXtOMJuT4w==", + "version": "1.2.10", + "resolved": "https://registry.npmjs.org/text-header-case/-/text-header-case-1.2.10.tgz", + "integrity": "sha512-sVb1NY9bwxtu+Z7CVyWbr+I0AkWtF0kEHL/Zz5V2u/WdkjK5tKBwl5nXf0NGy9da4ZUYTBb+TmQpOIqihzvFMQ==", "dev": true, "license": "MIT", "dependencies": { - "text-capital-case": "1.2.9" + "text-capital-case": "1.2.10" } }, "node_modules/text-is-lower-case": { - "version": "1.2.9", - "resolved": "https://registry.npmjs.org/text-is-lower-case/-/text-is-lower-case-1.2.9.tgz", - "integrity": "sha512-cEurrWSnYVYqL8FSwl5cK4mdfqF7qNDCcKJgXI3NnfTesiB8umxAhdlQoErrRYI1xEvYr2WN0MI333EehUhQjg==", + "version": "1.2.10", + "resolved": "https://registry.npmjs.org/text-is-lower-case/-/text-is-lower-case-1.2.10.tgz", + "integrity": "sha512-dMTeTgrdWWfYf3fKxvjMkDPuXWv96cWbd1Uym6Zjv9H855S1uHxjkFsGbTYJ2tEK0NvAylRySTQlI6axlcMc4w==", "dev": true, "license": "MIT" }, "node_modules/text-is-upper-case": { - "version": "1.2.9", - "resolved": "https://registry.npmjs.org/text-is-upper-case/-/text-is-upper-case-1.2.9.tgz", - "integrity": "sha512-HxsWr3VCsXXiLlhD0c+Ey+mS2lOTCiSJbkepjaXNHl2bp33KiscQaiG0qLwQmmpZQm4SJCg2s9FkndxS0RNDLQ==", + "version": "1.2.10", + "resolved": "https://registry.npmjs.org/text-is-upper-case/-/text-is-upper-case-1.2.10.tgz", + "integrity": "sha512-PGD/cXoXECGAY1HVZxDdmpJUW2ZUAKQ6DTamDfCHC9fc/z4epOz0pB/ThBnjJA3fz+d2ApkMjAfZDjuZFcodzg==", "dev": true, "license": "MIT" }, "node_modules/text-kebab-case": { - "version": "1.2.9", - "resolved": "https://registry.npmjs.org/text-kebab-case/-/text-kebab-case-1.2.9.tgz", - "integrity": "sha512-nOUyNR5Ej2B9D/wyyXfwUEv26+pQuOb1pEX+ojE37mCIWo8QeOxw5y6nxuqDmG7NrEPzbO6265UMV+EICH13Cw==", + "version": "1.2.10", + "resolved": "https://registry.npmjs.org/text-kebab-case/-/text-kebab-case-1.2.10.tgz", + "integrity": "sha512-3XZJAApx5JQpUO7eXo7GQ2TyRcGw3OVbqxz6QJb2h+N8PbLLbz3zJVeXdGrhTkoUIbkSZ6PmHx6LRDaHXTdMcA==", "dev": true, "license": "MIT", "dependencies": { - "text-no-case": "1.2.9" + "text-no-case": "1.2.10" } }, "node_modules/text-lower-case": { - "version": "1.2.9", - "resolved": "https://registry.npmjs.org/text-lower-case/-/text-lower-case-1.2.9.tgz", - "integrity": "sha512-53AOnDrhPpiAUQkgY1SHleKUXp/u7GsqRX13NcCREZscmtjLLJ099uxMRjkK7q2KwHkFYVPl9ytkQlTkTQLS0w==", + "version": "1.2.10", + "resolved": "https://registry.npmjs.org/text-lower-case/-/text-lower-case-1.2.10.tgz", + "integrity": "sha512-c9j5pIAN3ObAp1+4R7970e1bgtahTRF/5ZQdX2aJBuBngYTYZZIck0NwFXUKk5BnYpLGsre5KFHvpqvf4IYKgg==", "dev": true, "license": "MIT" }, "node_modules/text-lower-case-first": { - "version": "1.2.9", - "resolved": "https://registry.npmjs.org/text-lower-case-first/-/text-lower-case-first-1.2.9.tgz", - "integrity": "sha512-iiphHTV7PVH0MljrEQUA9iBE7jfDpXoi4RQju3WzZU3BRVbS6540cNZgxR19hWa0z6z/7cJTH0Ls9LPBaiUfKg==", + "version": "1.2.10", + "resolved": "https://registry.npmjs.org/text-lower-case-first/-/text-lower-case-first-1.2.10.tgz", + "integrity": "sha512-Oro84jZPDLD9alfdZWmtFHYTvCaaSz2o4thPtjMsK4GAkTyVg9juYXWj0y0YFyjLYGH69muWsBe4/MR5S7iolw==", "dev": true, "license": "MIT" }, "node_modules/text-no-case": { - "version": "1.2.9", - "resolved": "https://registry.npmjs.org/text-no-case/-/text-no-case-1.2.9.tgz", - "integrity": "sha512-IcCt328KaapimSrytP4ThfC8URmHZb2DgOqCL9BYvGjpxY2lDiqCkIQk9sClZtwcELs2gTnq83a7jNc573FTLA==", + "version": "1.2.10", + "resolved": "https://registry.npmjs.org/text-no-case/-/text-no-case-1.2.10.tgz", + "integrity": "sha512-4/m79pzQrywrwEG5lCULY1lQvFY+EKjhH9xSMT6caPK5plqzm9Y7rXyv+UXPd3s9qH6QODZnvsAYWW3M0JgxRA==", "dev": true, "license": "MIT", "dependencies": { - "text-lower-case": "1.2.9" + "text-lower-case": "1.2.10" } }, "node_modules/text-param-case": { - "version": "1.2.9", - "resolved": "https://registry.npmjs.org/text-param-case/-/text-param-case-1.2.9.tgz", - "integrity": "sha512-nR/Ju9amY3aQS1en2CUCgqN/ZiZIVdDyjlJ3xX5J92ChBevGuA4o9K10fh3JGMkbzK97Vcb+bWQJ4Q+Svz+GyQ==", + "version": "1.2.10", + "resolved": "https://registry.npmjs.org/text-param-case/-/text-param-case-1.2.10.tgz", + "integrity": "sha512-hkavcLsRRzZcGryPAshct1AwIOMj/FexYjMaLpGZCYYBn1lcZEeyMzJZPSckzkOYpq35LYSQr3xZto9XU5OAsw==", "dev": true, "license": "MIT", "dependencies": { - "text-dot-case": "1.2.9" + "text-dot-case": "1.2.10" } }, "node_modules/text-pascal-case": { - "version": "1.2.9", - "resolved": "https://registry.npmjs.org/text-pascal-case/-/text-pascal-case-1.2.9.tgz", - "integrity": "sha512-o6ZxMGjWDTUW54pcghpXes+C2PqbYRMdU5mHrIhueb6z6nq1NueiIOeCUdrSjN/3wXfhCmnFjK7/d9aRGZNqSg==", + "version": "1.2.10", + "resolved": "https://registry.npmjs.org/text-pascal-case/-/text-pascal-case-1.2.10.tgz", + "integrity": "sha512-/kynZD8vTYOmm/RECjIDaz3qYEUZc/N/bnC79XuAFxwXjdNVjj/jGovKJLRzqsYK/39N22XpGcVmGg7yIrbk6w==", "dev": true, "license": "MIT", "dependencies": { - "text-no-case": "1.2.9" + "text-no-case": "1.2.10" } }, "node_modules/text-path-case": { - "version": "1.2.9", - "resolved": "https://registry.npmjs.org/text-path-case/-/text-path-case-1.2.9.tgz", - "integrity": "sha512-s8cJ6r5TkJp5ticXMgtxd7f12odEN4d1CfX5u4aoz6jcUtBR2lDqzIhVimkqWFMJ4UKPSrmilUha8Xc2BPi+ow==", + "version": "1.2.10", + "resolved": "https://registry.npmjs.org/text-path-case/-/text-path-case-1.2.10.tgz", + "integrity": "sha512-vbKdRCaVEeOaW6sm24QP9NbH7TS9S4ZQ3u19H8eylDox7m2HtFwYIBjAPv+v3z4I/+VjrMy9LB54lNP1uEqRHw==", "dev": true, "license": "MIT", "dependencies": { - "text-dot-case": "1.2.9" + "text-dot-case": "1.2.10" } }, "node_modules/text-sentence-case": { - "version": "1.2.9", - "resolved": "https://registry.npmjs.org/text-sentence-case/-/text-sentence-case-1.2.9.tgz", - "integrity": "sha512-/G/Yi5kZfUa1edFRV4O3lGZAkbDZTFvlwW8CYfH7szkEGe2k2MYEYbOyAkGRVQEGV6V6JiuUAaP3VS9c1tB6nQ==", + "version": "1.2.10", + "resolved": "https://registry.npmjs.org/text-sentence-case/-/text-sentence-case-1.2.10.tgz", + "integrity": "sha512-NO4MRlbfxFhl9QgQLuCL4xHmvE7PUWHVPWsZxQ5nzRtDjXOUllWvtsvl8CP5tBEvBmzg0kwfflxfhRtr5vBQGg==", "dev": true, "license": "MIT", "dependencies": { - "text-no-case": "1.2.9", - "text-upper-case-first": "1.2.9" + "text-no-case": "1.2.10", + "text-upper-case-first": "1.2.10" } }, "node_modules/text-snake-case": { - "version": "1.2.9", - "resolved": "https://registry.npmjs.org/text-snake-case/-/text-snake-case-1.2.9.tgz", - "integrity": "sha512-+ZrqK19ynF/TLQZ7ynqVrL2Dy04uu9syYZwsm8PhzUdsY3XrwPy6QiRqhIEFqhyWbShPcfyfmheer5UEQqFxlw==", + "version": "1.2.10", + "resolved": "https://registry.npmjs.org/text-snake-case/-/text-snake-case-1.2.10.tgz", + "integrity": "sha512-6ttMZ+B9jkHKun908HYr4xSvEtlbfJJ4MvpQ06JEKRGhwjMI0x8t2Wywp+MEzN6142O6E/zKhra18KyBL6cvXA==", "dev": true, "license": "MIT", "dependencies": { - "text-dot-case": "1.2.9" + "text-dot-case": "1.2.10" } }, "node_modules/text-swap-case": { - "version": "1.2.9", - "resolved": "https://registry.npmjs.org/text-swap-case/-/text-swap-case-1.2.9.tgz", - "integrity": "sha512-g5fp12ldktYKK9wdHRMvvtSCQrZYNv/D+ZGLumDsvAY4q9T5bCMO2IWMkIP1F5gVQrysdHH6Xv877P/pjUq1iw==", + "version": "1.2.10", + "resolved": "https://registry.npmjs.org/text-swap-case/-/text-swap-case-1.2.10.tgz", + "integrity": "sha512-vO3jwInIk0N77oEFakYZ2Hn/llTmRwf2c3RvkX/LfvmLWVp+3QcIc6bwUEtbqGQ5Xh2okjFhYrfkHZstVc3N4Q==", "dev": true, "license": "MIT" }, "node_modules/text-title-case": { - "version": "1.2.9", - "resolved": "https://registry.npmjs.org/text-title-case/-/text-title-case-1.2.9.tgz", - "integrity": "sha512-RAtC9cdmPp41ns5/HXZBsaQg71BsHT7uZpj2ojTtuFa8o2dNuRYYOrSmy5YdLRIAJQ6WK5hQVpV3jHuq7a+4Tw==", + "version": "1.2.10", + "resolved": "https://registry.npmjs.org/text-title-case/-/text-title-case-1.2.10.tgz", + "integrity": "sha512-bqA+WWexUMWu9A3fdNar+3GXXW+c5xOvMyuK5hOx/w0AlqhyQptyCrMFjGB8Fd9dxbryBNmJ+5rWtC1OBDxlaA==", "dev": true, "license": "MIT", "dependencies": { - "text-no-case": "1.2.9", - "text-upper-case-first": "1.2.9" + "text-no-case": "1.2.10", + "text-upper-case-first": "1.2.10" } }, "node_modules/text-upper-case": { - "version": "1.2.9", - "resolved": "https://registry.npmjs.org/text-upper-case/-/text-upper-case-1.2.9.tgz", - "integrity": "sha512-K/0DNT7a4z8eah2spARtoJllTZyrNTo6Uc0ujhN/96Ir9uJ/slpahfs13y46H9osL3daaLl3O7iXOkW4xtX6bg==", + "version": "1.2.10", + "resolved": "https://registry.npmjs.org/text-upper-case/-/text-upper-case-1.2.10.tgz", + "integrity": "sha512-L1AtZ8R+jtSMTq0Ffma9R4Rzbrc3iuYW89BmWFH41AwnDfRmEBlBOllm1ZivRLQ/6pEu2p+3XKBHx9fsMl2CWg==", "dev": true, "license": "MIT" }, "node_modules/text-upper-case-first": { - "version": "1.2.9", - "resolved": "https://registry.npmjs.org/text-upper-case-first/-/text-upper-case-first-1.2.9.tgz", - "integrity": "sha512-wEDD1B6XqJmEV+xEnBJd+2sBCHZ+7fvA/8Rv/o8+dAsp05YWjYP/kjB8sPH6zqzW0s6jtehIg4IlcKjcYxk2CQ==", + "version": "1.2.10", + "resolved": "https://registry.npmjs.org/text-upper-case-first/-/text-upper-case-first-1.2.10.tgz", + "integrity": "sha512-VXs7j7BbpKwvolDh5fwpYRmMrUHGkxbY8E90fhBzKUoKfadvWmPT/jFieoZ4UPLzr208pXvQEFbb2zO9Qzs9Fg==", "dev": true, "license": "MIT" }, @@ -9078,9 +9077,9 @@ "license": "MIT" }, "node_modules/undici": { - "version": "7.18.2", - "resolved": "https://registry.npmjs.org/undici/-/undici-7.18.2.tgz", - "integrity": "sha512-y+8YjDFzWdQlSE9N5nzKMT3g4a5UBX1HKowfdXh0uvAnTaqqwqB92Jt4UXBAeKekDs5IaDKyJFR4X1gYVCgXcw==", + "version": "7.19.0", + "resolved": "https://registry.npmjs.org/undici/-/undici-7.19.0.tgz", + "integrity": "sha512-Heho1hJD81YChi+uS2RkSjcVO+EQLmLSyUlHyp7Y/wFbxQaGb4WXVKD073JytrjXJVkSZVzoE2MCSOKugFGtOQ==", "license": "MIT", "engines": { "node": ">=20.18.1" @@ -9438,16 +9437,16 @@ } }, "node_modules/vue": { - "version": "3.5.26", - "resolved": "https://registry.npmjs.org/vue/-/vue-3.5.26.tgz", - "integrity": "sha512-SJ/NTccVyAoNUJmkM9KUqPcYlY+u8OVL1X5EW9RIs3ch5H2uERxyyIUI4MRxVCSOiEcupX9xNGde1tL9ZKpimA==", + "version": "3.5.27", + "resolved": "https://registry.npmjs.org/vue/-/vue-3.5.27.tgz", + "integrity": "sha512-aJ/UtoEyFySPBGarREmN4z6qNKpbEguYHMmXSiOGk69czc+zhs0NF6tEFrY8TZKAl8N/LYAkd4JHVd5E/AsSmw==", "license": "MIT", "dependencies": { - "@vue/compiler-dom": "3.5.26", - "@vue/compiler-sfc": "3.5.26", - "@vue/runtime-dom": "3.5.26", - "@vue/server-renderer": "3.5.26", - "@vue/shared": "3.5.26" + "@vue/compiler-dom": "3.5.27", + "@vue/compiler-sfc": "3.5.27", + "@vue/runtime-dom": "3.5.27", + "@vue/server-renderer": "3.5.27", + "@vue/shared": "3.5.27" }, "peerDependencies": { "typescript": "*" @@ -9660,9 +9659,9 @@ "license": "MIT" }, "node_modules/zod": { - "version": "4.3.5", - "resolved": "https://registry.npmjs.org/zod/-/zod-4.3.5.tgz", - "integrity": "sha512-k7Nwx6vuWx1IJ9Bjuf4Zt1PEllcwe7cls3VNzm4CQ1/hgtFUK2bRNG3rvnpPUhFjmqJKAKtjV576KnUkHocg/g==", + "version": "4.3.6", + "resolved": "https://registry.npmjs.org/zod/-/zod-4.3.6.tgz", + "integrity": "sha512-rftlrkhHZOcjDwkGlnUtZZkvaPHCsDATp4pGpuOOMDaTdDDXF91wuVDJoWoPsKX/3YPQ5fHuF3STjcYyKr+Qhg==", "license": "MIT", "funding": { "url": "https://github.com/sponsors/colinhacks"