@maravilla-labs/vite-plugin 4.0.0 → 5.0.0

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.
@@ -66,8 +66,29 @@ async function rebuildWorkflows(opts) {
66
66
  throw err;
67
67
  }
68
68
  }
69
+ async function rebuildMcp(opts) {
70
+ const { buildMcp } = await import("@maravilla-labs/functions");
71
+ const mcpDir = join(opts.projectDir, "mcp");
72
+ const hasRoot = existsSync(join(opts.projectDir, "mcp.ts")) || existsSync(join(opts.projectDir, "mcp.js")) || existsSync(join(opts.projectDir, "mcp.mjs"));
73
+ const hasDir = existsSync(mcpDir);
74
+ if (!hasRoot && !hasDir) return null;
75
+ try {
76
+ mkdirSync(opts.outDir, { recursive: true });
77
+ const manifest = await buildMcp({
78
+ projectDir: opts.projectDir,
79
+ outputDir: opts.outDir,
80
+ production: false,
81
+ minify: false
82
+ });
83
+ return manifest?.tools?.length ?? null;
84
+ } catch (err) {
85
+ opts.log?.(`[maravilla][mcp] build failed: ${err?.message ?? err}`);
86
+ throw err;
87
+ }
88
+ }
69
89
  export {
70
90
  rebuildEvents,
91
+ rebuildMcp,
71
92
  rebuildWorkflows
72
93
  };
73
- //# sourceMappingURL=event-builder-CQL6EAPT.js.map
94
+ //# sourceMappingURL=event-builder-DVDKQWP2.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/event-builder.ts"],"sourcesContent":["/**\n * Dev-mode events + workflows + MCP builder. Replicates what\n * `@maravilla-labs/adapter-core::buildAndIntegrateEvents` /\n * `buildAndIntegrateWorkflows` / `buildAndIntegrateMcp` do at deploy time,\n * MINUS the manifest.json integration step (dev never owns a `manifest.json`\n * — that's the adapter's deploy-time artefact).\n *\n * Output goes to `${outDir}/events.js` + `events.json` (and the workflows /\n * `mcp.js` + `mcp.json` equivalents). The vite-plugin's auto-fire dispatcher\n * (`event-dispatcher.ts`) imports the events bundle; the `dev-server`'s\n * `/api/{events,workflows,mcp}/_reload` endpoints re-read the manifests.\n *\n * MCP matters most here for build-only adapters (React Router): they never\n * emit `mcp.json` during `vite dev`, so without this the dev-server boots with\n * no MCP tools. SvelteKit only appeared to work because a prior `maravilla\n * build` left a stale `mcp.json` around — this makes dev self-sufficient and\n * identical across frameworks.\n */\n\nimport { existsSync, mkdirSync, rmSync, writeFileSync } from 'node:fs';\nimport { join } from 'node:path';\n\ninterface RebuildOptions {\n projectDir: string;\n outDir: string;\n /** transforms block from maravilla.config.ts — drives synthesized handlers */\n transforms?: unknown;\n log?: (msg: string) => void;\n}\n\n/**\n * Rebuild the events bundle in-place. Returns the number of handlers\n * registered, or null if no events to build (no events/ dir, no\n * events.ts, no transforms).\n */\nexport async function rebuildEvents(opts: RebuildOptions): Promise<number | null> {\n const { compileTransforms } = await import('@maravilla-labs/adapter-core');\n const { buildEvents } = await import('@maravilla-labs/functions');\n\n const compiled = compileTransforms(opts.transforms as never);\n\n const eventsDir = join(opts.projectDir, 'events');\n const hasRoot = existsSync(join(opts.projectDir, 'events.ts'))\n || existsSync(join(opts.projectDir, 'events.js'))\n || existsSync(join(opts.projectDir, 'events.mjs'));\n const hasDir = existsSync(eventsDir);\n\n if (!hasRoot && !hasDir && !compiled) return null;\n\n // Materialize compiled transforms next to hand-written sources so\n // discoverEventSources picks them up. Track for rollback.\n const cleanup: Array<() => void> = [];\n if (compiled) {\n const eventsDirExisted = existsSync(eventsDir);\n if (!eventsDirExisted) {\n mkdirSync(eventsDir, { recursive: true });\n cleanup.push(() => {\n try { rmSync(eventsDir, { recursive: false }); } catch { /* not empty — leave */ }\n });\n }\n const generatedPath = join(eventsDir, `${(compiled as { suggestedFileBasename: string }).suggestedFileBasename}.ts`);\n writeFileSync(generatedPath, (compiled as { source: string }).source, 'utf8');\n cleanup.push(() => {\n try { rmSync(generatedPath, { force: true }); } catch { /* ignore */ }\n });\n }\n\n try {\n mkdirSync(opts.outDir, { recursive: true });\n const manifest = await buildEvents({\n projectDir: opts.projectDir,\n outputDir: opts.outDir,\n production: false,\n minify: false,\n });\n return manifest?.handlers.length ?? 0;\n } catch (err) {\n opts.log?.(`[maravilla][events] build failed: ${(err as Error)?.message ?? err}`);\n throw err;\n } finally {\n for (let i = cleanup.length - 1; i >= 0; i -= 1) cleanup[i]!();\n }\n}\n\ninterface RebuildWorkflowsOptions {\n projectDir: string;\n outDir: string;\n log?: (msg: string) => void;\n}\n\n/**\n * Rebuild the workflows bundle in-place. Returns the number of\n * workflows registered, or null if no workflows to build.\n */\nexport async function rebuildWorkflows(opts: RebuildWorkflowsOptions): Promise<number | null> {\n const { buildWorkflows } = await import('@maravilla-labs/functions');\n\n const workflowsDir = join(opts.projectDir, 'workflows');\n const hasRoot = existsSync(join(opts.projectDir, 'workflows.ts'))\n || existsSync(join(opts.projectDir, 'workflows.js'))\n || existsSync(join(opts.projectDir, 'workflows.mjs'));\n const hasDir = existsSync(workflowsDir);\n\n if (!hasRoot && !hasDir) return null;\n\n try {\n mkdirSync(opts.outDir, { recursive: true });\n const manifest = await buildWorkflows({\n projectDir: opts.projectDir,\n outputDir: opts.outDir,\n production: false,\n minify: false,\n });\n return manifest?.workflows?.length ?? 0;\n } catch (err) {\n opts.log?.(`[maravilla][workflows] build failed: ${(err as Error)?.message ?? err}`);\n throw err;\n }\n}\n\ninterface RebuildMcpOptions {\n projectDir: string;\n outDir: string;\n log?: (msg: string) => void;\n}\n\n/**\n * Rebuild the MCP bundle (`mcp.js` + `mcp.json`) in-place from the project's\n * `mcp/` sources. Returns the number of tools, or null if there's no MCP to\n * build (no `mcp/` dir and no `mcp.ts` root). The same `buildMcp` both adapters\n * call at deploy time — so dev is byte-for-byte the same shape as prod.\n *\n * `framework` is intentionally NOT passed: `buildMcp`'s widget step\n * auto-detects it from the project's package.json and gracefully skips widget\n * auto-build if the toolchain can't be resolved, so this stays framework-\n * agnostic (the `maravilla()` plugin is shared by every framework config).\n */\nexport async function rebuildMcp(opts: RebuildMcpOptions): Promise<number | null> {\n const { buildMcp } = await import('@maravilla-labs/functions');\n\n const mcpDir = join(opts.projectDir, 'mcp');\n const hasRoot = existsSync(join(opts.projectDir, 'mcp.ts'))\n || existsSync(join(opts.projectDir, 'mcp.js'))\n || existsSync(join(opts.projectDir, 'mcp.mjs'));\n const hasDir = existsSync(mcpDir);\n\n if (!hasRoot && !hasDir) return null;\n\n try {\n mkdirSync(opts.outDir, { recursive: true });\n const manifest = await buildMcp({\n projectDir: opts.projectDir,\n outputDir: opts.outDir,\n production: false,\n minify: false,\n });\n // buildMcp returns null when it finds no MCP sources after discovery.\n return manifest?.tools?.length ?? null;\n } catch (err) {\n opts.log?.(`[maravilla][mcp] build failed: ${(err as Error)?.message ?? err}`);\n throw err;\n }\n}\n"],"mappings":"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","names":[]}
package/dist/index.js CHANGED
@@ -261,6 +261,15 @@ var DEFAULT_PROXY_PREFIXES = [
261
261
  "/_auth",
262
262
  "/_assets",
263
263
  "/_rt",
264
+ // MCP host + the mandated OAuth discovery docs. The runtime serves these on
265
+ // the dev-server; without proxying them, reaching `/_mcp` (or the
266
+ // `.well-known/*` an MCP client fetches first) through the framework dev
267
+ // server's own port 404s. Mirrors the routes in
268
+ // `crates/dev-server/src/router.rs`.
269
+ "/_mcp",
270
+ "/.well-known/oauth-protected-resource",
271
+ "/.well-known/oauth-authorization-server",
272
+ "/.well-known/openid-configuration",
264
273
  "/api/kv",
265
274
  "/api/db",
266
275
  "/api/storage",
@@ -310,7 +319,7 @@ function maravilla(options = {}) {
310
319
  );
311
320
  } else if (outDir !== RECOMMENDED_OUT_DIR) {
312
321
  console.warn(
313
- `[maravilla] \u26A0 outDir is "${outDir}" \u2014 the dev-server only loads events.json / workflows.json from "${RECOMMENDED_OUT_DIR}/" or "${LEGACY_OUT_DIR}/". Your events + workflows manifests WILL be built but the dev-server WON'T pick them up: silent dispatcher dropout. Set outDir to "${RECOMMENDED_OUT_DIR}" (the default) \u2014 that's where the framework adapter writes too.`
322
+ `[maravilla] \u26A0 outDir is "${outDir}" \u2014 the dev-server only loads events.json / workflows.json / mcp.json from "${RECOMMENDED_OUT_DIR}/" or "${LEGACY_OUT_DIR}/". Your events + workflows + MCP manifests WILL be built but the dev-server WON'T pick them up: silent dropout. Set outDir to "${RECOMMENDED_OUT_DIR}" (the default) \u2014 that's where the framework adapter writes too.`
314
323
  );
315
324
  }
