sandlot 0.1.4 → 0.2.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.
Files changed (115) hide show
  1. package/dist/browser/bundler.d.ts +68 -0
  2. package/dist/browser/bundler.d.ts.map +1 -0
  3. package/dist/browser/executor.d.ts +46 -0
  4. package/dist/browser/executor.d.ts.map +1 -0
  5. package/dist/browser/index.d.ts +9 -0
  6. package/dist/browser/index.d.ts.map +1 -0
  7. package/dist/browser/index.js +2692 -0
  8. package/dist/browser/preset.d.ts +63 -0
  9. package/dist/browser/preset.d.ts.map +1 -0
  10. package/dist/commands/index.d.ts +20 -11
  11. package/dist/commands/index.d.ts.map +1 -1
  12. package/dist/commands/types.d.ts +31 -132
  13. package/dist/commands/types.d.ts.map +1 -1
  14. package/dist/core/bundler-utils.d.ts +142 -0
  15. package/dist/core/bundler-utils.d.ts.map +1 -0
  16. package/dist/core/esm-types-resolver.d.ts +125 -0
  17. package/dist/core/esm-types-resolver.d.ts.map +1 -0
  18. package/dist/core/executor.d.ts +35 -0
  19. package/dist/core/executor.d.ts.map +1 -0
  20. package/dist/{fs.d.ts → core/fs.d.ts} +27 -29
  21. package/dist/core/fs.d.ts.map +1 -0
  22. package/dist/core/sandbox.d.ts +30 -0
  23. package/dist/core/sandbox.d.ts.map +1 -0
  24. package/dist/core/sandlot.d.ts +30 -0
  25. package/dist/core/sandlot.d.ts.map +1 -0
  26. package/dist/core/shared-module-registry.d.ts +46 -0
  27. package/dist/core/shared-module-registry.d.ts.map +1 -0
  28. package/dist/core/typechecker.d.ts +60 -0
  29. package/dist/core/typechecker.d.ts.map +1 -0
  30. package/dist/index.d.ts +11 -16
  31. package/dist/index.d.ts.map +1 -1
  32. package/dist/index.js +1399 -2010
  33. package/dist/node/bundler.d.ts +48 -0
  34. package/dist/node/bundler.d.ts.map +1 -0
  35. package/dist/node/executor.d.ts +48 -0
  36. package/dist/node/executor.d.ts.map +1 -0
  37. package/dist/node/index.d.ts +9 -0
  38. package/dist/node/index.d.ts.map +1 -0
  39. package/dist/node/index.js +2646 -0
  40. package/dist/node/preset.d.ts +62 -0
  41. package/dist/node/preset.d.ts.map +1 -0
  42. package/dist/types.d.ts +525 -0
  43. package/dist/types.d.ts.map +1 -0
  44. package/package.json +16 -6
  45. package/src/browser/bundler.ts +294 -0
  46. package/src/browser/executor.ts +71 -0
  47. package/src/browser/index.ts +57 -0
  48. package/src/browser/preset.ts +179 -0
  49. package/src/commands/index.ts +526 -43
  50. package/src/commands/types.ts +82 -146
  51. package/src/core/bundler-utils.ts +630 -0
  52. package/src/core/esm-types-resolver.ts +432 -0
  53. package/src/core/executor.ts +161 -0
  54. package/src/{fs.ts → core/fs.ts} +59 -37
  55. package/src/core/sandbox.ts +621 -0
  56. package/src/core/sandlot.ts +77 -0
  57. package/src/core/shared-module-registry.ts +138 -0
  58. package/src/core/typechecker.ts +607 -0
  59. package/src/index.ts +104 -139
  60. package/src/node/bundler.ts +194 -0
  61. package/src/node/executor.ts +87 -0
  62. package/src/node/index.ts +39 -0
  63. package/src/node/preset.ts +178 -0
  64. package/src/types.ts +668 -0
  65. package/README.md +0 -243
  66. package/dist/build-emitter.d.ts +0 -47
  67. package/dist/build-emitter.d.ts.map +0 -1
  68. package/dist/builder.d.ts +0 -370
  69. package/dist/builder.d.ts.map +0 -1
  70. package/dist/bundler.d.ts +0 -152
  71. package/dist/bundler.d.ts.map +0 -1
  72. package/dist/commands/compile.d.ts +0 -13
  73. package/dist/commands/compile.d.ts.map +0 -1
  74. package/dist/commands/packages.d.ts +0 -17
  75. package/dist/commands/packages.d.ts.map +0 -1
  76. package/dist/commands/run.d.ts +0 -40
  77. package/dist/commands/run.d.ts.map +0 -1
  78. package/dist/commands.d.ts +0 -179
  79. package/dist/commands.d.ts.map +0 -1
  80. package/dist/fs.d.ts.map +0 -1
  81. package/dist/internal.d.ts +0 -79
  82. package/dist/internal.d.ts.map +0 -1
  83. package/dist/internal.js +0 -1942
  84. package/dist/loader.d.ts +0 -164
  85. package/dist/loader.d.ts.map +0 -1
  86. package/dist/packages.d.ts +0 -199
  87. package/dist/packages.d.ts.map +0 -1
  88. package/dist/runner.d.ts +0 -314
  89. package/dist/runner.d.ts.map +0 -1
  90. package/dist/sandbox-manager.d.ts +0 -261
  91. package/dist/sandbox-manager.d.ts.map +0 -1
  92. package/dist/sandbox.d.ts +0 -267
  93. package/dist/sandbox.d.ts.map +0 -1
  94. package/dist/shared-modules.d.ts +0 -148
  95. package/dist/shared-modules.d.ts.map +0 -1
  96. package/dist/shared-resources.d.ts +0 -102
  97. package/dist/shared-resources.d.ts.map +0 -1
  98. package/dist/ts-libs.d.ts +0 -85
  99. package/dist/ts-libs.d.ts.map +0 -1
  100. package/dist/typechecker.d.ts +0 -127
  101. package/dist/typechecker.d.ts.map +0 -1
  102. package/src/build-emitter.ts +0 -64
  103. package/src/builder.ts +0 -498
  104. package/src/bundler.ts +0 -575
  105. package/src/commands/compile.ts +0 -236
  106. package/src/commands/packages.ts +0 -154
  107. package/src/commands/run.ts +0 -245
  108. package/src/internal.ts +0 -119
  109. package/src/loader.ts +0 -229
  110. package/src/packages.ts +0 -936
  111. package/src/sandbox.ts +0 -398
  112. package/src/shared-modules.ts +0 -280
  113. package/src/shared-resources.ts +0 -166
  114. package/src/ts-libs.ts +0 -218
  115. package/src/typechecker.ts +0 -635
