sunpeak 0.10.6 → 0.10.7
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/bin/commands/mcp.mjs +213 -46
- package/dist/chatgpt/index.cjs +1 -1
- package/dist/chatgpt/index.js +1 -1
- package/dist/index.cjs +1 -1
- package/dist/index.js +2 -2
- package/dist/mcp/entry.cjs +2 -1
- package/dist/mcp/entry.cjs.map +1 -1
- package/dist/mcp/entry.js +2 -1
- package/dist/mcp/entry.js.map +1 -1
- package/dist/mcp/index.cjs +1 -1
- package/dist/mcp/index.js +1 -1
- package/dist/mcp/types.d.ts +7 -0
- package/dist/{server-CnRhUNGQ.js → server-BLKltt88.js} +124 -28
- package/dist/{server-CnRhUNGQ.js.map → server-BLKltt88.js.map} +1 -1
- package/dist/{server-B-T6Y3-J.cjs → server-D_oRdZjX.cjs} +124 -28
- package/dist/{server-B-T6Y3-J.cjs.map → server-D_oRdZjX.cjs.map} +1 -1
- package/dist/{simulator-url-pSDp_VWO.cjs → simulator-url-B6DZi3vV.cjs} +25 -14
- package/dist/simulator-url-B6DZi3vV.cjs.map +1 -0
- package/dist/{simulator-url-BUKX-wRa.js → simulator-url-izFV6mji.js} +24 -13
- package/dist/simulator-url-izFV6mji.js.map +1 -0
- package/package.json +1 -1
- package/template/dist/albums/albums.js +4 -4
- package/template/dist/albums/albums.json +1 -1
- package/template/dist/carousel/carousel.js +3 -3
- package/template/dist/carousel/carousel.json +1 -1
- package/template/dist/map/map.js +8 -8
- package/template/dist/map/map.json +1 -1
- package/template/dist/review/review.js +3 -3
- package/template/dist/review/review.json +1 -1
- package/template/node_modules/.vite/deps/_metadata.json +22 -22
- package/template/node_modules/.vite/vitest/da39a3ee5e6b4b0d3255bfef95601890afd80709/results.json +1 -1
- package/dist/simulator-url-BUKX-wRa.js.map +0 -1
- package/dist/simulator-url-pSDp_VWO.cjs.map +0 -1
|
@@ -4820,7 +4820,7 @@ union([
|
|
|
4820
4820
|
ListTasksResultSchema,
|
|
4821
4821
|
CreateTaskResultSchema
|
|
4822
4822
|
]);
|
|
4823
|
-
function
|
|
4823
|
+
function readResourceHtmlProd(distPath) {
|
|
4824
4824
|
const htmlPath = path.resolve(distPath);
|
|
4825
4825
|
if (!fs.existsSync(htmlPath)) {
|
|
4826
4826
|
throw new Error(
|
|
@@ -4842,12 +4842,76 @@ ${jsContents}
|
|
|
4842
4842
|
</body>
|
|
4843
4843
|
</html>`;
|
|
4844
4844
|
}
|
|
4845
|
-
function
|
|
4846
|
-
const
|
|
4845
|
+
function getViteResourceHtml(srcPath) {
|
|
4846
|
+
const fileName = srcPath.split("/").pop()?.replace(/-resource\.tsx$/, "") ?? "";
|
|
4847
|
+
const componentName = fileName.split("-").map((part) => part.charAt(0).toUpperCase() + part.slice(1)).join("") + "Resource";
|
|
4848
|
+
const devServerUrl = "http://localhost:6766";
|
|
4849
|
+
const entryParams = new URLSearchParams({ src: srcPath, component: componentName });
|
|
4850
|
+
const virtualModuleUrl = `${devServerUrl}/@id/virtual:sunpeak-entry?${entryParams.toString()}`;
|
|
4851
|
+
return `<!DOCTYPE html>
|
|
4852
|
+
<html>
|
|
4853
|
+
<head>
|
|
4854
|
+
<meta charset="UTF-8">
|
|
4855
|
+
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
|
4856
|
+
</head>
|
|
4857
|
+
<body>
|
|
4858
|
+
<script type="module">
|
|
4859
|
+
import { injectIntoGlobalHook } from "${devServerUrl}/@react-refresh";
|
|
4860
|
+
injectIntoGlobalHook(window);
|
|
4861
|
+
window.$RefreshReg$ = () => {};
|
|
4862
|
+
window.$RefreshSig$ = () => (type) => type;
|
|
4863
|
+
window.__vite_plugin_react_preamble_installed__ = true;
|
|
4864
|
+
<\/script>
|
|
4865
|
+
<script type="module" src="${devServerUrl}/@vite/client"><\/script>
|
|
4866
|
+
<script type="module">
|
|
4867
|
+
// Local network access check (matching skybridge)
|
|
4868
|
+
(async () => {
|
|
4869
|
+
if (!navigator.permissions?.query) return;
|
|
4870
|
+
const protocol = window.location.protocol;
|
|
4871
|
+
if (protocol !== 'http:' && protocol !== 'https:') return;
|
|
4872
|
+
const host = window.location.hostname;
|
|
4873
|
+
const isLoopback = host === 'localhost' || /^127\\.(\\d{1,3})\\.(\\d{1,3})\\.(\\d{1,3})$/.test(host) || host === '::1';
|
|
4874
|
+
if (isLoopback) return;
|
|
4875
|
+
try {
|
|
4876
|
+
const status = await navigator.permissions.query({ name: "local-network-access" });
|
|
4877
|
+
if (status.state === "denied") {
|
|
4878
|
+
document.getElementById('root').innerHTML = '<div style="background:#fef2f2;border:2px solid #ef4444;border-radius:8px;padding:16px;text-align:center;font-family:system-ui,sans-serif;"><div style="color:#ef4444;font-size:18px;font-weight:600;margin-bottom:8px;">Local network access permission is denied</div><div style="color:#ef4444;font-size:14px;">Please enable it in your browser settings. <a href="https://developer.chrome.com/blog/local-network-access" target="_blank" style="color:#ef4444;text-decoration:underline;">Learn more</a></div></div>';
|
|
4879
|
+
}
|
|
4880
|
+
} catch (e) {}
|
|
4881
|
+
})();
|
|
4882
|
+
<\/script>
|
|
4883
|
+
<div id="root"></div>
|
|
4884
|
+
<script type="module" src="${virtualModuleUrl}"><\/script>
|
|
4885
|
+
</body>
|
|
4886
|
+
</html>`;
|
|
4887
|
+
}
|
|
4888
|
+
function getResourceHtml(simulation, viteMode) {
|
|
4889
|
+
if (viteMode && simulation.srcPath) {
|
|
4890
|
+
return getViteResourceHtml(simulation.srcPath);
|
|
4891
|
+
}
|
|
4892
|
+
return readResourceHtmlProd(simulation.distPath);
|
|
4893
|
+
}
|
|
4894
|
+
const DEV_SERVER_URL = "http://localhost:6766";
|
|
4895
|
+
const HMR_WS_URL = "ws://localhost:24678";
|
|
4896
|
+
function injectViteCSP(existingMeta) {
|
|
4897
|
+
const meta = existingMeta ?? {};
|
|
4898
|
+
const widgetCSP = meta["openai/widgetCSP"] ?? {};
|
|
4899
|
+
const existingResourceDomains = widgetCSP["resource_domains"] ?? [];
|
|
4900
|
+
const resourceDomains = existingResourceDomains.includes(DEV_SERVER_URL) ? existingResourceDomains : [...existingResourceDomains, DEV_SERVER_URL];
|
|
4901
|
+
const existingConnectDomains = widgetCSP["connect_domains"] ?? [];
|
|
4902
|
+
const connectDomains = existingConnectDomains.includes(HMR_WS_URL) ? existingConnectDomains : [...existingConnectDomains, HMR_WS_URL];
|
|
4903
|
+
return {
|
|
4904
|
+
...meta,
|
|
4905
|
+
"openai/widgetCSP": {
|
|
4906
|
+
...widgetCSP,
|
|
4907
|
+
resource_domains: resourceDomains,
|
|
4908
|
+
connect_domains: connectDomains
|
|
4909
|
+
}
|
|
4910
|
+
};
|
|
4911
|
+
}
|
|
4912
|
+
function createAppServer(config2, simulations, viteMode) {
|
|
4913
|
+
const { name = "sunpeak-app", version: version2 = "0.1.0" } = config2;
|
|
4847
4914
|
const toolInputParser = z.object({});
|
|
4848
|
-
const resourceContentMap = new Map(
|
|
4849
|
-
simulations.map((simulation) => [simulation.tool.name, readResourceHtml(simulation.distPath)])
|
|
4850
|
-
);
|
|
4851
4915
|
const devTimestamp = Date.now().toString(36);
|
|
4852
4916
|
const resources = simulations.map((simulation) => {
|
|
4853
4917
|
const resource = simulation.resource;
|
|
@@ -4871,11 +4935,13 @@ function createAppServer(config2) {
|
|
|
4871
4935
|
simulation.callToolResult ?? { structuredContent: null, _meta: {} }
|
|
4872
4936
|
])
|
|
4873
4937
|
);
|
|
4874
|
-
const
|
|
4938
|
+
const uriToSimulation = new Map(
|
|
4939
|
+
resources.map((resource, index) => [resource.uri, simulations[index]])
|
|
4940
|
+
);
|
|
4941
|
+
const resourceMetaMap = new Map(
|
|
4875
4942
|
resources.map((resource, index) => [
|
|
4876
4943
|
resource.uri,
|
|
4877
4944
|
{
|
|
4878
|
-
content: resourceContentMap.get(simulations[index].tool.name),
|
|
4879
4945
|
resource,
|
|
4880
4946
|
_meta: simulations[index].resource._meta
|
|
4881
4947
|
}
|
|
@@ -4894,24 +4960,35 @@ function createAppServer(config2) {
|
|
|
4894
4960
|
}
|
|
4895
4961
|
);
|
|
4896
4962
|
server.setRequestHandler(ListResourcesRequestSchema, async (_request) => {
|
|
4897
|
-
console.log(
|
|
4963
|
+
console.log(
|
|
4964
|
+
`[MCP] ListResources → ${resources.length} resource(s)${viteMode ? " (vite mode)" : ""}`
|
|
4965
|
+
);
|
|
4966
|
+
if (viteMode) {
|
|
4967
|
+
const resourcesWithCsp = resources.map((resource) => ({
|
|
4968
|
+
...resource,
|
|
4969
|
+
_meta: injectViteCSP(resource._meta)
|
|
4970
|
+
}));
|
|
4971
|
+
return { resources: resourcesWithCsp };
|
|
4972
|
+
}
|
|
4898
4973
|
return { resources };
|
|
4899
4974
|
});
|
|
4900
4975
|
server.setRequestHandler(ReadResourceRequestSchema, async (request) => {
|
|
4901
4976
|
const requestedUri = request.params.uri;
|
|
4902
|
-
const
|
|
4903
|
-
|
|
4977
|
+
const simulation = uriToSimulation.get(requestedUri);
|
|
4978
|
+
const meta = resourceMetaMap.get(requestedUri);
|
|
4979
|
+
if (!simulation || !meta) {
|
|
4904
4980
|
throw new Error(`Unknown resource: ${requestedUri}`);
|
|
4905
4981
|
}
|
|
4906
|
-
const
|
|
4907
|
-
|
|
4982
|
+
const content = getResourceHtml(simulation, viteMode);
|
|
4983
|
+
const sizeKB = (content.length / 1024).toFixed(1);
|
|
4984
|
+
console.log(`[MCP] ReadResource: ${requestedUri} → ${sizeKB}KB${viteMode ? " (vite)" : ""}`);
|
|
4908
4985
|
return {
|
|
4909
4986
|
contents: [
|
|
4910
4987
|
{
|
|
4911
|
-
uri:
|
|
4912
|
-
mimeType:
|
|
4913
|
-
text:
|
|
4914
|
-
_meta:
|
|
4988
|
+
uri: meta.resource.uri,
|
|
4989
|
+
mimeType: meta.resource.mimeType,
|
|
4990
|
+
text: content,
|
|
4991
|
+
_meta: viteMode ? injectViteCSP(meta._meta) : meta._meta
|
|
4915
4992
|
}
|
|
4916
4993
|
]
|
|
4917
4994
|
};
|
|
@@ -4950,9 +5027,9 @@ function createAppServer(config2) {
|
|
|
4950
5027
|
const sessions = /* @__PURE__ */ new Map();
|
|
4951
5028
|
const ssePath = "/mcp";
|
|
4952
5029
|
const postPath = "/mcp/messages";
|
|
4953
|
-
async function handleSseRequest(res, config2) {
|
|
5030
|
+
async function handleSseRequest(res, config2, simulations, viteMode) {
|
|
4954
5031
|
res.setHeader("Access-Control-Allow-Origin", "*");
|
|
4955
|
-
const server = createAppServer(config2);
|
|
5032
|
+
const server = createAppServer(config2, simulations, viteMode);
|
|
4956
5033
|
const transport = new SSEServerTransport(postPath, res);
|
|
4957
5034
|
const sessionId = transport.sessionId;
|
|
4958
5035
|
sessions.set(sessionId, { server, transport });
|
|
@@ -4978,7 +5055,7 @@ async function handleSseRequest(res, config2) {
|
|
|
4978
5055
|
}
|
|
4979
5056
|
async function handlePostMessage(req, res, url) {
|
|
4980
5057
|
res.setHeader("Access-Control-Allow-Origin", "*");
|
|
4981
|
-
res.setHeader("Access-Control-Allow-Headers", "content-type");
|
|
5058
|
+
res.setHeader("Access-Control-Allow-Headers", "content-type, ngrok-skip-browser-warning");
|
|
4982
5059
|
const sessionId = url.searchParams.get("sessionId");
|
|
4983
5060
|
if (!sessionId) {
|
|
4984
5061
|
res.writeHead(400).end("Missing sessionId query parameter");
|
|
@@ -5001,32 +5078,48 @@ async function handlePostMessage(req, res, url) {
|
|
|
5001
5078
|
function runMCPServer(config2) {
|
|
5002
5079
|
const portEnv = Number(process.env.PORT ?? 6766);
|
|
5003
5080
|
const port = config2.port ?? (Number.isFinite(portEnv) ? portEnv : 6766);
|
|
5081
|
+
const { simulations } = config2;
|
|
5082
|
+
const viteServer = config2.viteServer;
|
|
5083
|
+
const viteMode = !!viteServer;
|
|
5004
5084
|
const httpServer = createServer(async (req, res) => {
|
|
5005
5085
|
if (!req.url) {
|
|
5006
5086
|
res.writeHead(400).end("Missing URL");
|
|
5007
5087
|
return;
|
|
5008
5088
|
}
|
|
5009
5089
|
const url = new URL$1(req.url, `http://${req.headers.host ?? "localhost"}`);
|
|
5010
|
-
|
|
5011
|
-
if (req.method === "OPTIONS" && (url.pathname === ssePath || url.pathname === postPath)) {
|
|
5090
|
+
if (req.method === "OPTIONS") {
|
|
5012
5091
|
res.writeHead(204, {
|
|
5013
5092
|
"Access-Control-Allow-Origin": "*",
|
|
5014
5093
|
"Access-Control-Allow-Methods": "GET, POST, OPTIONS",
|
|
5015
|
-
"Access-Control-Allow-Headers": "content-type"
|
|
5094
|
+
"Access-Control-Allow-Headers": "content-type, ngrok-skip-browser-warning"
|
|
5016
5095
|
});
|
|
5017
5096
|
res.end();
|
|
5018
5097
|
return;
|
|
5019
5098
|
}
|
|
5020
5099
|
if (req.method === "GET" && url.pathname === ssePath) {
|
|
5021
|
-
|
|
5100
|
+
console.log(`[HTTP] ${req.method} ${url.pathname}`);
|
|
5101
|
+
await handleSseRequest(res, config2, simulations, viteMode);
|
|
5022
5102
|
return;
|
|
5023
5103
|
}
|
|
5024
5104
|
if (req.method === "POST" && url.pathname === postPath) {
|
|
5105
|
+
console.log(`[HTTP] ${req.method} ${url.pathname}`);
|
|
5025
5106
|
await handlePostMessage(req, res, url);
|
|
5026
5107
|
return;
|
|
5027
5108
|
}
|
|
5109
|
+
if (viteServer) {
|
|
5110
|
+
res.setHeader("Access-Control-Allow-Origin", "*");
|
|
5111
|
+
res.setHeader("Access-Control-Allow-Headers", "content-type, ngrok-skip-browser-warning");
|
|
5112
|
+
viteServer.middlewares(req, res);
|
|
5113
|
+
return;
|
|
5114
|
+
}
|
|
5115
|
+
console.log(`[HTTP] ${req.method} ${url.pathname} → 404`);
|
|
5028
5116
|
res.writeHead(404).end("Not Found");
|
|
5029
5117
|
});
|
|
5118
|
+
if (viteServer) {
|
|
5119
|
+
httpServer.on("upgrade", (request, socket, head) => {
|
|
5120
|
+
viteServer.ws.handleUpgrade(request, socket, head);
|
|
5121
|
+
});
|
|
5122
|
+
}
|
|
5030
5123
|
httpServer.on("clientError", (err, socket) => {
|
|
5031
5124
|
console.error("HTTP client error", err);
|
|
5032
5125
|
socket.end("HTTP/1.1 400 Bad Request\r\n\r\n");
|
|
@@ -5035,8 +5128,11 @@ function runMCPServer(config2) {
|
|
|
5035
5128
|
console.log(`Sunpeak MCP server listening on http://localhost:${port}`);
|
|
5036
5129
|
console.log(` SSE stream: GET http://localhost:${port}${ssePath}`);
|
|
5037
5130
|
console.log(` Message post endpoint: POST http://localhost:${port}${postPath}?sessionId=...`);
|
|
5131
|
+
if (viteMode) {
|
|
5132
|
+
console.log(` Vite HMR: enabled (source files served with hot reload)`);
|
|
5133
|
+
}
|
|
5038
5134
|
});
|
|
5039
|
-
const shutdown = () => {
|
|
5135
|
+
const shutdown = async () => {
|
|
5040
5136
|
console.log("\nShutting down MCP server...");
|
|
5041
5137
|
httpServer.close(() => {
|
|
5042
5138
|
console.log("MCP server closed");
|
|
@@ -5047,10 +5143,10 @@ function runMCPServer(config2) {
|
|
|
5047
5143
|
process.exit(1);
|
|
5048
5144
|
}, 5e3);
|
|
5049
5145
|
};
|
|
5050
|
-
process.on("SIGTERM", shutdown);
|
|
5051
|
-
process.on("SIGINT", shutdown);
|
|
5146
|
+
process.on("SIGTERM", () => void shutdown());
|
|
5147
|
+
process.on("SIGINT", () => void shutdown());
|
|
5052
5148
|
}
|
|
5053
5149
|
export {
|
|
5054
5150
|
runMCPServer as r
|
|
5055
5151
|
};
|
|
5056
|
-
//# sourceMappingURL=server-
|
|
5152
|
+
//# sourceMappingURL=server-BLKltt88.js.map
|