316
325
  const { runWithRequest } = await import("@maravilla-labs/platform");
@@ -334,7 +343,7 @@ function maravilla(options = {}) {
334
343
  });
335
344
  try {
336
345
  const { startEventDispatcher } = await import("./event-dispatcher-PC2QF2CK.js");
337
- const { rebuildEvents, rebuildWorkflows } = await import("./event-builder-CQL6EAPT.js");
346
+ const { rebuildEvents, rebuildWorkflows, rebuildMcp } = await import("./event-builder-DVDKQWP2.js");
338
347
  const { loadMaravillaConfig } = await import("@maravilla-labs/adapter-core");
339
348
  const projectDir = process.cwd();
340
349
  let configCache = {};
@@ -343,9 +352,10 @@ function maravilla(options = {}) {
343
352
  configCache = loaded?.config ?? {};
344
353
  } catch {
345
354
  }
346
- const runRebuild = async (kind) => {
355
+ const runRebuild = async (targets) => {
356
+ const want = new Set(targets);
347
357
  try {
348
- if (kind === "events" || kind === "both") {
358
+ if (want.has("events")) {
349
359
  const n = await rebuildEvents({
350
360
  projectDir,
351
361
  outDir,
@@ -354,7 +364,7 @@ function maravilla(options = {}) {
354
364
  });
355
365
  if (n !== null) console.log(`[maravilla][events] built ${n} handler${n === 1 ? "" : "s"} \u2192 ${outDir}/events.json`);
356
366
  }
357
- if (kind === "workflows" || kind === "both") {
367
+ if (want.has("workflows")) {
358
368
  const n = await rebuildWorkflows({
359
369
  projectDir,
360
370
  outDir,
@@ -362,9 +372,18 @@ function maravilla(options = {}) {
362
372
  });
363
373
  if (n !== null) console.log(`[maravilla][workflows] built ${n} workflow${n === 1 ? "" : "s"} \u2192 ${outDir}/workflows.json`);
364
374
  }
375
+ if (want.has("mcp")) {
376
+ const n = await rebuildMcp({
377
+ projectDir,
378
+ outDir,
379
+ log: (m) => console.warn(m)
380
+ });
381
+ if (n !== null) console.log(`[maravilla][mcp] built ${n} tool${n === 1 ? "" : "s"} \u2192 ${outDir}/mcp.json`);
382
+ }
365
383
  const reloadPaths = [];
366
- if (kind === "events" || kind === "both") reloadPaths.push("/api/events/_reload");
367
- if (kind === "workflows" || kind === "both") reloadPaths.push("/api/workflows/_reload");
384
+ if (want.has("events")) reloadPaths.push("/api/events/_reload");
385
+ if (want.has("workflows")) reloadPaths.push("/api/workflows/_reload");
386
+ if (want.has("mcp")) reloadPaths.push("/api/mcp/_reload");
368
387
  for (const p of reloadPaths) {
369
388
  try {
370
389
  await fetch(`${devServerUrl}${p}`, {
@@ -376,12 +395,12 @@ function maravilla(options = {}) {
376
395
  }
377
396
  } catch (err) {
378
397
  console.error(
379
- `[maravilla][${kind}] rebuild failed:`,
398
+ `[maravilla][${targets.join("+")}] rebuild failed:`,
380
399
  err?.message ?? err
381
400
  );
382
401
  }
383
402
  };
384
- await runRebuild("both");
403
+ await runRebuild(["events", "workflows", "mcp"]);
385
404
  const watchPaths = [
386
405
  "events.ts",
387
406
  "events.js",
@@ -389,27 +408,42 @@ function maravilla(options = {}) {
389
408
  "workflows.ts",
390
409
  "workflows.js",
391
410
  "workflows.mjs",
411
+ "mcp.ts",
412
+ "mcp.js",
413
+ "mcp.mjs",
392
414
  "maravilla.config.ts",
393
415
  "maravilla.config.js",
394
416
  "maravilla.config.mjs"
395
417
  ].map((p) => `${projectDir}/${p}`);
396
- const watchDirs = [`${projectDir}/events`, `${projectDir}/workflows`];
418
+ const watchDirs = [
419
+ `${projectDir}/events`,
420
+ `${projectDir}/workflows`,
421
+ `${projectDir}/mcp`,
422
+ `${projectDir}/mcp-ui`
423
+ ];
397
424
  const fs = await import("fs");
398
425
  let debounce = null;
399
- let pendingKind = "events";
426
+ let pending = /* @__PURE__ */ new Set();
400
427
  const triggerRebuild = (path) => {
401
- const isWorkflow = path.includes("/workflows");
402
428
  const isConfig = path.includes("maravilla.config");
403
- const newKind = isConfig ? "both" : isWorkflow ? "workflows" : "events";
404
- if (pendingKind !== "both" && pendingKind !== newKind) pendingKind = "both";
405
- else if (debounce === null) pendingKind = newKind;
429
+ if (isConfig) {
430
+ pending.add("events");
431
+ pending.add("workflows");
432
+ pending.add("mcp");
433
+ } else if (path.includes("/mcp")) {
434
+ pending.add("mcp");
435
+ } else if (path.includes("/workflows")) {
436
+ pending.add("workflows");
437
+ } else {
438
+ pending.add("events");
439
+ }
406
440
  if (debounce) clearTimeout(debounce);
407
441
  debounce = setTimeout(async () => {
408
- const k = pendingKind;
409
- pendingKind = "events";
442
+ const targets = [...pending];
443
+ pending = /* @__PURE__ */ new Set();
410
444
  debounce = null;
411
- console.log(`[maravilla] source change detected \u2192 rebuilding ${k}`);
412
- await runRebuild(k);
445
+ console.log(`[maravilla] source change detected \u2192 rebuilding ${targets.join("+")}`);
446
+ await runRebuild(targets);
413
447
  }, 200);
414
448
  };
415
449
  const watchers = [];
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/functions.ts","../src/client.ts","../src/index.ts"],"sourcesContent":["import type { Plugin, ViteDevServer } from 'vite';\nimport { buildFunctions, developmentServer } from '@maravilla-labs/functions';\nimport { join } from 'node:path';\n\nexport interface FunctionsPluginOptions {\n functionsDir?: string;\n functionsPort?: number;\n watch?: boolean;\n}\n\n/**\n * Vite plugin for Maravilla functions development\n * Handles building and serving functions with hot reload\n */\nexport function maravillaFunctions(options: FunctionsPluginOptions = {}): Plugin {\n const {\n functionsDir = 'functions',\n functionsPort = 3003,\n watch = true,\n } = options;\n\n let functionsBundle: any = null;\n let cleanupWatcher: (() => void) | null = null;\n\n return {\n name: 'vite-plugin-maravilla-functions',\n \n async configureServer(server: ViteDevServer) {\n const resolvedFunctionsDir = join(server.config.root, functionsDir);\n \n // Check if functions directory exists\n try {\n await import('node:fs/promises').then(fs => fs.access(resolvedFunctionsDir));\n } catch {\n console.log(`[maravilla-functions] No functions directory found at ${resolvedFunctionsDir}`);\n return;\n }\n\n console.log(`[maravilla-functions] Found functions at ${resolvedFunctionsDir}`);\n\n // Build functions initially\n try {\n functionsBundle = await buildFunctions({\n functionsDir: resolvedFunctionsDir,\n outputDir: join(server.config.root, '.maravilla/functions-dev'),\n production: false,\n minify: false,\n });\n\n console.log(`[maravilla-functions] Built ${functionsBundle.functions} functions:`);\n functionsBundle.routes.forEach((route: any) => {\n console.log(` ${route.path} → ${route.name} (${route.methods.join(', ')})`);\n });\n } catch (error) {\n console.error('[maravilla-functions] Build failed:', error);\n return;\n }\n\n // Set up dev server with watcher\n if (watch) {\n const cleanup = await developmentServer({\n functionsDir: resolvedFunctionsDir,\n outputDir: join(server.config.root, '.maravilla/functions-dev'),\n watch: true,\n onRebuild: async () => {\n // Reload functions bundle\n functionsBundle = await buildFunctions({\n functionsDir: resolvedFunctionsDir,\n outputDir: join(server.config.root, '.maravilla/functions-dev'),\n production: false,\n minify: false,\n });\n \n // Notify Vite of the change\n server.ws.send({\n type: 'custom',\n event: 'maravilla:functions-reload',\n data: { routes: functionsBundle.routes }\n });\n }\n });\n cleanupWatcher = cleanup || null;\n }\n\n // Add middleware to handle function requests\n server.middlewares.use(async (req, res, next) => {\n // Only handle /api routes\n if (!req.url?.startsWith('/api')) {\n return next();\n }\n\n // Check if this matches a function route\n const matchedRoute = functionsBundle?.routes.find((route: any) => {\n const routePath = route.path;\n const requestPath = req.url?.split('?')[0];\n return routePath === requestPath || \n (routePath === '/api' && requestPath === '/api') ||\n (routePath === '/api' && requestPath === '/api/');\n });\n\n if (!matchedRoute) {\n return next();\n }\n\n // Check if method is allowed\n const method = req.method?.toUpperCase() || 'GET';\n if (!matchedRoute.methods.includes(method)) {\n res.statusCode = 405;\n res.setHeader('Allow', matchedRoute.methods.join(', '));\n res.setHeader('Content-Type', 'application/json');\n res.end(JSON.stringify({\n error: 'Method not allowed',\n allowed: matchedRoute.methods\n }));\n return;\n }\n\n console.log(`[maravilla-functions] ${method} ${req.url} → ${matchedRoute.name}`);\n\n // For now, execute the function in a simple way\n // In production, this would use the V8 isolate runtime\n try {\n const functionModule = await import(\n join(server.config.root, '.maravilla/functions-dev/functions.js')\n );\n\n // Create a mock Request object\n const url = new URL(req.url!, `http://localhost:${server.config.server?.port || 5173}`);\n const headers = new Headers();\n Object.entries(req.headers).forEach(([key, value]) => {\n if (typeof value === 'string') {\n headers.append(key, value);\n } else if (Array.isArray(value)) {\n value.forEach(v => headers.append(key, v));\n }\n });\n\n // Get body if present\n let body = null;\n if (req.method && ['POST', 'PUT', 'PATCH'].includes(req.method)) {\n const MAX_BODY_SIZE = 10 * 1024 * 1024; // 10MB\n body = await new Promise<string>((resolve, reject) => {\n let data = '';\n let size = 0;\n req.on('data', (chunk: Buffer | string) => {\n size += typeof chunk === 'string' ? Buffer.byteLength(chunk) : chunk.length;\n if (size > MAX_BODY_SIZE) {\n req.destroy(new Error('Request body too large'));\n reject(new Error('Request body too large'));\n return;\n }\n data += chunk;\n });\n req.on('end', () => resolve(data));\n req.on('error', reject);\n }).catch((err) => {\n res.statusCode = 413;\n res.setHeader('Content-Type', 'application/json');\n res.end(JSON.stringify({ error: 'Payload too large', message: err.message }));\n return null;\n });\n if (body === null) return;\n }\n\n const request = {\n url: url.toString(),\n method: req.method || 'GET',\n headers,\n json: body ? () => Promise.resolve(JSON.parse(body)) : undefined,\n text: () => Promise.resolve(body || ''),\n };\n\n // Call the function handler\n const response = await functionModule.handleFunctionRequest(request);\n\n // Send response\n res.statusCode = response.status || 200;\n Object.entries(response.headers || {}).forEach(([key, value]) => {\n res.setHeader(key, value as string);\n });\n \n if (response instanceof Response) {\n const responseBody = await response.text();\n res.end(responseBody);\n } else {\n res.end(JSON.stringify(response));\n }\n } catch (error: any) {\n console.error('[maravilla-functions] Execution error:', error);\n res.statusCode = 500;\n res.setHeader('Content-Type', 'application/json');\n res.end(JSON.stringify({\n error: 'Function execution failed',\n message: error.message,\n stack: process.env.NODE_ENV === 'development' ? error.stack : undefined\n }));\n }\n });\n },\n\n async closeBundle() {\n if (cleanupWatcher) {\n cleanupWatcher();\n }\n }\n };\n}","/**\n * Platform client for communicating with the dev server\n */\n\nexport interface PlatformClient {\n kv: KvClient;\n db: DbClient;\n}\n\nexport interface KvClient {\n get(namespace: string, key: string): Promise<any>;\n put(namespace: string, key: string, value: any, ttl?: number): Promise<void>;\n delete(namespace: string, key: string): Promise<void>;\n list(namespace: string, options?: KvListOptions): Promise<KvListResponse>;\n}\n\nexport interface DbClient {\n find(collection: string, filter?: any, options?: DbFindOptions): Promise<any[]>;\n findOne(collection: string, filter: any): Promise<any | null>;\n insertOne(collection: string, document: any): Promise<string>;\n updateOne(collection: string, filter: any, update: any): Promise<{ modified: number }>;\n deleteOne(collection: string, filter: any): Promise<{ deleted: number }>;\n}\n\nexport interface KvListOptions {\n prefix?: string;\n limit?: number;\n cursor?: string;\n}\n\nexport interface KvListResponse {\n success: boolean;\n result: Array<{ name: string; expiration?: number; metadata?: any }>;\n result_info: {\n count: number;\n cursor?: string;\n };\n}\n\nexport interface DbFindOptions {\n limit?: number;\n skip?: number;\n sort?: any;\n}\n\nexport function createPlatformClient(baseUrl: string, tenant?: string): PlatformClient {\n const tenantId = tenant || 'dev-tenant';\n const headers = {\n 'Content-Type': 'application/json',\n 'X-Tenant-Id': tenantId,\n };\n\n const fetchWithError = async (url: string, options: RequestInit = {}) => {\n try {\n const response = await fetch(url, {\n ...options,\n headers: {\n ...headers,\n ...options.headers,\n },\n });\n\n if (!response.ok && response.status !== 404) {\n const error = await response.text();\n throw new Error(`Platform API error: ${response.status} - ${error}`);\n }\n\n return response;\n } catch (error) {\n if (error instanceof TypeError && error.message.includes('fetch')) {\n throw new Error(\n `Failed to connect to Maravilla dev server at ${baseUrl}. ` +\n 'Please ensure the dev server is running (cargo run -p dev-server)'\n );\n }\n throw error;\n }\n };\n\n const kv: KvClient = {\n async get(namespace: string, key: string) {\n const response = await fetchWithError(`${baseUrl}/api/kv/${namespace}/${key}`);\n if (response.status === 404) return null;\n return response.json();\n },\n\n async put(namespace: string, key: string, value: any, ttl?: number) {\n const requestHeaders: Record<string, string> = { ...headers };\n if (ttl) {\n requestHeaders['X-TTL'] = ttl.toString();\n }\n\n await fetchWithError(`${baseUrl}/api/kv/${namespace}/${key}`, {\n method: 'PUT',\n headers: requestHeaders,\n body: JSON.stringify(value),\n });\n },\n\n async delete(namespace: string, key: string) {\n await fetchWithError(`${baseUrl}/api/kv/${namespace}/${key}`, {\n method: 'DELETE',\n });\n },\n\n async list(namespace: string, options: KvListOptions = {}) {\n const response = await fetchWithError(`${baseUrl}/api/kv/${namespace}`, {\n method: 'POST',\n body: JSON.stringify(options),\n });\n return response.json() as Promise<KvListResponse>;\n },\n };\n\n const db: DbClient = {\n async find(collection: string, filter: any = {}, options: DbFindOptions = {}) {\n const response = await fetchWithError(`${baseUrl}/api/db/${collection}`, {\n method: 'POST',\n body: JSON.stringify({ filter, options }),\n });\n return response.json() as Promise<any[]>;\n },\n\n async findOne(collection: string, filter: any) {\n const response = await fetchWithError(`${baseUrl}/api/db/${collection}/findOne`, {\n method: 'POST',\n body: JSON.stringify(filter),\n });\n if (response.status === 404) return null;\n return response.json();\n },\n\n async insertOne(collection: string, document: any) {\n const response = await fetchWithError(`${baseUrl}/api/db/${collection}`, {\n method: 'PUT',\n body: JSON.stringify(document),\n });\n const result = await response.json() as { id: string };\n return result.id;\n },\n\n async updateOne(collection: string, filter: any, update: any) {\n const response = await fetchWithError(`${baseUrl}/api/db/${collection}/update`, {\n method: 'POST',\n body: JSON.stringify({ filter, update }),\n });\n return response.json() as Promise<{ modified: number }>;\n },\n\n async deleteOne(collection: string, filter: any) {\n const response = await fetchWithError(`${baseUrl}/api/db/${collection}/delete`, {\n method: 'DELETE',\n body: JSON.stringify(filter),\n });\n return response.json() as Promise<{ deleted: number }>;\n },\n };\n\n return { kv, db };\n}","import type { Plugin, ProxyOptions } from 'vite';\n\nexport interface MaravillaPluginOptions {\n /**\n * URL of the Maravilla dev server. Used both for env-var injection and\n * as the proxy target for `/_auth`, `/_assets`, `/_rt`, and `/api`.\n * @default 'http://localhost:3001'\n */\n devServerUrl?: string;\n\n /**\n * Tenant ID for development. Must match the dev-server's tenant id —\n * `crates/dev-server/src/types.rs::extract_tenant_id` defaults to\n * `dev-tenant-001` when no `X-Tenant-Id` header is supplied, and\n * storage/db/etc. publish REN events keyed by the dev-server's\n * `TenantContext.tenant_id` (also `dev-tenant-001`). If this option\n * doesn't match, the dispatcher's SSE subscription lands on a\n * different broadcast channel and no events ever fire.\n * @default 'dev-tenant-001'\n */\n tenant?: string;\n\n /**\n * Extra URL prefixes to forward to the platform dev server, in addition\n * to the defaults (`/_auth`, `/_assets`, `/_rt`, `/api`). Each prefix is\n * proxied with `changeOrigin: true`. Use this for custom platform routes.\n */\n additionalProxies?: string[];\n\n /**\n * Disable the dev-server proxy entirely. Useful if your project routes\n * platform requests through some other mechanism.\n * @default false\n */\n disableProxy?: boolean;\n\n /**\n * Output directory for events.js / events.json / workflows.js /\n * workflows.json. Matches the framework adapter's `out` option so dev\n * re-uses the same artefacts.\n *\n * The dev-server (`crates/dev-server/src/server.rs`) only scans\n * `${cwd}/build/` and `${cwd}/.maravilla/` for these manifests. Any\n * other value causes silent dispatcher dropout — the plugin warns at\n * startup. `'build'` is recommended; `'.maravilla'` works but\n * conflates build output with the runtime's pipeline/storage state.\n *\n * @default 'build'\n */\n outDir?: string;\n}\n\n/**\n * URL prefixes the dev-server owns. Anything the browser navigates to\n * directly (auth pages, assets) or upgrades (realtime ws) must be proxied\n * here so it lands on the platform server instead of the framework dev\n * server. Mirrors the prefixes registered in\n * `crates/dev-server/src/router.rs`.\n *\n * `/api/*` is intentionally enumerated by sub-prefix instead of the\n * blanket `/api`. The framework's own `+server.ts` routes (e.g.\n * `src/routes/api/v/[...key]/+server.ts` in demo's photo proxy) live\n * under `/api/...` too — proxying them all to the dev-server would\n * 404 every tenant-defined API route. Each entry below corresponds to\n * a router.rs registration.\n */\nconst DEFAULT_PROXY_PREFIXES = [\n '/_auth',\n '/_assets',\n '/_rt',\n '/api/kv',\n '/api/db',\n '/api/storage',\n '/api/realtime',\n '/api/workflows',\n '/api/push',\n '/api/media',\n '/api/maravilla',\n '/api/platform',\n '/api/tenant',\n '/api/events',\n] as const;\n\nexport function maravilla(options: MaravillaPluginOptions = {}): Plugin {\n const devServerUrl = options.devServerUrl || 'http://localhost:3001';\n const tenant = options.tenant || 'dev-tenant-001';\n const disableProxy = options.disableProxy ?? false;\n const additionalProxies = options.additionalProxies ?? [];\n const outDir = options.outDir || 'build';\n\n return {\n name: 'vite-plugin-maravilla',\n\n config() {\n if (disableProxy) return undefined;\n const proxy: Record<string, ProxyOptions> = {};\n for (const prefix of [...DEFAULT_PROXY_PREFIXES, ...additionalProxies]) {\n // `/_rt/*` includes the WebSocket upgrade path `/_rt/ws`; enabling\n // `ws: true` is harmless for the plain HTTP routes under `/_rt`.\n proxy[prefix] = {\n target: devServerUrl,\n changeOrigin: true,\n ws: prefix === '/_rt',\n };\n }\n return { server: { proxy } };\n },\n\n async configureServer(server) {\n // Set environment variables that @maravilla/platform will use\n process.env.MARAVILLA_DEV_SERVER = devServerUrl;\n process.env.MARAVILLA_TENANT = tenant;\n\n console.log(`[maravilla] Platform APIs configured for ${devServerUrl}`);\n console.log('[maravilla] Using tenant:', tenant);\n if (!disableProxy) {\n const proxied = [...DEFAULT_PROXY_PREFIXES, ...additionalProxies].join(', ');\n console.log(`[maravilla] Proxying ${proxied} → ${devServerUrl}`);\n }\n\n // The dev-server only scans `${cwd}/build/` and `${cwd}/.maravilla/`\n // when loading events.json / workflows.json (see\n // crates/dev-server/src/server.rs). `build/` is the recommended\n // location — `.maravilla/` is where the runtime keeps pipeline state\n // and local object storage, so mixing build artefacts in there\n // works but conflates two concerns. Warn loudly on any other value.\n const RECOMMENDED_OUT_DIR = 'build';\n const LEGACY_OUT_DIR = '.maravilla';\n if (outDir === LEGACY_OUT_DIR) {\n console.warn(\n `[maravilla] ⓘ outDir is \"${LEGACY_OUT_DIR}\" — works, but that path ` +\n `also holds the runtime's pipeline state + local storage. ` +\n `Prefer \"${RECOMMENDED_OUT_DIR}\" so build artefacts stay separate.`,\n );\n } else if (outDir !== RECOMMENDED_OUT_DIR) {\n console.warn(\n `[maravilla] ⚠ outDir is \"${outDir}\" — the dev-server only loads ` +\n `events.json / workflows.json from \"${RECOMMENDED_OUT_DIR}/\" or ` +\n `\"${LEGACY_OUT_DIR}/\". Your events + workflows manifests WILL ` +\n `be built but the dev-server WON'T pick them up: silent ` +\n `dispatcher dropout. Set outDir to \"${RECOMMENDED_OUT_DIR}\" ` +\n `(the default) — that's where the framework adapter writes too.`,\n );\n }\n\n // Auto-open a per-request AsyncLocalStorage scope before any\n // framework hook runs. This is the dev-mode equivalent of the\n // runtime's per-request REQUEST_CTX (tokio::task_local! at\n // crates/runtime/src/request_ctx.rs). With this in place,\n // tenant code calls `platform.auth.setCurrentUser(token)` from\n // SvelteKit's `handle` hook (or RR/Remix loaders) without any\n // Maravilla-specific wrapper — same code as prod.\n //\n // Loaded via dynamic import so non-Maravilla apps that pull\n // this plugin in for the proxy alone don't pay the cost until\n // a request actually arrives.\n const { runWithRequest } = await import('@maravilla-labs/platform');\n server.middlewares.use((_req, _res, next) => {\n runWithRequest(() => {\n next();\n }).catch((err) => {\n // Connect's next() doesn't return a Promise we can await;\n // any unhandled error from downstream surfaces here only\n // if runWithRequest's own machinery rejects. Re-throw on\n // the next tick so it shows up in the dev console.\n setImmediate(() => { throw err; });\n });\n });\n\n // Hook into SSR module resolution to ensure platform is available\n server.ssrLoadModule = new Proxy(server.ssrLoadModule, {\n async apply(target, thisArg, args) {\n const result = await Reflect.apply(target, thisArg, args);\n\n // Clear platform cache before each SSR module load to ensure fresh instance\n if ((globalThis as any).__maravilla_platform) {\n delete (globalThis as any).__maravilla_platform;\n }\n\n return result;\n }\n });\n\n // Dev-mode events auto-fire: rebuild the events + workflows\n // bundle on startup (and on file changes), then run the\n // dispatcher that subscribes to dev-server REN SSE and invokes\n // matching handlers. Mirrors prod's `EventDispatcher` so\n // STORAGE.put / KV.put / etc. on a configured pattern auto-fires\n // without explicit calls from app code.\n try {\n const { startEventDispatcher } = await import('./event-dispatcher.js');\n const { rebuildEvents, rebuildWorkflows } = await import('./event-builder.js');\n const { loadMaravillaConfig } = await import('@maravilla-labs/adapter-core');\n const projectDir = process.cwd();\n\n // Lazy-load config once. Source-of-truth for the transforms block.\n let configCache: { transforms?: unknown } = {};\n try {\n const loaded = await loadMaravillaConfig(projectDir);\n configCache = (loaded?.config ?? {}) as { transforms?: unknown };\n } catch {\n // Missing/invalid config is fine — tenant just won't have\n // synthesized transforms handlers.\n }\n\n const runRebuild = async (kind: 'events' | 'workflows' | 'both') => {\n try {\n if (kind === 'events' || kind === 'both') {\n const n = await rebuildEvents({\n projectDir,\n outDir,\n transforms: configCache.transforms,\n log: (m) => console.warn(m),\n });\n if (n !== null) console.log(`[maravilla][events] built ${n} handler${n === 1 ? '' : 's'} → ${outDir}/events.json`);\n }\n if (kind === 'workflows' || kind === 'both') {\n const n = await rebuildWorkflows({\n projectDir,\n outDir,\n log: (m) => console.warn(m),\n });\n if (n !== null) console.log(`[maravilla][workflows] built ${n} workflow${n === 1 ? '' : 's'} → ${outDir}/workflows.json`);\n }\n // Tell dev-server to re-read its events / workflows manifests.\n // Both endpoints are safe no-ops when the corresponding manifest\n // file doesn't exist — the dev-server returns 404 and falls back\n // to whatever it already had.\n const reloadPaths: string[] = [];\n if (kind === 'events' || kind === 'both') reloadPaths.push('/api/events/_reload');\n if (kind === 'workflows' || kind === 'both') reloadPaths.push('/api/workflows/_reload');\n for (const p of reloadPaths) {\n try {\n await fetch(`${devServerUrl}${p}`, {\n method: 'POST',\n headers: { 'Content-Type': 'application/json', 'X-Tenant-Id': tenant },\n });\n } catch {\n // dev-server may not be up yet on first run — fine, it\n // loads the manifest at boot anyway.\n }\n }\n } catch (err) {\n console.error(\n `[maravilla][${kind}] rebuild failed:`,\n (err as Error)?.message ?? err,\n );\n }\n };\n\n // Initial build before the dispatcher attaches its file watcher.\n await runRebuild('both');\n\n // Watch tenant source files. Debounced so a single editor save\n // doesn't trigger multiple rebuilds while esbuild is mid-write.\n const watchPaths = [\n 'events.ts', 'events.js', 'events.mjs',\n 'workflows.ts', 'workflows.js', 'workflows.mjs',\n 'maravilla.config.ts', 'maravilla.config.js', 'maravilla.config.mjs',\n ].map((p) => `${projectDir}/${p}`);\n // Add directory paths\n const watchDirs = [`${projectDir}/events`, `${projectDir}/workflows`];\n\n const fs = await import('node:fs');\n let debounce: NodeJS.Timeout | null = null;\n let pendingKind: 'events' | 'workflows' | 'both' = 'events';\n const triggerRebuild = (path: string) => {\n const isWorkflow = path.includes('/workflows');\n const isConfig = path.includes('maravilla.config');\n // Config changes affect both since transforms compile into events\n // and (in future) other declarative blocks may affect workflows.\n const newKind: 'events' | 'workflows' | 'both' =\n isConfig ? 'both' : isWorkflow ? 'workflows' : 'events';\n if (pendingKind !== 'both' && pendingKind !== newKind) pendingKind = 'both';\n else if (debounce === null) pendingKind = newKind;\n if (debounce) clearTimeout(debounce);\n debounce = setTimeout(async () => {\n const k = pendingKind;\n pendingKind = 'events';\n debounce = null;\n console.log(`[maravilla] source change detected → rebuilding ${k}`);\n await runRebuild(k);\n }, 200);\n };\n const watchers: Array<{ close: () => void }> = [];\n for (const p of watchPaths) {\n if (!fs.existsSync(p)) continue;\n try {\n watchers.push(fs.watch(p, { persistent: false }, () => triggerRebuild(p)));\n } catch { /* skip files that can't be watched */ }\n }\n // Recursive directory watchers. `fs.watch` doesn't support adding\n // a watcher to a non-existent directory — and unlike chokidar, won't\n // pick up the directory if it appears later. So if events/ or\n // workflows/ isn't there at boot, dropping a file inside it later\n // won't trigger any rebuild until the next `maravilla dev` restart.\n // We warn loudly when that's the case so users don't lose time.\n for (const d of watchDirs) {\n const dirName = d.slice(projectDir.length + 1);\n if (!fs.existsSync(d)) {\n console.warn(\n `[maravilla] ⚠ ${dirName}/ not present at startup — handlers/workflows ` +\n `you add later won't hot-rebuild until you restart maravilla dev. ` +\n `Create ${dirName}/ before next start to enable live rebuild.`,\n );\n continue;\n }\n try {\n watchers.push(fs.watch(d, { persistent: false, recursive: true }, (_evt, fname) => {\n if (fname) triggerRebuild(`${d}/${fname}`);\n }));\n } catch (e) {\n console.warn(\n `[maravilla] ⚠ failed to attach watcher to ${dirName}/: ${(e as Error)?.message ?? e}. ` +\n `Live rebuild for this directory is disabled — restart maravilla dev to pick up changes.`,\n );\n }\n }\n\n const teardown = await startEventDispatcher({\n projectDir,\n outDir,\n devServerUrl,\n tenant,\n });\n // Vite's `server.httpServer.once('close')` fires on `vite dev` exit.\n server.httpServer?.once('close', () => {\n for (const w of watchers) {\n try { w.close(); } catch { /* ignore */ }\n }\n if (debounce) clearTimeout(debounce);\n teardown();\n });\n } catch (err) {\n console.error(\n '[maravilla][events] failed to start dispatcher:',\n (err as Error)?.message ?? err,\n );\n }\n }\n };\n}\n\n// Functions plugin\nexport { maravillaFunctions } from './functions.js';\nexport type { FunctionsPluginOptions } from './functions.js';\n\n// Legacy exports for backwards compatibility\nexport { createPlatformClient } from './client.js';\nexport type { PlatformClient, KvClient, DbClient } from './client.js';\n"],"mappings":"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","names":[]}
1
+ {"version":3,"sources":["../src/functions.ts","../src/client.ts","../src/index.ts"],"sourcesContent":["import type { Plugin, ViteDevServer } from 'vite';\nimport { buildFunctions, developmentServer } from '@maravilla-labs/functions';\nimport { join } from 'node:path';\n\nexport interface FunctionsPluginOptions {\n functionsDir?: string;\n functionsPort?: number;\n watch?: boolean;\n}\n\n/**\n * Vite plugin for Maravilla functions development\n * Handles building and serving functions with hot reload\n */\nexport function maravillaFunctions(options: FunctionsPluginOptions = {}): Plugin {\n const {\n functionsDir = 'functions',\n functionsPort = 3003,\n watch = true,\n } = options;\n\n let functionsBundle: any = null;\n let cleanupWatcher: (() => void) | null = null;\n\n return {\n name: 'vite-plugin-maravilla-functions',\n \n async configureServer(server: ViteDevServer) {\n const resolvedFunctionsDir = join(server.config.root, functionsDir);\n \n // Check if functions directory exists\n try {\n await import('node:fs/promises').then(fs => fs.access(resolvedFunctionsDir));\n } catch {\n console.log(`[maravilla-functions] No functions directory found at ${resolvedFunctionsDir}`);\n return;\n }\n\n console.log(`[maravilla-functions] Found functions at ${resolvedFunctionsDir}`);\n\n // Build functions initially\n try {\n functionsBundle = await buildFunctions({\n functionsDir: resolvedFunctionsDir,\n outputDir: join(server.config.root, '.maravilla/functions-dev'),\n production: false,\n minify: false,\n });\n\n console.log(`[maravilla-functions] Built ${functionsBundle.functions} functions:`);\n functionsBundle.routes.forEach((route: any) => {\n console.log(` ${route.path} → ${route.name} (${route.methods.join(', ')})`);\n });\n } catch (error) {\n console.error('[maravilla-functions] Build failed:', error);\n return;\n }\n\n // Set up dev server with watcher\n if (watch) {\n const cleanup = await developmentServer({\n functionsDir: resolvedFunctionsDir,\n outputDir: join(server.config.root, '.maravilla/functions-dev'),\n watch: true,\n onRebuild: async () => {\n // Reload functions bundle\n functionsBundle = await buildFunctions({\n functionsDir: resolvedFunctionsDir,\n outputDir: join(server.config.root, '.maravilla/functions-dev'),\n production: false,\n minify: false,\n });\n \n // Notify Vite of the change\n server.ws.send({\n type: 'custom',\n event: 'maravilla:functions-reload',\n data: { routes: functionsBundle.routes }\n });\n }\n });\n cleanupWatcher = cleanup || null;\n }\n\n // Add middleware to handle function requests\n server.middlewares.use(async (req, res, next) => {\n // Only handle /api routes\n if (!req.url?.startsWith('/api')) {\n return next();\n }\n\n // Check if this matches a function route\n const matchedRoute = functionsBundle?.routes.find((route: any) => {\n const routePath = route.path;\n const requestPath = req.url?.split('?')[0];\n return routePath === requestPath || \n (routePath === '/api' && requestPath === '/api') ||\n (routePath === '/api' && requestPath === '/api/');\n });\n\n if (!matchedRoute) {\n return next();\n }\n\n // Check if method is allowed\n const method = req.method?.toUpperCase() || 'GET';\n if (!matchedRoute.methods.includes(method)) {\n res.statusCode = 405;\n res.setHeader('Allow', matchedRoute.methods.join(', '));\n res.setHeader('Content-Type', 'application/json');\n res.end(JSON.stringify({\n error: 'Method not allowed',\n allowed: matchedRoute.methods\n }));\n return;\n }\n\n console.log(`[maravilla-functions] ${method} ${req.url} → ${matchedRoute.name}`);\n\n // For now, execute the function in a simple way\n // In production, this would use the V8 isolate runtime\n try {\n const functionModule = await import(\n join(server.config.root, '.maravilla/functions-dev/functions.js')\n );\n\n // Create a mock Request object\n const url = new URL(req.url!, `http://localhost:${server.config.server?.port || 5173}`);\n const headers = new Headers();\n Object.entries(req.headers).forEach(([key, value]) => {\n if (typeof value === 'string') {\n headers.append(key, value);\n } else if (Array.isArray(value)) {\n value.forEach(v => headers.append(key, v));\n }\n });\n\n // Get body if present\n let body = null;\n if (req.method && ['POST', 'PUT', 'PATCH'].includes(req.method)) {\n const MAX_BODY_SIZE = 10 * 1024 * 1024; // 10MB\n body = await new Promise<string>((resolve, reject) => {\n let data = '';\n let size = 0;\n req.on('data', (chunk: Buffer | string) => {\n size += typeof chunk === 'string' ? Buffer.byteLength(chunk) : chunk.length;\n if (size > MAX_BODY_SIZE) {\n req.destroy(new Error('Request body too large'));\n reject(new Error('Request body too large'));\n return;\n }\n data += chunk;\n });\n req.on('end', () => resolve(data));\n req.on('error', reject);\n }).catch((err) => {\n res.statusCode = 413;\n res.setHeader('Content-Type', 'application/json');\n res.end(JSON.stringify({ error: 'Payload too large', message: err.message }));\n return null;\n });\n if (body === null) return;\n }\n\n const request = {\n url: url.toString(),\n method: req.method || 'GET',\n headers,\n json: body ? () => Promise.resolve(JSON.parse(body)) : undefined,\n text: () => Promise.resolve(body || ''),\n };\n\n // Call the function handler\n const response = await functionModule.handleFunctionRequest(request);\n\n // Send response\n res.statusCode = response.status || 200;\n Object.entries(response.headers || {}).forEach(([key, value]) => {\n res.setHeader(key, value as string);\n });\n \n if (response instanceof Response) {\n const responseBody = await response.text();\n res.end(responseBody);\n } else {\n res.end(JSON.stringify(response));\n }\n } catch (error: any) {\n console.error('[maravilla-functions] Execution error:', error);\n res.statusCode = 500;\n res.setHeader('Content-Type', 'application/json');\n res.end(JSON.stringify({\n error: 'Function execution failed',\n message: error.message,\n stack: process.env.NODE_ENV === 'development' ? error.stack : undefined\n }));\n }\n });\n },\n\n async closeBundle() {\n if (cleanupWatcher) {\n cleanupWatcher();\n }\n }\n };\n}","/**\n * Platform client for communicating with the dev server\n */\n\nexport interface PlatformClient {\n kv: KvClient;\n db: DbClient;\n}\n\nexport interface KvClient {\n get(namespace: string, key: string): Promise<any>;\n put(namespace: string, key: string, value: any, ttl?: number): Promise<void>;\n delete(namespace: string, key: string): Promise<void>;\n list(namespace: string, options?: KvListOptions): Promise<KvListResponse>;\n}\n\nexport interface DbClient {\n find(collection: string, filter?: any, options?: DbFindOptions): Promise<any[]>;\n findOne(collection: string, filter: any): Promise<any | null>;\n insertOne(collection: string, document: any): Promise<string>;\n updateOne(collection: string, filter: any, update: any): Promise<{ modified: number }>;\n deleteOne(collection: string, filter: any): Promise<{ deleted: number }>;\n}\n\nexport interface KvListOptions {\n prefix?: string;\n limit?: number;\n cursor?: string;\n}\n\nexport interface KvListResponse {\n success: boolean;\n result: Array<{ name: string; expiration?: number; metadata?: any }>;\n result_info: {\n count: number;\n cursor?: string;\n };\n}\n\nexport interface DbFindOptions {\n limit?: number;\n skip?: number;\n sort?: any;\n}\n\nexport function createPlatformClient(baseUrl: string, tenant?: string): PlatformClient {\n const tenantId = tenant || 'dev-tenant';\n const headers = {\n 'Content-Type': 'application/json',\n 'X-Tenant-Id': tenantId,\n };\n\n const fetchWithError = async (url: string, options: RequestInit = {}) => {\n try {\n const response = await fetch(url, {\n ...options,\n headers: {\n ...headers,\n ...options.headers,\n },\n });\n\n if (!response.ok && response.status !== 404) {\n const error = await response.text();\n throw new Error(`Platform API error: ${response.status} - ${error}`);\n }\n\n return response;\n } catch (error) {\n if (error instanceof TypeError && error.message.includes('fetch')) {\n throw new Error(\n `Failed to connect to Maravilla dev server at ${baseUrl}. ` +\n 'Please ensure the dev server is running (cargo run -p dev-server)'\n );\n }\n throw error;\n }\n };\n\n const kv: KvClient = {\n async get(namespace: string, key: string) {\n const response = await fetchWithError(`${baseUrl}/api/kv/${namespace}/${key}`);\n if (response.status === 404) return null;\n return response.json();\n },\n\n async put(namespace: string, key: string, value: any, ttl?: number) {\n const requestHeaders: Record<string, string> = { ...headers };\n if (ttl) {\n requestHeaders['X-TTL'] = ttl.toString();\n }\n\n await fetchWithError(`${baseUrl}/api/kv/${namespace}/${key}`, {\n method: 'PUT',\n headers: requestHeaders,\n body: JSON.stringify(value),\n });\n },\n\n async delete(namespace: string, key: string) {\n await fetchWithError(`${baseUrl}/api/kv/${namespace}/${key}`, {\n method: 'DELETE',\n });\n },\n\n async list(namespace: string, options: KvListOptions = {}) {\n const response = await fetchWithError(`${baseUrl}/api/kv/${namespace}`, {\n method: 'POST',\n body: JSON.stringify(options),\n });\n return response.json() as Promise<KvListResponse>;\n },\n };\n\n const db: DbClient = {\n async find(collection: string, filter: any = {}, options: DbFindOptions = {}) {\n const response = await fetchWithError(`${baseUrl}/api/db/${collection}`, {\n method: 'POST',\n body: JSON.stringify({ filter, options }),\n });\n return response.json() as Promise<any[]>;\n },\n\n async findOne(collection: string, filter: any) {\n const response = await fetchWithError(`${baseUrl}/api/db/${collection}/findOne`, {\n method: 'POST',\n body: JSON.stringify(filter),\n });\n if (response.status === 404) return null;\n return response.json();\n },\n\n async insertOne(collection: string, document: any) {\n const response = await fetchWithError(`${baseUrl}/api/db/${collection}`, {\n method: 'PUT',\n body: JSON.stringify(document),\n });\n const result = await response.json() as { id: string };\n return result.id;\n },\n\n async updateOne(collection: string, filter: any, update: any) {\n const response = await fetchWithError(`${baseUrl}/api/db/${collection}/update`, {\n method: 'POST',\n body: JSON.stringify({ filter, update }),\n });\n return response.json() as Promise<{ modified: number }>;\n },\n\n async deleteOne(collection: string, filter: any) {\n const response = await fetchWithError(`${baseUrl}/api/db/${collection}/delete`, {\n method: 'DELETE',\n body: JSON.stringify(filter),\n });\n return response.json() as Promise<{ deleted: number }>;\n },\n };\n\n return { kv, db };\n}","import type { Plugin, ProxyOptions } from 'vite';\n\nexport interface MaravillaPluginOptions {\n /**\n * URL of the Maravilla dev server. Used both for env-var injection and\n * as the proxy target for `/_auth`, `/_assets`, `/_rt`, and `/api`.\n * @default 'http://localhost:3001'\n */\n devServerUrl?: string;\n\n /**\n * Tenant ID for development. Must match the dev-server's tenant id —\n * `crates/dev-server/src/types.rs::extract_tenant_id` defaults to\n * `dev-tenant-001` when no `X-Tenant-Id` header is supplied, and\n * storage/db/etc. publish REN events keyed by the dev-server's\n * `TenantContext.tenant_id` (also `dev-tenant-001`). If this option\n * doesn't match, the dispatcher's SSE subscription lands on a\n * different broadcast channel and no events ever fire.\n * @default 'dev-tenant-001'\n */\n tenant?: string;\n\n /**\n * Extra URL prefixes to forward to the platform dev server, in addition\n * to the defaults (`/_auth`, `/_assets`, `/_rt`, `/api`). Each prefix is\n * proxied with `changeOrigin: true`. Use this for custom platform routes.\n */\n additionalProxies?: string[];\n\n /**\n * Disable the dev-server proxy entirely. Useful if your project routes\n * platform requests through some other mechanism.\n * @default false\n */\n disableProxy?: boolean;\n\n /**\n * Output directory for events.js / events.json / workflows.js /\n * workflows.json. Matches the framework adapter's `out` option so dev\n * re-uses the same artefacts.\n *\n * The dev-server (`crates/dev-server/src/server.rs`) only scans\n * `${cwd}/build/` and `${cwd}/.maravilla/` for these manifests. Any\n * other value causes silent dispatcher dropout — the plugin warns at\n * startup. `'build'` is recommended; `'.maravilla'` works but\n * conflates build output with the runtime's pipeline/storage state.\n *\n * @default 'build'\n */\n outDir?: string;\n}\n\n/**\n * URL prefixes the dev-server owns. Anything the browser navigates to\n * directly (auth pages, assets) or upgrades (realtime ws) must be proxied\n * here so it lands on the platform server instead of the framework dev\n * server. Mirrors the prefixes registered in\n * `crates/dev-server/src/router.rs`.\n *\n * `/api/*` is intentionally enumerated by sub-prefix instead of the\n * blanket `/api`. The framework's own `+server.ts` routes (e.g.\n * `src/routes/api/v/[...key]/+server.ts` in demo's photo proxy) live\n * under `/api/...` too — proxying them all to the dev-server would\n * 404 every tenant-defined API route. Each entry below corresponds to\n * a router.rs registration.\n */\nconst DEFAULT_PROXY_PREFIXES = [\n '/_auth',\n '/_assets',\n '/_rt',\n // MCP host + the mandated OAuth discovery docs. The runtime serves these on\n // the dev-server; without proxying them, reaching `/_mcp` (or the\n // `.well-known/*` an MCP client fetches first) through the framework dev\n // server's own port 404s. Mirrors the routes in\n // `crates/dev-server/src/router.rs`.\n '/_mcp',\n '/.well-known/oauth-protected-resource',\n '/.well-known/oauth-authorization-server',\n '/.well-known/openid-configuration',\n '/api/kv',\n '/api/db',\n '/api/storage',\n '/api/realtime',\n '/api/workflows',\n '/api/push',\n '/api/media',\n '/api/maravilla',\n '/api/platform',\n '/api/tenant',\n '/api/events',\n] as const;\n\n/** The declarative capabilities the dev plugin rebuilds + hot-reloads. */\ntype BuildTarget = 'events' | 'workflows' | 'mcp';\n\nexport function maravilla(options: MaravillaPluginOptions = {}): Plugin {\n const devServerUrl = options.devServerUrl || 'http://localhost:3001';\n const tenant = options.tenant || 'dev-tenant-001';\n const disableProxy = options.disableProxy ?? false;\n const additionalProxies = options.additionalProxies ?? [];\n const outDir = options.outDir || 'build';\n\n return {\n name: 'vite-plugin-maravilla',\n\n config() {\n if (disableProxy) return undefined;\n const proxy: Record<string, ProxyOptions> = {};\n for (const prefix of [...DEFAULT_PROXY_PREFIXES, ...additionalProxies]) {\n // `/_rt/*` includes the WebSocket upgrade path `/_rt/ws`; enabling\n // `ws: true` is harmless for the plain HTTP routes under `/_rt`.\n proxy[prefix] = {\n target: devServerUrl,\n changeOrigin: true,\n ws: prefix === '/_rt',\n };\n }\n return { server: { proxy } };\n },\n\n async configureServer(server) {\n // Set environment variables that @maravilla/platform will use\n process.env.MARAVILLA_DEV_SERVER = devServerUrl;\n process.env.MARAVILLA_TENANT = tenant;\n\n console.log(`[maravilla] Platform APIs configured for ${devServerUrl}`);\n console.log('[maravilla] Using tenant:', tenant);\n if (!disableProxy) {\n const proxied = [...DEFAULT_PROXY_PREFIXES, ...additionalProxies].join(', ');\n console.log(`[maravilla] Proxying ${proxied} → ${devServerUrl}`);\n }\n\n // The dev-server only scans `${cwd}/build/` and `${cwd}/.maravilla/`\n // when loading events.json / workflows.json (see\n // crates/dev-server/src/server.rs). `build/` is the recommended\n // location — `.maravilla/` is where the runtime keeps pipeline state\n // and local object storage, so mixing build artefacts in there\n // works but conflates two concerns. Warn loudly on any other value.\n const RECOMMENDED_OUT_DIR = 'build';\n const LEGACY_OUT_DIR = '.maravilla';\n if (outDir === LEGACY_OUT_DIR) {\n console.warn(\n `[maravilla] ⓘ outDir is \"${LEGACY_OUT_DIR}\" — works, but that path ` +\n `also holds the runtime's pipeline state + local storage. ` +\n `Prefer \"${RECOMMENDED_OUT_DIR}\" so build artefacts stay separate.`,\n );\n } else if (outDir !== RECOMMENDED_OUT_DIR) {\n console.warn(\n `[maravilla] ⚠ outDir is \"${outDir}\" — the dev-server only loads ` +\n `events.json / workflows.json / mcp.json from \"${RECOMMENDED_OUT_DIR}/\" ` +\n `or \"${LEGACY_OUT_DIR}/\". Your events + workflows + MCP manifests ` +\n `WILL be built but the dev-server WON'T pick them up: silent ` +\n `dropout. Set outDir to \"${RECOMMENDED_OUT_DIR}\" ` +\n `(the default) — that's where the framework adapter writes too.`,\n );\n }\n\n // Auto-open a per-request AsyncLocalStorage scope before any\n // framework hook runs. This is the dev-mode equivalent of the\n // runtime's per-request REQUEST_CTX (tokio::task_local! at\n // crates/runtime/src/request_ctx.rs). With this in place,\n // tenant code calls `platform.auth.setCurrentUser(token)` from\n // SvelteKit's `handle` hook (or RR/Remix loaders) without any\n // Maravilla-specific wrapper — same code as prod.\n //\n // Loaded via dynamic import so non-Maravilla apps that pull\n // this plugin in for the proxy alone don't pay the cost until\n // a request actually arrives.\n const { runWithRequest } = await import('@maravilla-labs/platform');\n server.middlewares.use((_req, _res, next) => {\n runWithRequest(() => {\n next();\n }).catch((err) => {\n // Connect's next() doesn't return a Promise we can await;\n // any unhandled error from downstream surfaces here only\n // if runWithRequest's own machinery rejects. Re-throw on\n // the next tick so it shows up in the dev console.\n setImmediate(() => { throw err; });\n });\n });\n\n // Hook into SSR module resolution to ensure platform is available\n server.ssrLoadModule = new Proxy(server.ssrLoadModule, {\n async apply(target, thisArg, args) {\n const result = await Reflect.apply(target, thisArg, args);\n\n // Clear platform cache before each SSR module load to ensure fresh instance\n if ((globalThis as any).__maravilla_platform) {\n delete (globalThis as any).__maravilla_platform;\n }\n\n return result;\n }\n });\n\n // Dev-mode events auto-fire: rebuild the events + workflows\n // bundle on startup (and on file changes), then run the\n // dispatcher that subscribes to dev-server REN SSE and invokes\n // matching handlers. Mirrors prod's `EventDispatcher` so\n // STORAGE.put / KV.put / etc. on a configured pattern auto-fires\n // without explicit calls from app code.\n try {\n const { startEventDispatcher } = await import('./event-dispatcher.js');\n const { rebuildEvents, rebuildWorkflows, rebuildMcp } = await import('./event-builder.js');\n const { loadMaravillaConfig } = await import('@maravilla-labs/adapter-core');\n const projectDir = process.cwd();\n\n // Lazy-load config once. Source-of-truth for the transforms block.\n let configCache: { transforms?: unknown } = {};\n try {\n const loaded = await loadMaravillaConfig(projectDir);\n configCache = (loaded?.config ?? {}) as { transforms?: unknown };\n } catch {\n // Missing/invalid config is fine — tenant just won't have\n // synthesized transforms handlers.\n }\n\n const runRebuild = async (targets: BuildTarget[]) => {\n const want = new Set(targets);\n try {\n if (want.has('events')) {\n const n = await rebuildEvents({\n projectDir,\n outDir,\n transforms: configCache.transforms,\n log: (m) => console.warn(m),\n });\n if (n !== null) console.log(`[maravilla][events] built ${n} handler${n === 1 ? '' : 's'} → ${outDir}/events.json`);\n }\n if (want.has('workflows')) {\n const n = await rebuildWorkflows({\n projectDir,\n outDir,\n log: (m) => console.warn(m),\n });\n if (n !== null) console.log(`[maravilla][workflows] built ${n} workflow${n === 1 ? '' : 's'} → ${outDir}/workflows.json`);\n }\n if (want.has('mcp')) {\n const n = await rebuildMcp({\n projectDir,\n outDir,\n log: (m) => console.warn(m),\n });\n if (n !== null) console.log(`[maravilla][mcp] built ${n} tool${n === 1 ? '' : 's'} → ${outDir}/mcp.json`);\n }\n // Tell dev-server to re-read its events / workflows / mcp manifests.\n // Each endpoint is a safe no-op when the corresponding manifest file\n // doesn't exist — the dev-server returns 404 and falls back to\n // whatever it already had.\n const reloadPaths: string[] = [];\n if (want.has('events')) reloadPaths.push('/api/events/_reload');\n if (want.has('workflows')) reloadPaths.push('/api/workflows/_reload');\n if (want.has('mcp')) reloadPaths.push('/api/mcp/_reload');\n for (const p of reloadPaths) {\n try {\n await fetch(`${devServerUrl}${p}`, {\n method: 'POST',\n headers: { 'Content-Type': 'application/json', 'X-Tenant-Id': tenant },\n });\n } catch {\n // dev-server may not be up yet on first run — fine, it\n // loads the manifest at boot anyway.\n }\n }\n } catch (err) {\n console.error(\n `[maravilla][${targets.join('+')}] rebuild failed:`,\n (err as Error)?.message ?? err,\n );\n }\n };\n\n // Initial build before the dispatcher attaches its file watcher.\n await runRebuild(['events', 'workflows', 'mcp']);\n\n // Watch tenant source files. Debounced so a single editor save\n // doesn't trigger multiple rebuilds while esbuild is mid-write.\n const watchPaths = [\n 'events.ts', 'events.js', 'events.mjs',\n 'workflows.ts', 'workflows.js', 'workflows.mjs',\n 'mcp.ts', 'mcp.js', 'mcp.mjs',\n 'maravilla.config.ts', 'maravilla.config.js', 'maravilla.config.mjs',\n ].map((p) => `${projectDir}/${p}`);\n // Add directory paths. `mcp/` holds tool sources; `mcp-ui/` holds the\n // UI mini-app widget sources buildMcp auto-builds — both feed mcp.json.\n const watchDirs = [\n `${projectDir}/events`,\n `${projectDir}/workflows`,\n `${projectDir}/mcp`,\n `${projectDir}/mcp-ui`,\n ];\n\n const fs = await import('node:fs');\n let debounce: NodeJS.Timeout | null = null;\n let pending = new Set<BuildTarget>();\n const triggerRebuild = (path: string) => {\n const isConfig = path.includes('maravilla.config');\n if (isConfig) {\n // Config changes can affect events (transforms compile into them),\n // and the mcp `public` flag is re-read on reload — rebuild all.\n pending.add('events');\n pending.add('workflows');\n pending.add('mcp');\n } else if (path.includes('/mcp')) {\n // Matches both `/mcp/` and `/mcp-ui/` (and the `mcp.ts` root).\n pending.add('mcp');\n } else if (path.includes('/workflows')) {\n pending.add('workflows');\n } else {\n pending.add('events');\n }\n if (debounce) clearTimeout(debounce);\n debounce = setTimeout(async () => {\n const targets = [...pending];\n pending = new Set();\n debounce = null;\n console.log(`[maravilla] source change detected → rebuilding ${targets.join('+')}`);\n await runRebuild(targets);\n }, 200);\n };\n const watchers: Array<{ close: () => void }> = [];\n for (const p of watchPaths) {\n if (!fs.existsSync(p)) continue;\n try {\n watchers.push(fs.watch(p, { persistent: false }, () => triggerRebuild(p)));\n } catch { /* skip files that can't be watched */ }\n }\n // Recursive directory watchers. `fs.watch` doesn't support adding\n // a watcher to a non-existent directory — and unlike chokidar, won't\n // pick up the directory if it appears later. So if events/ or\n // workflows/ isn't there at boot, dropping a file inside it later\n // won't trigger any rebuild until the next `maravilla dev` restart.\n // We warn loudly when that's the case so users don't lose time.\n for (const d of watchDirs) {\n const dirName = d.slice(projectDir.length + 1);\n if (!fs.existsSync(d)) {\n console.warn(\n `[maravilla] ⚠ ${dirName}/ not present at startup — handlers/workflows ` +\n `you add later won't hot-rebuild until you restart maravilla dev. ` +\n `Create ${dirName}/ before next start to enable live rebuild.`,\n );\n continue;\n }\n try {\n watchers.push(fs.watch(d, { persistent: false, recursive: true }, (_evt, fname) => {\n if (fname) triggerRebuild(`${d}/${fname}`);\n }));\n } catch (e) {\n console.warn(\n `[maravilla] ⚠ failed to attach watcher to ${dirName}/: ${(e as Error)?.message ?? e}. ` +\n `Live rebuild for this directory is disabled — restart maravilla dev to pick up changes.`,\n );\n }\n }\n\n const teardown = await startEventDispatcher({\n projectDir,\n outDir,\n devServerUrl,\n tenant,\n });\n // Vite's `server.httpServer.once('close')` fires on `vite dev` exit.\n server.httpServer?.once('close', () => {\n for (const w of watchers) {\n try { w.close(); } catch { /* ignore */ }\n }\n if (debounce) clearTimeout(debounce);\n teardown();\n });\n } catch (err) {\n console.error(\n '[maravilla][events] failed to start dispatcher:',\n (err as Error)?.message ?? err,\n );\n }\n }\n };\n}\n\n// Functions plugin\nexport { maravillaFunctions } from './functions.js';\nexport type { FunctionsPluginOptions } from './functions.js';\n\n// Legacy exports for backwards compatibility\nexport { createPlatformClient } from './client.js';\nexport type { PlatformClient, KvClient, DbClient } from './client.js';\n"],"mappings":"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","names":[]}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@maravilla-labs/vite-plugin",
3
- "version": "4.0.0",
3
+ "version": "5.0.0",
4
4
  "description": "Vite plugin for Maravilla Runtime development",
5
5
  "type": "module",
6
6
  "main": "dist/index.js",
@@ -24,11 +24,11 @@
24
24
  "tsup": "^8.0.1",
25
25
  "typescript": "^5.3.3",
26
26
  "vite": "^8.0.0",
27
- "@maravilla-labs/platform": "^0.12.0"
27
+ "@maravilla-labs/platform": "^0.13.0"
28
28
  },
29
29
  "peerDependencies": {
30
30
  "vite": "^4.0.0 || ^5.0.0 || ^6.0.0 || ^7.0.0 || ^8.0.0",
31
- "@maravilla-labs/platform": "^0.12.0"
31
+ "@maravilla-labs/platform": "^0.13.0"
32
32
  },
33
33
  "keywords": [
34
34
  "vite",
@@ -1 +0,0 @@
1
- {"version":3,"sources":["../src/event-builder.ts"],"sourcesContent":["/**\n * Dev-mode events + workflows builder. Replicates what\n * `@maravilla-labs/adapter-core::buildAndIntegrateEvents` /\n * `buildAndIntegrateWorkflows` do at deploy time, MINUS the manifest.json\n * integration step (dev never owns a `manifest.json` — that's the\n * adapter's deploy-time artefact).\n *\n * Output goes to `${outDir}/events.js` + `events.json` (and the workflows\n * equivalents). The vite-plugin's auto-fire dispatcher\n * (`event-dispatcher.ts`) imports those and the `dev-server`'s\n * `/api/events/_reload` reads the manifest.\n */\n\nimport { existsSync, mkdirSync, rmSync, writeFileSync } from 'node:fs';\nimport { join } from 'node:path';\n\ninterface RebuildOptions {\n projectDir: string;\n outDir: string;\n /** transforms block from maravilla.config.ts — drives synthesized handlers */\n transforms?: unknown;\n log?: (msg: string) => void;\n}\n\n/**\n * Rebuild the events bundle in-place. Returns the number of handlers\n * registered, or null if no events to build (no events/ dir, no\n * events.ts, no transforms).\n */\nexport async function rebuildEvents(opts: RebuildOptions): Promise<number | null> {\n const { compileTransforms } = await import('@maravilla-labs/adapter-core');\n const { buildEvents } = await import('@maravilla-labs/functions');\n\n const compiled = compileTransforms(opts.transforms as never);\n\n const eventsDir = join(opts.projectDir, 'events');\n const hasRoot = existsSync(join(opts.projectDir, 'events.ts'))\n || existsSync(join(opts.projectDir, 'events.js'))\n || existsSync(join(opts.projectDir, 'events.mjs'));\n const hasDir = existsSync(eventsDir);\n\n if (!hasRoot && !hasDir && !compiled) return null;\n\n // Materialize compiled transforms next to hand-written sources so\n // discoverEventSources picks them up. Track for rollback.\n const cleanup: Array<() => void> = [];\n if (compiled) {\n const eventsDirExisted = existsSync(eventsDir);\n if (!eventsDirExisted) {\n mkdirSync(eventsDir, { recursive: true });\n cleanup.push(() => {\n try { rmSync(eventsDir, { recursive: false }); } catch { /* not empty — leave */ }\n });\n }\n const generatedPath = join(eventsDir, `${(compiled as { suggestedFileBasename: string }).suggestedFileBasename}.ts`);\n writeFileSync(generatedPath, (compiled as { source: string }).source, 'utf8');\n cleanup.push(() => {\n try { rmSync(generatedPath, { force: true }); } catch { /* ignore */ }\n });\n }\n\n try {\n mkdirSync(opts.outDir, { recursive: true });\n const manifest = await buildEvents({\n projectDir: opts.projectDir,\n outputDir: opts.outDir,\n production: false,\n minify: false,\n });\n return manifest?.handlers.length ?? 0;\n } catch (err) {\n opts.log?.(`[maravilla][events] build failed: ${(err as Error)?.message ?? err}`);\n throw err;\n } finally {\n for (let i = cleanup.length - 1; i >= 0; i -= 1) cleanup[i]!();\n }\n}\n\ninterface RebuildWorkflowsOptions {\n projectDir: string;\n outDir: string;\n log?: (msg: string) => void;\n}\n\n/**\n * Rebuild the workflows bundle in-place. Returns the number of\n * workflows registered, or null if no workflows to build.\n */\nexport async function rebuildWorkflows(opts: RebuildWorkflowsOptions): Promise<number | null> {\n const { buildWorkflows } = await import('@maravilla-labs/functions');\n\n const workflowsDir = join(opts.projectDir, 'workflows');\n const hasRoot = existsSync(join(opts.projectDir, 'workflows.ts'))\n || existsSync(join(opts.projectDir, 'workflows.js'))\n || existsSync(join(opts.projectDir, 'workflows.mjs'));\n const hasDir = existsSync(workflowsDir);\n\n if (!hasRoot && !hasDir) return null;\n\n try {\n mkdirSync(opts.outDir, { recursive: true });\n const manifest = await buildWorkflows({\n projectDir: opts.projectDir,\n outputDir: opts.outDir,\n production: false,\n minify: false,\n });\n return manifest?.workflows?.length ?? 0;\n } catch (err) {\n opts.log?.(`[maravilla][workflows] build failed: ${(err as Error)?.message ?? err}`);\n throw err;\n }\n}\n"],"mappings":";AAaA,SAAS,YAAY,WAAW,QAAQ,qBAAqB;AAC7D,SAAS,YAAY;AAerB,eAAsB,cAAc,MAA8C;AAChF,QAAM,EAAE,kBAAkB,IAAI,MAAM,OAAO,8BAA8B;AACzE,QAAM,EAAE,YAAY,IAAI,MAAM,OAAO,2BAA2B;AAEhE,QAAM,WAAW,kBAAkB,KAAK,UAAmB;AAE3D,QAAM,YAAY,KAAK,KAAK,YAAY,QAAQ;AAChD,QAAM,UAAU,WAAW,KAAK,KAAK,YAAY,WAAW,CAAC,KACxD,WAAW,KAAK,KAAK,YAAY,WAAW,CAAC,KAC7C,WAAW,KAAK,KAAK,YAAY,YAAY,CAAC;AACnD,QAAM,SAAS,WAAW,SAAS;AAEnC,MAAI,CAAC,WAAW,CAAC,UAAU,CAAC,SAAU,QAAO;AAI7C,QAAM,UAA6B,CAAC;AACpC,MAAI,UAAU;AACZ,UAAM,mBAAmB,WAAW,SAAS;AAC7C,QAAI,CAAC,kBAAkB;AACrB,gBAAU,WAAW,EAAE,WAAW,KAAK,CAAC;AACxC,cAAQ,KAAK,MAAM;AACjB,YAAI;AAAE,iBAAO,WAAW,EAAE,WAAW,MAAM,CAAC;AAAA,QAAG,QAAQ;AAAA,QAA0B;AAAA,MACnF,CAAC;AAAA,IACH;AACA,UAAM,gBAAgB,KAAK,WAAW,GAAI,SAA+C,qBAAqB,KAAK;AACnH,kBAAc,eAAgB,SAAgC,QAAQ,MAAM;AAC5E,YAAQ,KAAK,MAAM;AACjB,UAAI;AAAE,eAAO,eAAe,EAAE,OAAO,KAAK,CAAC;AAAA,MAAG,QAAQ;AAAA,MAAe;AAAA,IACvE,CAAC;AAAA,EACH;AAEA,MAAI;AACF,cAAU,KAAK,QAAQ,EAAE,WAAW,KAAK,CAAC;AAC1C,UAAM,WAAW,MAAM,YAAY;AAAA,MACjC,YAAY,KAAK;AAAA,MACjB,WAAW,KAAK;AAAA,MAChB,YAAY;AAAA,MACZ,QAAQ;AAAA,IACV,CAAC;AACD,WAAO,UAAU,SAAS,UAAU;AAAA,EACtC,SAAS,KAAK;AACZ,SAAK,MAAM,qCAAsC,KAAe,WAAW,GAAG,EAAE;AAChF,UAAM;AAAA,EACR,UAAE;AACA,aAAS,IAAI,QAAQ,SAAS,GAAG,KAAK,GAAG,KAAK,EAAG,SAAQ,CAAC,EAAG;AAAA,EAC/D;AACF;AAYA,eAAsB,iBAAiB,MAAuD;AAC5F,QAAM,EAAE,eAAe,IAAI,MAAM,OAAO,2BAA2B;AAEnE,QAAM,eAAe,KAAK,KAAK,YAAY,WAAW;AACtD,QAAM,UAAU,WAAW,KAAK,KAAK,YAAY,cAAc,CAAC,KAC3D,WAAW,KAAK,KAAK,YAAY,cAAc,CAAC,KAChD,WAAW,KAAK,KAAK,YAAY,eAAe,CAAC;AACtD,QAAM,SAAS,WAAW,YAAY;AAEtC,MAAI,CAAC,WAAW,CAAC,OAAQ,QAAO;AAEhC,MAAI;AACF,cAAU,KAAK,QAAQ,EAAE,WAAW,KAAK,CAAC;AAC1C,UAAM,WAAW,MAAM,eAAe;AAAA,MACpC,YAAY,KAAK;AAAA,MACjB,WAAW,KAAK;AAAA,MAChB,YAAY;AAAA,MACZ,QAAQ;AAAA,IACV,CAAC;AACD,WAAO,UAAU,WAAW,UAAU;AAAA,EACxC,SAAS,KAAK;AACZ,SAAK,MAAM,wCAAyC,KAAe,WAAW,GAAG,EAAE;AACnF,UAAM;AAAA,EACR;AACF;","names":[]}