package/src/bundler.ts DELETED
@@ -1,575 +0,0 @@
1
- import type { IFileSystem } from "just-bash/browser";
2
- import type * as EsbuildTypes from "esbuild-wasm";
3
- import { getPackageManifest, resolveToEsmUrl } from "./packages";
4
- import { getSharedModuleRuntimeCode, getSharedModuleExports } from "./shared-modules";
5
-
6
- // Lazily loaded esbuild module
7
- let esbuild: typeof EsbuildTypes | null = null;
8
-
9
- /**
10
- * Detect if we're running in a server environment (Node.js, Bun, Deno)
11
- * vs a browser environment.
12
- */
13
- function isServerEnvironment(): boolean {
14
- // Check for Bun
15
- if (typeof globalThis !== "undefined" && "Bun" in globalThis) {
16
- return true;
17
- }
18
- // Check for Deno
19
- if (typeof globalThis !== "undefined" && "Deno" in globalThis) {
20
- return true;
21
- }
22
- // Check for Node.js (process.versions.node exists)
23
- if (typeof process !== "undefined" && process.versions?.node) {
24
- return true;
25
- }
26
- return false;
27
- }
28
-
29
- async function getEsbuild(): Promise<typeof EsbuildTypes> {
30
- if (esbuild) return esbuild;
31
-
32
- if (isServerEnvironment()) {
33
- // In server environments, use native esbuild for better performance
34
- // eslint-disable-next-line @typescript-eslint/no-explicit-any
35
- const mod: any = await import("esbuild");
36
- esbuild = mod.default ?? mod;
37
- } else {
38
- // In browser, load esbuild-wasm from esm.sh CDN
39
- const cdnUrl = `https://esm.sh/esbuild-wasm@${ESBUILD_VERSION}`;
40
-
41
- // eslint-disable-next-line @typescript-eslint/no-explicit-any
42
- const mod: any = await import(/* @vite-ignore */ cdnUrl);
43
-
44
- // esm.sh typically provides both default and named exports
45
- esbuild = mod.default ?? mod;
46
-
47
- // Verify we have the initialize function (only needed for wasm version)
48
- if (typeof esbuild?.initialize !== "function") {
49
- console.error("esbuild-wasm module structure:", mod);
50
- throw new Error("Failed to load esbuild-wasm: initialize function not found");
51
- }
52
- }
53
-
54
- return esbuild!;
55
- }
56
-
57
- /**
58
- * How to handle npm package imports (bare imports like "react").
59
- *
60
- * - "cdn" (default): Rewrite to esm.sh CDN URLs using installed package versions.
61
- * Requires packages to be installed via the `install` command.
62
- * - "external": Mark as external, don't rewrite. The consumer must handle
63
- * module resolution (useful for SSR or custom bundling).
64
- * - "bundle": Attempt to bundle from node_modules. Rarely useful in browser
65
- * since node_modules typically doesn't exist in the virtual filesystem.
66
- */
67
- export type NpmImportsMode = "cdn" | "external" | "bundle";
68
-
69
- /**
70
- * Options for bundling
71
- */
72
- export interface BundleOptions {
73
- /**
74
- * The virtual filesystem to read source files from
75
- */
76
- fs: IFileSystem;
77
-
78
- /**
79
- * Entry point path (absolute path in the virtual filesystem)
80
- */
81
- entryPoint: string;
82
-
83
- /**
84
- * Module names to mark as external (won't be bundled).
85
- * These are in addition to bare imports when using npmImports: "external".
86
- */
87
- external?: string[];
88
-
89
- /**
90
- * How to handle npm package imports (bare imports like "react").
91
- *
92
- * - "cdn" (default): Rewrite to esm.sh CDN URLs using installed package versions
93
- * - "external": Mark as external, don't rewrite (consumer must handle)
94
- * - "bundle": Attempt to bundle from node_modules (rarely useful in browser)
95
- */
96
- npmImports?: NpmImportsMode;
97
-
98
- /**
99
- * Module IDs that should be resolved from the host's SharedModuleRegistry
100
- * instead of esm.sh CDN. The host must have registered these modules.
101
- *
102
- * Example: ['react', 'react-dom/client']
103
- *
104
- * When specified, imports of these modules will use the host's instances,
105
- * allowing dynamic components to share React context, hooks, etc.
106
- */
107
- sharedModules?: string[];
108
-
109
- /**
110
- * Output format: 'esm' (default), 'iife', or 'cjs'
111
- */
112
- format?: "esm" | "iife" | "cjs";
113
-
114
- /**
115
- * Enable minification
116
- * Default: false
117
- */
118
- minify?: boolean;
119
-
120
- /**
121
- * Enable source maps (inline)
122
- * Default: false
123
- */
124
- sourcemap?: boolean;
125
-
126
- /**
127
- * Global name for IIFE format
128
- */
129
- globalName?: string;
130
-
131
- /**
132
- * Target environment(s)
133
- * Default: ['es2020']
134
- */
135
- target?: string[];
136
- }
137
-
138
- /**
139
- * Result of bundling
140
- */
141
- export interface BundleResult {
142
- /**
143
- * The bundled JavaScript code
144
- */
145
- code: string;
146
-
147
- /**
148
- * Any warnings from esbuild
149
- */
150
- warnings: EsbuildTypes.Message[];
151
-
152
- /**
153
- * List of files that were included in the bundle
154
- */
155
- includedFiles: string[];
156
- }
157
-
158
- /**
159
- * esbuild-wasm version - MUST match the version in package.json dependencies
160
- */
161
- const ESBUILD_VERSION = "0.27.2";
162
-
163
- // Track initialization state
164
- let initialized = false;
165
- let initPromise: Promise<void> | null = null;
166
-
167
- /**
168
- * Get the esbuild-wasm binary URL based on the installed version
169
- */
170
- function getWasmUrl(): string {
171
- return `https://unpkg.com/esbuild-wasm@${ESBUILD_VERSION}/esbuild.wasm`;
172
- }
173
-
174
- /**
175
- * Check if the browser environment supports cross-origin isolation.
176
- * This is needed for SharedArrayBuffer which esbuild-wasm may use.
177
- */
178
- function checkCrossOriginIsolation(): void {
179
- if (typeof window === "undefined") return; // Not in browser
180
-
181
- // crossOriginIsolated is true when COOP/COEP headers are set correctly
182
- if (!window.crossOriginIsolated) {
183
- console.warn(
184
- "[sandlot] Cross-origin isolation is not enabled. " +
185
- "esbuild-wasm may have reduced performance or fail on some browsers.\n" +
186
- "To enable, add these headers to your dev server:\n" +
187
- " Cross-Origin-Embedder-Policy: require-corp\n" +
188
- " Cross-Origin-Opener-Policy: same-origin\n" +
189
- "In Vite, add a plugin to configureServer. See sandlot README for details."
190
- );
191
- }
192
- }
193
-
194
- /**
195
- * Initialize esbuild. Called automatically on first bundle.
196
- * Can be called explicitly to pre-warm.
197
- *
198
- * In browser environments, this loads and initializes esbuild-wasm.
199
- * In server environments (Node.js, Bun, Deno), this loads native esbuild
200
- * which doesn't require WASM initialization.
201
- */
202
- export async function initBundler(): Promise<void> {
203
- if (initialized) return;
204
-
205
- if (initPromise) {
206
- await initPromise;
207
- return;
208
- }
209
-
210
- initPromise = (async () => {
211
- const es = await getEsbuild();
212
-
213
- // Native esbuild doesn't need initialization, only esbuild-wasm does
214
- if (!isServerEnvironment() && typeof es.initialize === "function") {
215
- checkCrossOriginIsolation();
216
- await es.initialize({
217
- wasmURL: getWasmUrl(),
218
- });
219
- }
220
- })();
221
-
222
- await initPromise;
223
- initialized = true;
224
- }
225
-
226
- /**
227
- * Check if a path is a bare import (not relative or absolute)
228
- */
229
- function isBareImport(path: string): boolean {
230
- return !path.startsWith(".") && !path.startsWith("/");
231
- }
232
-
233
- /**
234
- * Get the appropriate loader based on file extension
235
- */
236
- function getLoader(path: string): EsbuildTypes.Loader {
237
- const ext = path.split(".").pop()?.toLowerCase();
238
- switch (ext) {
239
- case "ts":
240
- return "ts";
241
- case "tsx":
242
- return "tsx";
243
- case "jsx":
244
- return "jsx";
245
- case "js":
246
- case "mjs":
247
- return "js";
248
- case "json":
249
- return "json";
250
- case "css":
251
- return "css";
252
- case "txt":
253
- return "text";
254
- default:
255
- return "js";
256
- }
257
- }
258
-
259
- /**
260
- * Options for the VFS plugin
261
- */
262
- interface VfsPluginOptions {
263
- fs: IFileSystem;
264
- entryPoint: string;
265
- npmImports: NpmImportsMode;
266
- installedPackages: Record<string, string>;
267
- includedFiles: Set<string>;
268
- /** Module IDs to resolve from SharedModuleRegistry */
269
- sharedModuleIds: Set<string>;
270
- }
271
-
272
- /**
273
- * Check if an import path matches a shared module ID.
274
- * Handles both exact matches and subpath imports (e.g., 'react-dom/client').
275
- */
276
- function matchesSharedModule(importPath: string, sharedModuleIds: Set<string>): string | null {
277
- // Check exact match first
278
- if (sharedModuleIds.has(importPath)) {
279
- return importPath;
280
- }
281
-
282
- // Check if any shared module is a prefix (for subpath imports)
283
- // e.g., if 'react-dom' is registered, 'react-dom/client' should match
284
- for (const moduleId of sharedModuleIds) {
285
- if (importPath === moduleId || importPath.startsWith(moduleId + '/')) {
286
- return importPath;
287
- }
288
- }
289
-
290
- return null;
291
- }
292
-
293
- /**
294
- * Create an esbuild plugin that reads from a virtual filesystem
295
- */
296
- function createVfsPlugin(options: VfsPluginOptions): EsbuildTypes.Plugin {
297
- const {
298
- fs,
299
- entryPoint,
300
- npmImports,
301
- installedPackages,
302
- includedFiles,
303
- sharedModuleIds,
304
- } = options;
305
-
306
- return {
307
- name: "virtual-fs",
308
- setup(build) {
309
- // Resolve all imports
310
- build.onResolve({ filter: /.*/ }, async (args) => {
311
- // Handle the virtual entry point
312
- if (args.kind === "entry-point") {
313
- return { path: entryPoint, namespace: "vfs" };
314
- }
315
-
316
- // Handle bare imports
317
- if (isBareImport(args.path)) {
318
- // Check if this module should use the shared registry
319
- const sharedMatch = matchesSharedModule(args.path, sharedModuleIds);
320
- if (sharedMatch) {
321
- return {
322
- path: sharedMatch,
323
- namespace: "sandlot-shared"
324
- };
325
- }
326
-
327
- // Handle based on npmImports mode
328
- switch (npmImports) {
329
- case "cdn": {
330
- // Try to rewrite to esm.sh URL if package is installed
331
- const esmUrl = resolveToEsmUrl(args.path, installedPackages);
332
- if (esmUrl) {
333
- return { path: esmUrl, external: true };
334
- }
335
- // Fall back to external if not installed
336
- return { path: args.path, external: true };
337
- }
338
-
339
- case "external":
340
- // Mark as external, don't rewrite
341
- return { path: args.path, external: true };
342
-
343
- case "bundle": {
344
- // Try to resolve from VFS node_modules
345
- const resolved = fs.resolvePath(args.resolveDir, `node_modules/${args.path}`);
346
- const exists = await fs.exists(resolved);
347
- if (exists) {
348
- return { path: resolved, namespace: "vfs" };
349
- }
350
- // Fall back to external if not found
351
- return { path: args.path, external: true };
352
- }
353
- }
354
- }
355
-
356
- // Resolve relative/absolute paths
357
- const resolved = fs.resolvePath(args.resolveDir, args.path);
358
-
359
- // Try with extensions if no extension provided
360
- const extensions = [".ts", ".tsx", ".js", ".jsx", ".mjs", ".json"];
361
- const hasExtension = extensions.some((ext) => resolved.endsWith(ext));
362
-
363
- if (hasExtension) {
364
- const exists = await fs.exists(resolved);
365
- if (exists) {
366
- return { path: resolved, namespace: "vfs" };
367
- }
368
- return { errors: [{ text: `File not found: ${resolved}` }] };
369
- }
370
-
371
- // Try adding extensions
372
- for (const ext of extensions) {
373
- const withExt = resolved + ext;
374
- if (await fs.exists(withExt)) {
375
- return { path: withExt, namespace: "vfs" };
376
- }
377
- }
378
-
379
- // Try index files
380
- for (const ext of extensions) {
381
- const indexPath = `${resolved}/index${ext}`;
382
- if (await fs.exists(indexPath)) {
383
- return { path: indexPath, namespace: "vfs" };
384
- }
385
- }
386
-
387
- return { errors: [{ text: `Cannot resolve: ${args.path} from ${args.resolveDir}` }] };
388
- });
389
-
390
- // Load shared modules from the registry
391
- build.onLoad({ filter: /.*/, namespace: "sandlot-shared" }, (args) => {
392
- // Generate ESM code that re-exports from the shared module registry
393
- const contents = `
394
- const __sandlot_mod__ = ${getSharedModuleRuntimeCode(args.path)};
395
- export default __sandlot_mod__.default ?? __sandlot_mod__;
396
- ${generateNamedExports(args.path)}
397
- `;
398
- return {
399
- contents: contents.trim(),
400
- loader: 'js'
401
- };
402
- });
403
-
404
- // Load files from VFS
405
- build.onLoad({ filter: /.*/, namespace: "vfs" }, async (args) => {
406
- try {
407
- const contents = await fs.readFile(args.path);
408
- includedFiles.add(args.path);
409
- return {
410
- contents,
411
- loader: getLoader(args.path),
412
- resolveDir: args.path.substring(0, args.path.lastIndexOf("/")),
413
- };
414
- } catch (err) {
415
- return {
416
- errors: [{ text: `Failed to read ${args.path}: ${err}` }],
417
- };
418
- }
419
- });
420
- },
421
- };
422
- }
423
-
424
- /**
425
- * Generate named export statements for shared modules.
426
- *
427
- * Uses dynamically discovered exports from the SharedModuleRegistry,
428
- * which are populated when registerSharedModules() is called.
429
- *
430
- * If the module wasn't registered (or has no enumerable exports),
431
- * returns a comment - named imports won't work but default import will.
432
- */
433
- function generateNamedExports(moduleId: string): string {
434
- const exports = getSharedModuleExports(moduleId);
435
-
436
- if (exports.length > 0) {
437
- return exports
438
- .map(name => `export const ${name} = __sandlot_mod__.${name};`)
439
- .join('\n');
440
- }
441
-
442
- // Module not registered or has no enumerable exports
443
- // Default import will still work: import foo from 'module'
444
- return `// No exports discovered for "${moduleId}" - use default import or call registerSharedModules() first`;
445
- }
446
-
447
- /**
448
- * Bundle TypeScript/JavaScript files from a virtual filesystem
449
- *
450
- * @example
451
- * ```ts
452
- * const fs = Filesystem.create({
453
- * initialFiles: {
454
- * "/src/index.ts": "export const hello = 'world';",
455
- * "/src/utils.ts": "export function add(a: number, b: number) { return a + b; }",
456
- * }
457
- * });
458
- *
459
- * const result = await bundle({
460
- * fs,
461
- * entryPoint: "/src/index.ts",
462
- * });
463
- *
464
- * console.log(result.code);
465
- * ```
466
- */
467
- export async function bundle(options: BundleOptions): Promise<BundleResult> {
468
- await initBundler();
469
-
470
- const {
471
- fs,
472
- entryPoint,
473
- external = [],
474
- npmImports = "cdn",
475
- sharedModules = [],
476
- format = "esm",
477
- minify = false,
478
- sourcemap = false,
479
- globalName,
480
- target = ["es2020"],
481
- } = options;
482
-
483
- // Normalize entry point
484
- const normalizedEntry = entryPoint.startsWith("/") ? entryPoint : `/${entryPoint}`;
485
-
486
- // Verify entry point exists
487
- if (!(await fs.exists(normalizedEntry))) {
488
- throw new Error(`Entry point not found: ${normalizedEntry}`);
489
- }
490
-
491
- // Get installed packages for ESM URL rewriting
492
- const manifest = await getPackageManifest(fs);
493
- const installedPackages = manifest.dependencies;
494
-
495
- // Create set of shared module IDs for fast lookup
496
- const sharedModuleIds = new Set(sharedModules);
497
-
498
- const includedFiles = new Set<string>();
499
- const plugin = createVfsPlugin({
500
- fs,
501
- entryPoint: normalizedEntry,
502
- npmImports,
503
- installedPackages,
504
- includedFiles,
505
- sharedModuleIds,
506
- });
507
-
508
- const es = await getEsbuild();
509
- const result = await es.build({
510
- entryPoints: [normalizedEntry],
511
- bundle: true,
512
- write: false,
513
- format,
514
- minify,
515
- sourcemap: sourcemap ? "inline" : false,
516
- globalName,
517
- target,
518
- external,
519
- plugins: [plugin],
520
- jsx: "automatic",
521
- });
522
-
523
- const code = result.outputFiles?.[0]?.text ?? "";
524
-
525
- return {
526
- code,
527
- warnings: result.warnings,
528
- includedFiles: Array.from(includedFiles),
529
- };
530
- }
531
-
532
- /**
533
- * Bundle and return a blob URL for dynamic import
534
- *
535
- * @example
536
- * ```ts
537
- * const url = await bundleToUrl({
538
- * fs,
539
- * entryPoint: "/src/index.ts",
540
- * });
541
- *
542
- * const module = await import(url);
543
- * console.log(module.hello); // 'world'
544
- *
545
- * // Clean up when done
546
- * URL.revokeObjectURL(url);
547
- * ```
548
- */
549
- export async function bundleToUrl(options: BundleOptions): Promise<string> {
550
- const result = await bundle(options);
551
- const blob = new Blob([result.code], { type: "application/javascript" });
552
- return URL.createObjectURL(blob);
553
- }
554
-
555
- /**
556
- * Bundle and immediately import the module
557
- *
558
- * @example
559
- * ```ts
560
- * const module = await bundleAndImport<{ hello: string }>({
561
- * fs,
562
- * entryPoint: "/src/index.ts",
563
- * });
564
- *
565
- * console.log(module.hello); // 'world'
566
- * ```
567
- */
568
- export async function bundleAndImport<T = unknown>(options: BundleOptions): Promise<T> {
569
- const url = await bundleToUrl(options);
570
- try {
571
- return await import(/* @vite-ignore */ url);
572
- } finally {
573
- URL.revokeObjectURL(url);
574
- }
575
- }