freestyle-sandboxes 0.0.38 → 0.0.41
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/dist/ai/index.d.cts +3 -3
- package/dist/ai/index.d.mts +3 -3
- package/dist/expo/index.cjs +319 -0
- package/dist/expo/index.d.cts +6 -0
- package/dist/expo/index.d.mts +6 -0
- package/dist/expo/index.mjs +297 -0
- package/dist/{index-CGc0kRd_.cjs → index-BBXyg0JQ.cjs} +5 -9
- package/dist/index-BQHqnjZK.mjs +3231 -0
- package/dist/index-CEEa9WHp.cjs +3238 -0
- package/dist/{index-jh-93svX.mjs → index-DCF70Xbq.mjs} +5 -9
- package/dist/index.d.cts +4 -4
- package/dist/index.d.mts +4 -4
- package/dist/langgraph/index.d.cts +1 -1
- package/dist/langgraph/index.d.mts +1 -1
- package/dist/mastra/index.d.cts +1 -1
- package/dist/mastra/index.d.mts +1 -1
- package/dist/types.gen-1sd31qLV.d.ts +172 -0
- package/dist/types.gen-BCdfx7yt.d.ts +760 -0
- package/dist/types.gen-BaMKzqxQ.d.ts +233 -0
- package/dist/types.gen-BtK6PMQy.d.ts +195 -0
- package/dist/types.gen-C03gaIPq.d.ts +297 -0
- package/dist/types.gen-CMuCas4r.d.ts +183 -0
- package/dist/types.gen-CnEkmbco.d.ts +314 -0
- package/dist/types.gen-DHmdEOOa.d.ts +172 -0
- package/dist/{types.gen-CfrGF-JI.d.ts → types.gen-DLYohMJT.d.ts} +1 -1
- package/dist/types.gen-DbTb_SrD.d.ts +156 -0
- package/dist/types.gen-DkQ-Dbs1.d.ts +764 -0
- package/dist/types.gen-DyY7Deri.d.ts +138 -0
- package/dist/types.gen-MBZCvIhE.d.ts +311 -0
- package/dist/types.gen-YhJAHBw8.d.ts +233 -0
- package/dist/types.gen-cCnnhnB6.d.ts +182 -0
- package/dist/types.gen-uDTr6v-7.d.ts +731 -0
- package/dist/utils/index.d.cts +1 -1
- package/dist/utils/index.d.mts +1 -1
- package/openapi/types.gen.ts +8 -8
- package/openapi.json +1 -4453
- package/package.json +15 -3
- package/src/expo/_expo_internals.ts +389 -0
- package/src/expo/index.ts +26 -0
- package/src/index.ts +3 -3
package/dist/ai/index.d.cts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { F as FreestyleExecuteScriptParamsConfiguration, a as FreestyleExecuteScriptResultSuccess, aR as HandleExecuteScriptError, c as
|
|
1
|
+
import { F as FreestyleExecuteScriptParamsConfiguration, a as FreestyleExecuteScriptResultSuccess, aR as HandleExecuteScriptError, c as FreestyleDeployWebSuccessResponseV2 } from '../types.gen-DkQ-Dbs1.js';
|
|
2
2
|
import { T as Tool, a as ToolExecutionOptions } from '../index.d-CXx1AdyW.js';
|
|
3
3
|
import { z } from 'zod';
|
|
4
4
|
import 'node:http';
|
|
@@ -62,10 +62,10 @@ declare const deployWebTool: (config: FreestyleExecuteScriptParamsConfiguration
|
|
|
62
62
|
files?: Record<string, string>;
|
|
63
63
|
}, {
|
|
64
64
|
files?: Record<string, string>;
|
|
65
|
-
}>, string |
|
|
65
|
+
}>, string | FreestyleDeployWebSuccessResponseV2> & {
|
|
66
66
|
execute: (args: {
|
|
67
67
|
files?: Record<string, string>;
|
|
68
|
-
}, options: ToolExecutionOptions) => PromiseLike<string |
|
|
68
|
+
}, options: ToolExecutionOptions) => PromiseLike<string | FreestyleDeployWebSuccessResponseV2>;
|
|
69
69
|
};
|
|
70
70
|
|
|
71
71
|
export { deployWebTool, executeCodeDescription, executeCodeSchema, executeTool };
|
package/dist/ai/index.d.mts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { F as FreestyleExecuteScriptParamsConfiguration, a as FreestyleExecuteScriptResultSuccess, aR as HandleExecuteScriptError, c as
|
|
1
|
+
import { F as FreestyleExecuteScriptParamsConfiguration, a as FreestyleExecuteScriptResultSuccess, aR as HandleExecuteScriptError, c as FreestyleDeployWebSuccessResponseV2 } from '../types.gen-DkQ-Dbs1.js';
|
|
2
2
|
import { T as Tool, a as ToolExecutionOptions } from '../index.d-CXx1AdyW.js';
|
|
3
3
|
import { z } from 'zod';
|
|
4
4
|
import 'node:http';
|
|
@@ -62,10 +62,10 @@ declare const deployWebTool: (config: FreestyleExecuteScriptParamsConfiguration
|
|
|
62
62
|
files?: Record<string, string>;
|
|
63
63
|
}, {
|
|
64
64
|
files?: Record<string, string>;
|
|
65
|
-
}>, string |
|
|
65
|
+
}>, string | FreestyleDeployWebSuccessResponseV2> & {
|
|
66
66
|
execute: (args: {
|
|
67
67
|
files?: Record<string, string>;
|
|
68
|
-
}, options: ToolExecutionOptions) => PromiseLike<string |
|
|
68
|
+
}, options: ToolExecutionOptions) => PromiseLike<string | FreestyleDeployWebSuccessResponseV2>;
|
|
69
69
|
};
|
|
70
70
|
|
|
71
71
|
export { deployWebTool, executeCodeDescription, executeCodeSchema, executeTool };
|
|
@@ -0,0 +1,319 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
var fs = require('node:fs');
|
|
4
|
+
var path = require('node:path');
|
|
5
|
+
var require$$0 = require('module');
|
|
6
|
+
var process = require('node:process');
|
|
7
|
+
var hono = require('hono');
|
|
8
|
+
var deno = require('hono/deno');
|
|
9
|
+
|
|
10
|
+
var _documentCurrentScript = typeof document !== 'undefined' ? document.currentScript : null;
|
|
11
|
+
function _interopNamespaceDefault(e) {
|
|
12
|
+
var n = Object.create(null);
|
|
13
|
+
if (e) {
|
|
14
|
+
Object.keys(e).forEach(function (k) {
|
|
15
|
+
if (k !== 'default') {
|
|
16
|
+
var d = Object.getOwnPropertyDescriptor(e, k);
|
|
17
|
+
Object.defineProperty(n, k, d.get ? d : {
|
|
18
|
+
enumerable: true,
|
|
19
|
+
get: function () { return e[k]; }
|
|
20
|
+
});
|
|
21
|
+
}
|
|
22
|
+
});
|
|
23
|
+
}
|
|
24
|
+
n.default = e;
|
|
25
|
+
return Object.freeze(n);
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
var path__namespace = /*#__PURE__*/_interopNamespaceDefault(path);
|
|
29
|
+
var process__namespace = /*#__PURE__*/_interopNamespaceDefault(process);
|
|
30
|
+
|
|
31
|
+
const require$1 = require$$0.createRequire((typeof document === 'undefined' ? require('u' + 'rl').pathToFileURL(__filename).href : (_documentCurrentScript && _documentCurrentScript.tagName.toUpperCase() === 'SCRIPT' && _documentCurrentScript.src || new URL('expo/index.cjs', document.baseURI).href)));
|
|
32
|
+
const debug = console.log;
|
|
33
|
+
function getProcessedManifest(path2) {
|
|
34
|
+
const routesManifest = JSON.parse(
|
|
35
|
+
fs.readFileSync(path2, "utf-8")
|
|
36
|
+
);
|
|
37
|
+
const parsed = {
|
|
38
|
+
...routesManifest,
|
|
39
|
+
notFoundRoutes: routesManifest.notFoundRoutes.map((value) => {
|
|
40
|
+
return {
|
|
41
|
+
...value,
|
|
42
|
+
namedRegex: new RegExp(value.namedRegex)
|
|
43
|
+
};
|
|
44
|
+
}),
|
|
45
|
+
apiRoutes: routesManifest.apiRoutes.map((value) => {
|
|
46
|
+
return {
|
|
47
|
+
...value,
|
|
48
|
+
namedRegex: new RegExp(value.namedRegex)
|
|
49
|
+
};
|
|
50
|
+
}),
|
|
51
|
+
htmlRoutes: routesManifest.htmlRoutes.map((value) => {
|
|
52
|
+
return {
|
|
53
|
+
...value,
|
|
54
|
+
namedRegex: new RegExp(value.namedRegex)
|
|
55
|
+
};
|
|
56
|
+
}),
|
|
57
|
+
redirects: routesManifest.redirects?.map((value) => {
|
|
58
|
+
return {
|
|
59
|
+
...value,
|
|
60
|
+
namedRegex: new RegExp(value.namedRegex)
|
|
61
|
+
};
|
|
62
|
+
}),
|
|
63
|
+
rewrites: routesManifest.rewrites?.map((value) => {
|
|
64
|
+
return {
|
|
65
|
+
...value,
|
|
66
|
+
namedRegex: new RegExp(value.namedRegex)
|
|
67
|
+
};
|
|
68
|
+
})
|
|
69
|
+
};
|
|
70
|
+
return parsed;
|
|
71
|
+
}
|
|
72
|
+
function getRoutesManifest(distFolder) {
|
|
73
|
+
return getProcessedManifest(path.join(distFolder, "_expo/routes.json"));
|
|
74
|
+
}
|
|
75
|
+
function createRequestHandler(distFolder, {
|
|
76
|
+
getRoutesManifest: getInternalRoutesManifest,
|
|
77
|
+
getHtml = async (_request, route) => {
|
|
78
|
+
const filePath = path.join(distFolder, route.page + ".html");
|
|
79
|
+
if (fs.existsSync(filePath)) {
|
|
80
|
+
return fs.readFileSync(filePath, "utf-8");
|
|
81
|
+
}
|
|
82
|
+
const hoistedFilePath = route.page.match(/\/index$/) ? path.join(distFolder, route.page.replace(/\/index$/, "") + ".html") : null;
|
|
83
|
+
if (hoistedFilePath && fs.existsSync(hoistedFilePath)) {
|
|
84
|
+
return fs.readFileSync(hoistedFilePath, "utf-8");
|
|
85
|
+
}
|
|
86
|
+
return null;
|
|
87
|
+
},
|
|
88
|
+
getApiRoute = async (route) => {
|
|
89
|
+
const filePath = path.join(distFolder, route.file);
|
|
90
|
+
debug(`Handling API route: ${route.page}: ${filePath}`);
|
|
91
|
+
if (!fs.existsSync(filePath)) {
|
|
92
|
+
return null;
|
|
93
|
+
}
|
|
94
|
+
if (/\.c?js$/.test(filePath)) {
|
|
95
|
+
return require$1(filePath);
|
|
96
|
+
}
|
|
97
|
+
return import(filePath);
|
|
98
|
+
},
|
|
99
|
+
logApiRouteExecutionError = (error) => {
|
|
100
|
+
console.error(error);
|
|
101
|
+
},
|
|
102
|
+
handleApiRouteError = async (error) => {
|
|
103
|
+
if ("statusCode" in error && typeof error.statusCode === "number") {
|
|
104
|
+
return new Response(error.message, {
|
|
105
|
+
status: error.statusCode,
|
|
106
|
+
headers: {
|
|
107
|
+
"Content-Type": "text/plain"
|
|
108
|
+
}
|
|
109
|
+
});
|
|
110
|
+
}
|
|
111
|
+
return new Response("Internal server error", {
|
|
112
|
+
status: 500,
|
|
113
|
+
headers: {
|
|
114
|
+
"Content-Type": "text/plain"
|
|
115
|
+
}
|
|
116
|
+
});
|
|
117
|
+
}
|
|
118
|
+
} = {}) {
|
|
119
|
+
let routesManifest;
|
|
120
|
+
return async function handler(request) {
|
|
121
|
+
if (getInternalRoutesManifest) {
|
|
122
|
+
const manifest = await getInternalRoutesManifest(distFolder);
|
|
123
|
+
if (manifest) {
|
|
124
|
+
routesManifest = manifest;
|
|
125
|
+
} else {
|
|
126
|
+
return new Response("No routes manifest found", {
|
|
127
|
+
status: 404,
|
|
128
|
+
headers: {
|
|
129
|
+
"Content-Type": "text/plain"
|
|
130
|
+
}
|
|
131
|
+
});
|
|
132
|
+
}
|
|
133
|
+
} else if (!routesManifest) {
|
|
134
|
+
routesManifest = getRoutesManifest(distFolder);
|
|
135
|
+
}
|
|
136
|
+
const url = new URL(request.url, "http://expo.dev");
|
|
137
|
+
const sanitizedPathname = url.pathname;
|
|
138
|
+
debug("Request", sanitizedPathname);
|
|
139
|
+
if (routesManifest.rewrites) {
|
|
140
|
+
for (const route of routesManifest.rewrites) {
|
|
141
|
+
if (!route.namedRegex.test(sanitizedPathname)) {
|
|
142
|
+
continue;
|
|
143
|
+
}
|
|
144
|
+
const url2 = getRedirectRewriteLocation(request, route);
|
|
145
|
+
if (url2) {
|
|
146
|
+
request = new Request(
|
|
147
|
+
new URL(url2, new URL(request.url).origin),
|
|
148
|
+
request
|
|
149
|
+
);
|
|
150
|
+
}
|
|
151
|
+
}
|
|
152
|
+
}
|
|
153
|
+
if (routesManifest.redirects) {
|
|
154
|
+
for (const route of routesManifest.redirects) {
|
|
155
|
+
if (!route.namedRegex.test(sanitizedPathname)) {
|
|
156
|
+
continue;
|
|
157
|
+
}
|
|
158
|
+
const Location = getRedirectRewriteLocation(request, route);
|
|
159
|
+
if (Location) {
|
|
160
|
+
debug("Redirecting", Location);
|
|
161
|
+
return new Response(null, {
|
|
162
|
+
status: route.permanent ? 308 : 307,
|
|
163
|
+
headers: {
|
|
164
|
+
Location
|
|
165
|
+
}
|
|
166
|
+
});
|
|
167
|
+
}
|
|
168
|
+
}
|
|
169
|
+
}
|
|
170
|
+
if (request.method === "GET" || request.method === "HEAD") {
|
|
171
|
+
for (const route of routesManifest.htmlRoutes) {
|
|
172
|
+
if (!route.namedRegex.test(sanitizedPathname)) {
|
|
173
|
+
continue;
|
|
174
|
+
}
|
|
175
|
+
updateRequestWithConfig(request, route);
|
|
176
|
+
const contents = await getHtml(request, route);
|
|
177
|
+
if (!contents) {
|
|
178
|
+
return new Response("Not found", {
|
|
179
|
+
status: 404,
|
|
180
|
+
headers: {
|
|
181
|
+
"Content-Type": "text/plain"
|
|
182
|
+
}
|
|
183
|
+
});
|
|
184
|
+
} else if (contents instanceof Response) {
|
|
185
|
+
return contents;
|
|
186
|
+
}
|
|
187
|
+
return new Response(contents, {
|
|
188
|
+
status: 200,
|
|
189
|
+
headers: {
|
|
190
|
+
"Content-Type": "text/html"
|
|
191
|
+
}
|
|
192
|
+
});
|
|
193
|
+
}
|
|
194
|
+
}
|
|
195
|
+
for (const route of routesManifest.apiRoutes) {
|
|
196
|
+
if (!route.namedRegex.test(sanitizedPathname)) {
|
|
197
|
+
continue;
|
|
198
|
+
}
|
|
199
|
+
const func = await getApiRoute(route);
|
|
200
|
+
if (func instanceof Response) {
|
|
201
|
+
return func;
|
|
202
|
+
}
|
|
203
|
+
const routeHandler = func?.[request.method];
|
|
204
|
+
if (!routeHandler) {
|
|
205
|
+
return new Response("Method not allowed", {
|
|
206
|
+
status: 405,
|
|
207
|
+
headers: {
|
|
208
|
+
"Content-Type": "text/plain"
|
|
209
|
+
}
|
|
210
|
+
});
|
|
211
|
+
}
|
|
212
|
+
const params = updateRequestWithConfig(request, route);
|
|
213
|
+
try {
|
|
214
|
+
return await routeHandler(request, params);
|
|
215
|
+
} catch (error) {
|
|
216
|
+
if (error instanceof Error) {
|
|
217
|
+
logApiRouteExecutionError(error);
|
|
218
|
+
}
|
|
219
|
+
return handleApiRouteError(error);
|
|
220
|
+
}
|
|
221
|
+
}
|
|
222
|
+
for (const route of routesManifest.notFoundRoutes) {
|
|
223
|
+
if (!route.namedRegex.test(sanitizedPathname)) {
|
|
224
|
+
continue;
|
|
225
|
+
}
|
|
226
|
+
updateRequestWithConfig(request, route);
|
|
227
|
+
const contents = await getHtml(request, route);
|
|
228
|
+
if (!contents) {
|
|
229
|
+
return new Response("Not found", {
|
|
230
|
+
status: 404,
|
|
231
|
+
headers: {
|
|
232
|
+
"Content-Type": "text/plain"
|
|
233
|
+
}
|
|
234
|
+
});
|
|
235
|
+
} else if (contents instanceof Response) {
|
|
236
|
+
return contents;
|
|
237
|
+
}
|
|
238
|
+
return new Response(contents, {
|
|
239
|
+
status: 404,
|
|
240
|
+
headers: {
|
|
241
|
+
"Content-Type": "text/html"
|
|
242
|
+
}
|
|
243
|
+
});
|
|
244
|
+
}
|
|
245
|
+
const response = new Response("Not found", {
|
|
246
|
+
status: 404,
|
|
247
|
+
headers: {
|
|
248
|
+
"Content-Type": "text/plain"
|
|
249
|
+
}
|
|
250
|
+
});
|
|
251
|
+
return response;
|
|
252
|
+
};
|
|
253
|
+
}
|
|
254
|
+
function matchDynamicName(name) {
|
|
255
|
+
return name.match(/^\[([^[\](?:\.\.\.)]+?)\]$/)?.[1];
|
|
256
|
+
}
|
|
257
|
+
function matchDeepDynamicRouteName(name) {
|
|
258
|
+
return name.match(/^\[\.\.\.([^/]+?)\]$/)?.[1];
|
|
259
|
+
}
|
|
260
|
+
function updateRequestWithConfig(request, config) {
|
|
261
|
+
const params = {};
|
|
262
|
+
const url = new URL(request.url);
|
|
263
|
+
const match = config.namedRegex.exec(url.pathname);
|
|
264
|
+
if (match?.groups) {
|
|
265
|
+
for (const [key, value] of Object.entries(match.groups)) {
|
|
266
|
+
const namedKey = config.routeKeys[key];
|
|
267
|
+
params[namedKey] = value;
|
|
268
|
+
}
|
|
269
|
+
}
|
|
270
|
+
return params;
|
|
271
|
+
}
|
|
272
|
+
function getRedirectRewriteLocation(request, route) {
|
|
273
|
+
if (route.methods) {
|
|
274
|
+
if (!route.methods.includes(request.method)) {
|
|
275
|
+
return;
|
|
276
|
+
}
|
|
277
|
+
}
|
|
278
|
+
const params = updateRequestWithConfig(request, route);
|
|
279
|
+
const urlSearchParams = new URL(request.url).searchParams;
|
|
280
|
+
let location = route.page.split("/").map((segment) => {
|
|
281
|
+
let match = matchDynamicName(segment);
|
|
282
|
+
if (match) {
|
|
283
|
+
const value = params[match];
|
|
284
|
+
delete params[match];
|
|
285
|
+
return value?.split("/")[0];
|
|
286
|
+
}
|
|
287
|
+
match = matchDeepDynamicRouteName(segment);
|
|
288
|
+
if (match) {
|
|
289
|
+
const value = params[match];
|
|
290
|
+
delete params[match];
|
|
291
|
+
return value;
|
|
292
|
+
}
|
|
293
|
+
return segment;
|
|
294
|
+
}).join("/");
|
|
295
|
+
if (Object.keys(params).length > 0 || urlSearchParams.size > 0) {
|
|
296
|
+
location += "?" + new URLSearchParams({
|
|
297
|
+
...params,
|
|
298
|
+
...Object.fromEntries(urlSearchParams.entries())
|
|
299
|
+
}).toString();
|
|
300
|
+
}
|
|
301
|
+
return location;
|
|
302
|
+
}
|
|
303
|
+
|
|
304
|
+
const freestyleExpoServer = ({
|
|
305
|
+
CLIENT_BUILD_DIR = path__namespace.join(process__namespace.cwd(), "dist/client"),
|
|
306
|
+
SERVER_BUILD_DIR = path__namespace.join(process__namespace.cwd(), "dist/server")
|
|
307
|
+
}) => {
|
|
308
|
+
const expoHandler = createRequestHandler(SERVER_BUILD_DIR);
|
|
309
|
+
const app = new hono.Hono();
|
|
310
|
+
app.use("*", deno.serveStatic({ root: CLIENT_BUILD_DIR }));
|
|
311
|
+
app.all("*", async (c, next) => {
|
|
312
|
+
console.log("Request received:", c.req.url);
|
|
313
|
+
const response = await expoHandler(c.req.raw);
|
|
314
|
+
return response;
|
|
315
|
+
});
|
|
316
|
+
Deno.serve(app.fetch);
|
|
317
|
+
};
|
|
318
|
+
|
|
319
|
+
exports.freestyleExpoServer = freestyleExpoServer;
|
|
@@ -0,0 +1,297 @@
|
|
|
1
|
+
import fs from 'node:fs';
|
|
2
|
+
import * as path from 'node:path';
|
|
3
|
+
import path__default from 'node:path';
|
|
4
|
+
import { createRequire } from 'module';
|
|
5
|
+
import * as process from 'node:process';
|
|
6
|
+
import { Hono } from 'hono';
|
|
7
|
+
import { serveStatic } from 'hono/deno';
|
|
8
|
+
|
|
9
|
+
const require = createRequire(import.meta.url);
|
|
10
|
+
const debug = console.log;
|
|
11
|
+
function getProcessedManifest(path2) {
|
|
12
|
+
const routesManifest = JSON.parse(
|
|
13
|
+
fs.readFileSync(path2, "utf-8")
|
|
14
|
+
);
|
|
15
|
+
const parsed = {
|
|
16
|
+
...routesManifest,
|
|
17
|
+
notFoundRoutes: routesManifest.notFoundRoutes.map((value) => {
|
|
18
|
+
return {
|
|
19
|
+
...value,
|
|
20
|
+
namedRegex: new RegExp(value.namedRegex)
|
|
21
|
+
};
|
|
22
|
+
}),
|
|
23
|
+
apiRoutes: routesManifest.apiRoutes.map((value) => {
|
|
24
|
+
return {
|
|
25
|
+
...value,
|
|
26
|
+
namedRegex: new RegExp(value.namedRegex)
|
|
27
|
+
};
|
|
28
|
+
}),
|
|
29
|
+
htmlRoutes: routesManifest.htmlRoutes.map((value) => {
|
|
30
|
+
return {
|
|
31
|
+
...value,
|
|
32
|
+
namedRegex: new RegExp(value.namedRegex)
|
|
33
|
+
};
|
|
34
|
+
}),
|
|
35
|
+
redirects: routesManifest.redirects?.map((value) => {
|
|
36
|
+
return {
|
|
37
|
+
...value,
|
|
38
|
+
namedRegex: new RegExp(value.namedRegex)
|
|
39
|
+
};
|
|
40
|
+
}),
|
|
41
|
+
rewrites: routesManifest.rewrites?.map((value) => {
|
|
42
|
+
return {
|
|
43
|
+
...value,
|
|
44
|
+
namedRegex: new RegExp(value.namedRegex)
|
|
45
|
+
};
|
|
46
|
+
})
|
|
47
|
+
};
|
|
48
|
+
return parsed;
|
|
49
|
+
}
|
|
50
|
+
function getRoutesManifest(distFolder) {
|
|
51
|
+
return getProcessedManifest(path__default.join(distFolder, "_expo/routes.json"));
|
|
52
|
+
}
|
|
53
|
+
function createRequestHandler(distFolder, {
|
|
54
|
+
getRoutesManifest: getInternalRoutesManifest,
|
|
55
|
+
getHtml = async (_request, route) => {
|
|
56
|
+
const filePath = path__default.join(distFolder, route.page + ".html");
|
|
57
|
+
if (fs.existsSync(filePath)) {
|
|
58
|
+
return fs.readFileSync(filePath, "utf-8");
|
|
59
|
+
}
|
|
60
|
+
const hoistedFilePath = route.page.match(/\/index$/) ? path__default.join(distFolder, route.page.replace(/\/index$/, "") + ".html") : null;
|
|
61
|
+
if (hoistedFilePath && fs.existsSync(hoistedFilePath)) {
|
|
62
|
+
return fs.readFileSync(hoistedFilePath, "utf-8");
|
|
63
|
+
}
|
|
64
|
+
return null;
|
|
65
|
+
},
|
|
66
|
+
getApiRoute = async (route) => {
|
|
67
|
+
const filePath = path__default.join(distFolder, route.file);
|
|
68
|
+
debug(`Handling API route: ${route.page}: ${filePath}`);
|
|
69
|
+
if (!fs.existsSync(filePath)) {
|
|
70
|
+
return null;
|
|
71
|
+
}
|
|
72
|
+
if (/\.c?js$/.test(filePath)) {
|
|
73
|
+
return require(filePath);
|
|
74
|
+
}
|
|
75
|
+
return import(filePath);
|
|
76
|
+
},
|
|
77
|
+
logApiRouteExecutionError = (error) => {
|
|
78
|
+
console.error(error);
|
|
79
|
+
},
|
|
80
|
+
handleApiRouteError = async (error) => {
|
|
81
|
+
if ("statusCode" in error && typeof error.statusCode === "number") {
|
|
82
|
+
return new Response(error.message, {
|
|
83
|
+
status: error.statusCode,
|
|
84
|
+
headers: {
|
|
85
|
+
"Content-Type": "text/plain"
|
|
86
|
+
}
|
|
87
|
+
});
|
|
88
|
+
}
|
|
89
|
+
return new Response("Internal server error", {
|
|
90
|
+
status: 500,
|
|
91
|
+
headers: {
|
|
92
|
+
"Content-Type": "text/plain"
|
|
93
|
+
}
|
|
94
|
+
});
|
|
95
|
+
}
|
|
96
|
+
} = {}) {
|
|
97
|
+
let routesManifest;
|
|
98
|
+
return async function handler(request) {
|
|
99
|
+
if (getInternalRoutesManifest) {
|
|
100
|
+
const manifest = await getInternalRoutesManifest(distFolder);
|
|
101
|
+
if (manifest) {
|
|
102
|
+
routesManifest = manifest;
|
|
103
|
+
} else {
|
|
104
|
+
return new Response("No routes manifest found", {
|
|
105
|
+
status: 404,
|
|
106
|
+
headers: {
|
|
107
|
+
"Content-Type": "text/plain"
|
|
108
|
+
}
|
|
109
|
+
});
|
|
110
|
+
}
|
|
111
|
+
} else if (!routesManifest) {
|
|
112
|
+
routesManifest = getRoutesManifest(distFolder);
|
|
113
|
+
}
|
|
114
|
+
const url = new URL(request.url, "http://expo.dev");
|
|
115
|
+
const sanitizedPathname = url.pathname;
|
|
116
|
+
debug("Request", sanitizedPathname);
|
|
117
|
+
if (routesManifest.rewrites) {
|
|
118
|
+
for (const route of routesManifest.rewrites) {
|
|
119
|
+
if (!route.namedRegex.test(sanitizedPathname)) {
|
|
120
|
+
continue;
|
|
121
|
+
}
|
|
122
|
+
const url2 = getRedirectRewriteLocation(request, route);
|
|
123
|
+
if (url2) {
|
|
124
|
+
request = new Request(
|
|
125
|
+
new URL(url2, new URL(request.url).origin),
|
|
126
|
+
request
|
|
127
|
+
);
|
|
128
|
+
}
|
|
129
|
+
}
|
|
130
|
+
}
|
|
131
|
+
if (routesManifest.redirects) {
|
|
132
|
+
for (const route of routesManifest.redirects) {
|
|
133
|
+
if (!route.namedRegex.test(sanitizedPathname)) {
|
|
134
|
+
continue;
|
|
135
|
+
}
|
|
136
|
+
const Location = getRedirectRewriteLocation(request, route);
|
|
137
|
+
if (Location) {
|
|
138
|
+
debug("Redirecting", Location);
|
|
139
|
+
return new Response(null, {
|
|
140
|
+
status: route.permanent ? 308 : 307,
|
|
141
|
+
headers: {
|
|
142
|
+
Location
|
|
143
|
+
}
|
|
144
|
+
});
|
|
145
|
+
}
|
|
146
|
+
}
|
|
147
|
+
}
|
|
148
|
+
if (request.method === "GET" || request.method === "HEAD") {
|
|
149
|
+
for (const route of routesManifest.htmlRoutes) {
|
|
150
|
+
if (!route.namedRegex.test(sanitizedPathname)) {
|
|
151
|
+
continue;
|
|
152
|
+
}
|
|
153
|
+
updateRequestWithConfig(request, route);
|
|
154
|
+
const contents = await getHtml(request, route);
|
|
155
|
+
if (!contents) {
|
|
156
|
+
return new Response("Not found", {
|
|
157
|
+
status: 404,
|
|
158
|
+
headers: {
|
|
159
|
+
"Content-Type": "text/plain"
|
|
160
|
+
}
|
|
161
|
+
});
|
|
162
|
+
} else if (contents instanceof Response) {
|
|
163
|
+
return contents;
|
|
164
|
+
}
|
|
165
|
+
return new Response(contents, {
|
|
166
|
+
status: 200,
|
|
167
|
+
headers: {
|
|
168
|
+
"Content-Type": "text/html"
|
|
169
|
+
}
|
|
170
|
+
});
|
|
171
|
+
}
|
|
172
|
+
}
|
|
173
|
+
for (const route of routesManifest.apiRoutes) {
|
|
174
|
+
if (!route.namedRegex.test(sanitizedPathname)) {
|
|
175
|
+
continue;
|
|
176
|
+
}
|
|
177
|
+
const func = await getApiRoute(route);
|
|
178
|
+
if (func instanceof Response) {
|
|
179
|
+
return func;
|
|
180
|
+
}
|
|
181
|
+
const routeHandler = func?.[request.method];
|
|
182
|
+
if (!routeHandler) {
|
|
183
|
+
return new Response("Method not allowed", {
|
|
184
|
+
status: 405,
|
|
185
|
+
headers: {
|
|
186
|
+
"Content-Type": "text/plain"
|
|
187
|
+
}
|
|
188
|
+
});
|
|
189
|
+
}
|
|
190
|
+
const params = updateRequestWithConfig(request, route);
|
|
191
|
+
try {
|
|
192
|
+
return await routeHandler(request, params);
|
|
193
|
+
} catch (error) {
|
|
194
|
+
if (error instanceof Error) {
|
|
195
|
+
logApiRouteExecutionError(error);
|
|
196
|
+
}
|
|
197
|
+
return handleApiRouteError(error);
|
|
198
|
+
}
|
|
199
|
+
}
|
|
200
|
+
for (const route of routesManifest.notFoundRoutes) {
|
|
201
|
+
if (!route.namedRegex.test(sanitizedPathname)) {
|
|
202
|
+
continue;
|
|
203
|
+
}
|
|
204
|
+
updateRequestWithConfig(request, route);
|
|
205
|
+
const contents = await getHtml(request, route);
|
|
206
|
+
if (!contents) {
|
|
207
|
+
return new Response("Not found", {
|
|
208
|
+
status: 404,
|
|
209
|
+
headers: {
|
|
210
|
+
"Content-Type": "text/plain"
|
|
211
|
+
}
|
|
212
|
+
});
|
|
213
|
+
} else if (contents instanceof Response) {
|
|
214
|
+
return contents;
|
|
215
|
+
}
|
|
216
|
+
return new Response(contents, {
|
|
217
|
+
status: 404,
|
|
218
|
+
headers: {
|
|
219
|
+
"Content-Type": "text/html"
|
|
220
|
+
}
|
|
221
|
+
});
|
|
222
|
+
}
|
|
223
|
+
const response = new Response("Not found", {
|
|
224
|
+
status: 404,
|
|
225
|
+
headers: {
|
|
226
|
+
"Content-Type": "text/plain"
|
|
227
|
+
}
|
|
228
|
+
});
|
|
229
|
+
return response;
|
|
230
|
+
};
|
|
231
|
+
}
|
|
232
|
+
function matchDynamicName(name) {
|
|
233
|
+
return name.match(/^\[([^[\](?:\.\.\.)]+?)\]$/)?.[1];
|
|
234
|
+
}
|
|
235
|
+
function matchDeepDynamicRouteName(name) {
|
|
236
|
+
return name.match(/^\[\.\.\.([^/]+?)\]$/)?.[1];
|
|
237
|
+
}
|
|
238
|
+
function updateRequestWithConfig(request, config) {
|
|
239
|
+
const params = {};
|
|
240
|
+
const url = new URL(request.url);
|
|
241
|
+
const match = config.namedRegex.exec(url.pathname);
|
|
242
|
+
if (match?.groups) {
|
|
243
|
+
for (const [key, value] of Object.entries(match.groups)) {
|
|
244
|
+
const namedKey = config.routeKeys[key];
|
|
245
|
+
params[namedKey] = value;
|
|
246
|
+
}
|
|
247
|
+
}
|
|
248
|
+
return params;
|
|
249
|
+
}
|
|
250
|
+
function getRedirectRewriteLocation(request, route) {
|
|
251
|
+
if (route.methods) {
|
|
252
|
+
if (!route.methods.includes(request.method)) {
|
|
253
|
+
return;
|
|
254
|
+
}
|
|
255
|
+
}
|
|
256
|
+
const params = updateRequestWithConfig(request, route);
|
|
257
|
+
const urlSearchParams = new URL(request.url).searchParams;
|
|
258
|
+
let location = route.page.split("/").map((segment) => {
|
|
259
|
+
let match = matchDynamicName(segment);
|
|
260
|
+
if (match) {
|
|
261
|
+
const value = params[match];
|
|
262
|
+
delete params[match];
|
|
263
|
+
return value?.split("/")[0];
|
|
264
|
+
}
|
|
265
|
+
match = matchDeepDynamicRouteName(segment);
|
|
266
|
+
if (match) {
|
|
267
|
+
const value = params[match];
|
|
268
|
+
delete params[match];
|
|
269
|
+
return value;
|
|
270
|
+
}
|
|
271
|
+
return segment;
|
|
272
|
+
}).join("/");
|
|
273
|
+
if (Object.keys(params).length > 0 || urlSearchParams.size > 0) {
|
|
274
|
+
location += "?" + new URLSearchParams({
|
|
275
|
+
...params,
|
|
276
|
+
...Object.fromEntries(urlSearchParams.entries())
|
|
277
|
+
}).toString();
|
|
278
|
+
}
|
|
279
|
+
return location;
|
|
280
|
+
}
|
|
281
|
+
|
|
282
|
+
const freestyleExpoServer = ({
|
|
283
|
+
CLIENT_BUILD_DIR = path.join(process.cwd(), "dist/client"),
|
|
284
|
+
SERVER_BUILD_DIR = path.join(process.cwd(), "dist/server")
|
|
285
|
+
}) => {
|
|
286
|
+
const expoHandler = createRequestHandler(SERVER_BUILD_DIR);
|
|
287
|
+
const app = new Hono();
|
|
288
|
+
app.use("*", serveStatic({ root: CLIENT_BUILD_DIR }));
|
|
289
|
+
app.all("*", async (c, next) => {
|
|
290
|
+
console.log("Request received:", c.req.url);
|
|
291
|
+
const response = await expoHandler(c.req.raw);
|
|
292
|
+
return response;
|
|
293
|
+
});
|
|
294
|
+
Deno.serve(app.fetch);
|
|
295
|
+
};
|
|
296
|
+
|
|
297
|
+
export { freestyleExpoServer };
|
|
@@ -3169,12 +3169,11 @@ const executeTool = (config) => {
|
|
|
3169
3169
|
return tool({
|
|
3170
3170
|
description: executeCodeDescription(envVars, nodeModules),
|
|
3171
3171
|
parameters: executeCodeSchema,
|
|
3172
|
-
execute: async ({ script, ...otherParams }
|
|
3172
|
+
execute: async ({ script, ...otherParams }) => {
|
|
3173
3173
|
try {
|
|
3174
3174
|
const res = await api.executeScript(script, config);
|
|
3175
3175
|
if (config.onResult) {
|
|
3176
3176
|
await config.onResult({
|
|
3177
|
-
toolCallId,
|
|
3178
3177
|
result: res,
|
|
3179
3178
|
input: {
|
|
3180
3179
|
script,
|
|
@@ -3217,13 +3216,10 @@ ${nodeModules.length > 0 ? `You can use the following node modules: ${nodeModule
|
|
|
3217
3216
|
`)
|
|
3218
3217
|
}),
|
|
3219
3218
|
execute: async ({ files }) => {
|
|
3220
|
-
const new_files = Object.keys(files).reduce(
|
|
3221
|
-
|
|
3222
|
-
|
|
3223
|
-
|
|
3224
|
-
},
|
|
3225
|
-
{}
|
|
3226
|
-
);
|
|
3219
|
+
const new_files = Object.keys(files).reduce((acc, key) => {
|
|
3220
|
+
acc[key] = { content: files[key] };
|
|
3221
|
+
return acc;
|
|
3222
|
+
}, {});
|
|
3227
3223
|
try {
|
|
3228
3224
|
const res = await api.deployWeb(
|
|
3229
3225
|
{
|