sunpeak 0.16.3 → 0.16.5
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +3 -1
- package/bin/commands/build.mjs +1 -0
- package/bin/commands/dev.mjs +2 -0
- package/dist/chatgpt/globals.css +0 -8
- package/dist/mcp/index.cjs +61 -48
- package/dist/mcp/index.cjs.map +1 -1
- package/dist/mcp/index.js +61 -48
- package/dist/mcp/index.js.map +1 -1
- package/dist/style.css +0 -8
- package/package.json +1 -1
- package/template/package.json +0 -3
- package/template/src/components/avatar.tsx +1 -1
- package/template/src/resources/albums/components/album-card.tsx +2 -2
- package/template/src/resources/albums/components/album-carousel.tsx +3 -3
- package/template/src/resources/albums/components/film-strip.tsx +2 -2
- package/template/src/resources/albums/components/fullscreen-viewer.tsx +1 -1
- package/template/src/resources/carousel/components/card.tsx +2 -2
- package/template/src/resources/carousel/components/carousel.tsx +3 -3
- package/template/src/resources/map/components/map-view.tsx +1 -1
- package/template/src/resources/map/components/map.tsx +3 -3
- package/template/src/resources/map/components/place-card.tsx +2 -2
- package/template/src/resources/map/components/place-carousel.tsx +1 -1
- package/template/src/resources/map/components/place-inspector.tsx +4 -4
- package/template/src/resources/map/components/place-list.tsx +2 -2
- package/template/src/resources/review/review.tsx +59 -29
- package/template/src/tools/review-diff.ts +3 -1
- package/template/src/tools/review-post.ts +3 -1
- package/template/src/tools/review-purchase.ts +3 -1
- package/template/src/tools/show-albums.ts +3 -1
- package/template/src/tools/show-carousel.ts +3 -1
- package/template/src/tools/show-map.ts +3 -1
- package/template/tsconfig.json +7 -2
- package/template/vitest.config.ts +1 -0
- package/template/node_modules/.bin/nodemon +0 -21
- package/template/node_modules/.bin/tsx +0 -21
package/dist/mcp/index.js
CHANGED
|
@@ -15518,27 +15518,30 @@ function createAppServer(config, simulations, viteMode) {
|
|
|
15518
15518
|
},
|
|
15519
15519
|
{ capabilities: { resources: {}, tools: {} } }
|
|
15520
15520
|
);
|
|
15521
|
-
const
|
|
15521
|
+
const registeredUriSet = /* @__PURE__ */ new Set();
|
|
15522
|
+
const resourceHandles = /* @__PURE__ */ new Map();
|
|
15523
|
+
const toolHandles = [];
|
|
15522
15524
|
for (const simulation of simulations) {
|
|
15523
15525
|
const resource = simulation.resource;
|
|
15524
15526
|
const tool = simulation.tool;
|
|
15525
15527
|
const toolResult = simulation.toolResult ?? { structuredContent: null };
|
|
15526
15528
|
const uri2 = resource.uri ?? `ui://${resource.name}`;
|
|
15529
|
+
const resourceName = resource.name;
|
|
15527
15530
|
const resourceMeta = resource._meta ?? {};
|
|
15528
15531
|
const toolMeta = tool._meta ?? {};
|
|
15529
|
-
if (!
|
|
15530
|
-
|
|
15532
|
+
if (!registeredUriSet.has(uri2)) {
|
|
15533
|
+
registeredUriSet.add(uri2);
|
|
15531
15534
|
const listMeta = viteMode ? injectViteCSP(resourceMeta) : resourceMeta;
|
|
15532
15535
|
console.log(`[MCP] RegisterResource: ${uri2}`);
|
|
15533
|
-
|
|
15534
|
-
|
|
15535
|
-
resource.name,
|
|
15536
|
+
const handle = mcpServer.registerResource(
|
|
15537
|
+
resourceName,
|
|
15536
15538
|
uri2,
|
|
15537
15539
|
{
|
|
15540
|
+
mimeType: EI,
|
|
15538
15541
|
description: resource.description,
|
|
15539
15542
|
_meta: listMeta
|
|
15540
15543
|
},
|
|
15541
|
-
async (
|
|
15544
|
+
async (readUri, extra) => {
|
|
15542
15545
|
const prodBuild = needsProdBuild(
|
|
15543
15546
|
extra?.requestInfo?.headers ?? {}
|
|
15544
15547
|
);
|
|
@@ -15547,17 +15550,18 @@ function createAppServer(config, simulations, viteMode) {
|
|
|
15547
15550
|
try {
|
|
15548
15551
|
content = getResourceHtml(simulation, viteMode, prodBuild);
|
|
15549
15552
|
} catch (error) {
|
|
15550
|
-
console.error(`[MCP] ReadResource error for ${
|
|
15553
|
+
console.error(`[MCP] ReadResource error for ${readUri.href}:`, error);
|
|
15551
15554
|
throw error;
|
|
15552
15555
|
}
|
|
15553
15556
|
const sizeKB = (content.length / 1024).toFixed(1);
|
|
15554
15557
|
console.log(
|
|
15555
|
-
`[MCP] ReadResource: ${
|
|
15558
|
+
`[MCP] ReadResource: ${readUri.href} → ${sizeKB}KB${prodBuild ? " (prod build)" : " (vite)"}`
|
|
15556
15559
|
);
|
|
15557
15560
|
return {
|
|
15558
15561
|
contents: [
|
|
15559
15562
|
{
|
|
15560
|
-
|
|
15563
|
+
// Use readUri (not closure variable) so the response URI matches after updates
|
|
15564
|
+
uri: readUri.href,
|
|
15561
15565
|
mimeType: EI,
|
|
15562
15566
|
text: content,
|
|
15563
15567
|
_meta: readMeta
|
|
@@ -15566,20 +15570,22 @@ function createAppServer(config, simulations, viteMode) {
|
|
|
15566
15570
|
};
|
|
15567
15571
|
}
|
|
15568
15572
|
);
|
|
15573
|
+
resourceHandles.set(resourceName, handle);
|
|
15569
15574
|
}
|
|
15570
|
-
|
|
15575
|
+
const fullToolMeta = {
|
|
15576
|
+
...toolMeta,
|
|
15577
|
+
ui: {
|
|
15578
|
+
resourceUri: uri2,
|
|
15579
|
+
// Preserve tool visibility from simulation metadata if declared
|
|
15580
|
+
...toolMeta.ui?.visibility ? { visibility: toolMeta.ui.visibility } : {}
|
|
15581
|
+
}
|
|
15582
|
+
};
|
|
15583
|
+
const toolHandle = hk(
|
|
15571
15584
|
mcpServer,
|
|
15572
15585
|
tool.name,
|
|
15573
15586
|
{
|
|
15574
15587
|
description: tool.description,
|
|
15575
|
-
_meta:
|
|
15576
|
-
...toolMeta,
|
|
15577
|
-
ui: {
|
|
15578
|
-
resourceUri: uri2,
|
|
15579
|
-
// Preserve tool visibility from simulation metadata if declared
|
|
15580
|
-
...toolMeta.ui?.visibility ? { visibility: toolMeta.ui.visibility } : {}
|
|
15581
|
-
}
|
|
15582
|
-
}
|
|
15588
|
+
_meta: fullToolMeta
|
|
15583
15589
|
},
|
|
15584
15590
|
async (extra) => {
|
|
15585
15591
|
const args = extra.request?.params?.arguments ?? {};
|
|
@@ -15600,12 +15606,13 @@ function createAppServer(config, simulations, viteMode) {
|
|
|
15600
15606
|
};
|
|
15601
15607
|
}
|
|
15602
15608
|
);
|
|
15609
|
+
toolHandles.push({ handle: toolHandle, resourceName, toolMeta: fullToolMeta });
|
|
15603
15610
|
}
|
|
15604
|
-
const registeredUris = Array.from(
|
|
15611
|
+
const registeredUris = Array.from(registeredUriSet).join(", ");
|
|
15605
15612
|
console.log(
|
|
15606
15613
|
`[MCP] Registered ${simulations.length} tool(s) and resource(s)${viteMode ? " (vite mode)" : ""}: ${registeredUris}`
|
|
15607
15614
|
);
|
|
15608
|
-
return mcpServer;
|
|
15615
|
+
return { server: mcpServer, resourceHandles, toolHandles };
|
|
15609
15616
|
}
|
|
15610
15617
|
const SESSION_IDLE_TIMEOUT_MS$1 = 5 * 60 * 1e3;
|
|
15611
15618
|
function isLocalConnection(req) {
|
|
@@ -15624,10 +15631,8 @@ const cleanupInterval = setInterval(() => {
|
|
|
15624
15631
|
const now = Date.now();
|
|
15625
15632
|
for (const [id2, session] of sessions) {
|
|
15626
15633
|
if (now - session.lastActivity > SESSION_IDLE_TIMEOUT_MS$1) {
|
|
15627
|
-
|
|
15628
|
-
session.
|
|
15629
|
-
session.server.close();
|
|
15630
|
-
console.log(`[MCP] Session expired: ${id2.substring(0, 8)}... (${sessions.size} active)`);
|
|
15634
|
+
console.log(`[MCP] Session expired: ${id2.substring(0, 8)}...`);
|
|
15635
|
+
void session.server.close();
|
|
15631
15636
|
}
|
|
15632
15637
|
}
|
|
15633
15638
|
}, 6e4);
|
|
@@ -15674,11 +15679,18 @@ async function handleMcpRequest(req, res, config, simulations, viteMode) {
|
|
|
15674
15679
|
}
|
|
15675
15680
|
if (req.method === "POST") {
|
|
15676
15681
|
const isLocal = isLocalConnection(req);
|
|
15677
|
-
const server = createAppServer(config, simulations, viteMode);
|
|
15682
|
+
const { server, resourceHandles, toolHandles } = createAppServer(config, simulations, viteMode);
|
|
15678
15683
|
const transport = new StreamableHTTPServerTransport({
|
|
15679
15684
|
sessionIdGenerator: () => randomUUID(),
|
|
15680
15685
|
onsessioninitialized: (id2) => {
|
|
15681
|
-
sessions.set(id2, {
|
|
15686
|
+
sessions.set(id2, {
|
|
15687
|
+
server,
|
|
15688
|
+
transport,
|
|
15689
|
+
isLocal,
|
|
15690
|
+
lastActivity: Date.now(),
|
|
15691
|
+
resourceHandles,
|
|
15692
|
+
toolHandles
|
|
15693
|
+
});
|
|
15682
15694
|
const origin = isLocal ? "local" : "tunnel";
|
|
15683
15695
|
console.log(
|
|
15684
15696
|
`[MCP] Session started: ${id2.substring(0, 8)}... (${origin}, ${sessions.size} active)`
|
|
@@ -15693,13 +15705,12 @@ async function handleMcpRequest(req, res, config, simulations, viteMode) {
|
|
|
15693
15705
|
const id2 = transport.sessionId;
|
|
15694
15706
|
console.error(`[MCP] Transport error${id2 ? ` (${id2.substring(0, 8)}...)` : ""}:`, error);
|
|
15695
15707
|
};
|
|
15696
|
-
transport.onclose =
|
|
15708
|
+
transport.onclose = () => {
|
|
15697
15709
|
const id2 = transport.sessionId;
|
|
15698
15710
|
if (id2 && sessions.has(id2)) {
|
|
15699
15711
|
sessions.delete(id2);
|
|
15700
15712
|
console.log(`[MCP] Session closed: ${id2.substring(0, 8)}... (${sessions.size} active)`);
|
|
15701
15713
|
}
|
|
15702
|
-
await server.close();
|
|
15703
15714
|
};
|
|
15704
15715
|
await server.connect(transport);
|
|
15705
15716
|
await transport.handleRequest(req, res, parsedBody);
|
|
@@ -15794,16 +15805,24 @@ function runMCPServer(config) {
|
|
|
15794
15805
|
process.on("SIGINT", () => void shutdown());
|
|
15795
15806
|
return {
|
|
15796
15807
|
invalidateResources() {
|
|
15797
|
-
|
|
15808
|
+
if (sessions.size === 0) return;
|
|
15809
|
+
const timestamp = Date.now();
|
|
15798
15810
|
for (const [, session] of sessions) {
|
|
15799
|
-
|
|
15800
|
-
|
|
15801
|
-
|
|
15811
|
+
for (const [name, handle] of session.resourceHandles) {
|
|
15812
|
+
handle.update({ uri: `ui://${name}-${timestamp}` });
|
|
15813
|
+
}
|
|
15814
|
+
for (const { handle, resourceName, toolMeta } of session.toolHandles) {
|
|
15815
|
+
const newUri = `ui://${resourceName}-${timestamp}`;
|
|
15816
|
+
handle.update({
|
|
15817
|
+
_meta: {
|
|
15818
|
+
...toolMeta,
|
|
15819
|
+
ui: { ...toolMeta.ui, resourceUri: newUri },
|
|
15820
|
+
"ui/resourceUri": newUri
|
|
15821
|
+
}
|
|
15822
|
+
});
|
|
15802
15823
|
}
|
|
15803
15824
|
}
|
|
15804
|
-
|
|
15805
|
-
console.log(`[MCP] Notified ${notified} session(s) of resource changes`);
|
|
15806
|
-
}
|
|
15825
|
+
console.log(`[MCP] Cache-busted ${sessions.size} session(s) with timestamp ${timestamp}`);
|
|
15807
15826
|
}
|
|
15808
15827
|
};
|
|
15809
15828
|
}
|
|
@@ -15914,10 +15933,8 @@ function createMcpHandler(config) {
|
|
|
15914
15933
|
const now = Date.now();
|
|
15915
15934
|
for (const [id2, session] of sessions2) {
|
|
15916
15935
|
if (now - session.lastActivity > SESSION_IDLE_TIMEOUT_MS) {
|
|
15917
|
-
|
|
15918
|
-
session.
|
|
15919
|
-
session.server.close();
|
|
15920
|
-
console.log(`[MCP] Session expired: ${id2.substring(0, 8)}... (${sessions2.size} active)`);
|
|
15936
|
+
console.log(`[MCP] Session expired: ${id2.substring(0, 8)}...`);
|
|
15937
|
+
void session.server.close();
|
|
15921
15938
|
}
|
|
15922
15939
|
}
|
|
15923
15940
|
}, 6e4);
|
|
@@ -15995,13 +16012,12 @@ function createMcpHandler(config) {
|
|
|
15995
16012
|
const id2 = transport.sessionId;
|
|
15996
16013
|
console.error(`[MCP] Transport error${id2 ? ` (${id2.substring(0, 8)}...)` : ""}:`, error);
|
|
15997
16014
|
};
|
|
15998
|
-
transport.onclose =
|
|
16015
|
+
transport.onclose = () => {
|
|
15999
16016
|
const id2 = transport.sessionId;
|
|
16000
16017
|
if (id2 && sessions2.has(id2)) {
|
|
16001
16018
|
sessions2.delete(id2);
|
|
16002
16019
|
console.log(`[MCP] Session closed: ${id2.substring(0, 8)}... (${sessions2.size} active)`);
|
|
16003
16020
|
}
|
|
16004
|
-
await server.close();
|
|
16005
16021
|
};
|
|
16006
16022
|
await server.connect(transport);
|
|
16007
16023
|
await transport.handleRequest(req, res, parsedBody);
|
|
@@ -16017,10 +16033,8 @@ function createHandler(config) {
|
|
|
16017
16033
|
const now = Date.now();
|
|
16018
16034
|
for (const [id2, session] of sessions2) {
|
|
16019
16035
|
if (now - session.lastActivity > SESSION_IDLE_TIMEOUT_MS) {
|
|
16020
|
-
|
|
16021
|
-
session.
|
|
16022
|
-
session.server.close();
|
|
16023
|
-
console.log(`[MCP] Session expired: ${id2.substring(0, 8)}... (${sessions2.size} active)`);
|
|
16036
|
+
console.log(`[MCP] Session expired: ${id2.substring(0, 8)}...`);
|
|
16037
|
+
void session.server.close();
|
|
16024
16038
|
}
|
|
16025
16039
|
}
|
|
16026
16040
|
}, 6e4);
|
|
@@ -16075,12 +16089,11 @@ function createHandler(config) {
|
|
|
16075
16089
|
transport.onerror = (error) => {
|
|
16076
16090
|
console.error("[MCP] Transport error:", error);
|
|
16077
16091
|
};
|
|
16078
|
-
transport.onclose =
|
|
16092
|
+
transport.onclose = () => {
|
|
16079
16093
|
const id2 = transport.sessionId;
|
|
16080
16094
|
if (id2 && sessions2.has(id2)) {
|
|
16081
16095
|
sessions2.delete(id2);
|
|
16082
16096
|
}
|
|
16083
|
-
await server.close();
|
|
16084
16097
|
};
|
|
16085
16098
|
await server.connect(transport);
|
|
16086
16099
|
const response = await transport.handleRequest(req, { parsedBody, authInfo });
|