vite
Advanced tools
Comparing version 5.1.4 to 5.1.5
@@ -5,3 +5,3 @@ import path from 'node:path'; | ||
import { EventEmitter } from 'events'; | ||
import { c as colors, a as createLogger, r as resolveConfig } from './chunks/dep-jDlpJiMN.js'; | ||
import { A as colors, v as createLogger, r as resolveConfig } from './chunks/dep-G-px366b.js'; | ||
import { VERSION } from './constants.js'; | ||
@@ -761,3 +761,3 @@ import 'node:fs/promises'; | ||
// is ok here | ||
const { createServer } = await import('./chunks/dep-jDlpJiMN.js').then(function (n) { return n.E; }); | ||
const { createServer } = await import('./chunks/dep-G-px366b.js').then(function (n) { return n.E; }); | ||
try { | ||
@@ -841,3 +841,3 @@ const server = await createServer({ | ||
filterDuplicateOptions(options); | ||
const { build } = await import('./chunks/dep-jDlpJiMN.js').then(function (n) { return n.F; }); | ||
const { build } = await import('./chunks/dep-G-px366b.js').then(function (n) { return n.F; }); | ||
const buildOptions = cleanOptions(options); | ||
@@ -869,3 +869,3 @@ try { | ||
filterDuplicateOptions(options); | ||
const { optimizeDeps } = await import('./chunks/dep-jDlpJiMN.js').then(function (n) { return n.D; }); | ||
const { optimizeDeps } = await import('./chunks/dep-G-px366b.js').then(function (n) { return n.D; }); | ||
try { | ||
@@ -896,3 +896,3 @@ const config = await resolveConfig({ | ||
filterDuplicateOptions(options); | ||
const { preview } = await import('./chunks/dep-jDlpJiMN.js').then(function (n) { return n.G; }); | ||
const { preview } = await import('./chunks/dep-G-px366b.js').then(function (n) { return n.G; }); | ||
try { | ||
@@ -899,0 +899,0 @@ const server = await preview({ |
@@ -48,18 +48,2 @@ import path, { resolve } from 'node:path'; | ||
const FS_PREFIX = `/@fs/`; | ||
/** | ||
* Prefix for resolved Ids that are not valid browser import specifiers | ||
*/ | ||
const VALID_ID_PREFIX = `/@id/`; | ||
/** | ||
* Plugins that use 'virtual modules' (e.g. for helper functions), prefix the | ||
* module ID with `\0`, a convention from the rollup ecosystem. | ||
* This prevents other plugins from trying to process the id (like node resolution), | ||
* and core features like sourcemaps can use this info to differentiate between | ||
* virtual modules and regular files. | ||
* `\0` is not a permitted char in import URLs so we have to replace them during | ||
* import analysis. The id will be decoded back before entering the plugins pipeline. | ||
* These encoded virtual ids are also prefixed by the VALID_ID_PREFIX, so virtual | ||
* modules in the browser end up encoded as `/@id/__x00__{id}` | ||
*/ | ||
const NULL_BYTE_PLACEHOLDER = `__x00__`; | ||
const CLIENT_PUBLIC_PATH = `/@vite/client`; | ||
@@ -132,2 +116,2 @@ const ENV_PUBLIC_PATH = `/@vite/env`; | ||
export { CLIENT_DIR, CLIENT_ENTRY, CLIENT_PUBLIC_PATH, CSS_LANGS_RE, DEFAULT_ASSETS_INLINE_LIMIT, DEFAULT_ASSETS_RE, DEFAULT_CONFIG_FILES, DEFAULT_DEV_PORT, DEFAULT_EXTENSIONS, DEFAULT_MAIN_FIELDS, DEFAULT_PREVIEW_PORT, DEP_VERSION_RE, ENV_ENTRY, ENV_PUBLIC_PATH, ESBUILD_MODULES_TARGET, FS_PREFIX, JS_TYPES_RE, KNOWN_ASSET_TYPES, METADATA_FILENAME, NULL_BYTE_PLACEHOLDER, OPTIMIZABLE_ENTRY_RE, SPECIAL_QUERY_RE, VALID_ID_PREFIX, VERSION, VITE_PACKAGE_DIR, loopbackHosts, wildcardHosts }; | ||
export { CLIENT_DIR, CLIENT_ENTRY, CLIENT_PUBLIC_PATH, CSS_LANGS_RE, DEFAULT_ASSETS_INLINE_LIMIT, DEFAULT_ASSETS_RE, DEFAULT_CONFIG_FILES, DEFAULT_DEV_PORT, DEFAULT_EXTENSIONS, DEFAULT_MAIN_FIELDS, DEFAULT_PREVIEW_PORT, DEP_VERSION_RE, ENV_ENTRY, ENV_PUBLIC_PATH, ESBUILD_MODULES_TARGET, FS_PREFIX, JS_TYPES_RE, KNOWN_ASSET_TYPES, METADATA_FILENAME, OPTIMIZABLE_ENTRY_RE, SPECIAL_QUERY_RE, VERSION, VITE_PACKAGE_DIR, loopbackHosts, wildcardHosts }; |
export { parseAst, parseAstAsync } from 'rollup/parseAst'; | ||
import { i as isInNodeModules, b as arraify } from './chunks/dep-jDlpJiMN.js'; | ||
export { f as build, j as buildErrorMessage, u as createFilter, a as createLogger, e as createServer, d as defineConfig, k as fetchModule, g as formatPostcssSourceMap, y as isFileServingAllowed, l as loadConfigFromFile, z as loadEnv, q as mergeAlias, m as mergeConfig, n as normalizePath, o as optimizeDeps, h as preprocessCSS, p as preview, r as resolveConfig, A as resolveEnvPrefix, v as rollupVersion, x as searchForWorkspaceRoot, w as send, s as sortUserPlugins, t as transformWithEsbuild } from './chunks/dep-jDlpJiMN.js'; | ||
import { i as isInNodeModules, a as arraify } from './chunks/dep-G-px366b.js'; | ||
export { b as build, g as buildErrorMessage, k as createFilter, v as createLogger, c as createServer, d as defineConfig, h as fetchModule, f as formatPostcssSourceMap, x as isFileServingAllowed, l as loadConfigFromFile, y as loadEnv, j as mergeAlias, m as mergeConfig, n as normalizePath, o as optimizeDeps, e as preprocessCSS, p as preview, r as resolveConfig, z as resolveEnvPrefix, q as rollupVersion, w as searchForWorkspaceRoot, u as send, s as sortUserPlugins, t as transformWithEsbuild } from './chunks/dep-G-px366b.js'; | ||
export { VERSION as version } from './constants.js'; | ||
export { version as esbuildVersion } from 'esbuild'; | ||
import { existsSync, readFileSync } from 'node:fs'; | ||
import { ViteRuntime, ESModulesRunner } from './runtime.js'; | ||
import { ViteRuntime, ESModulesRunner } from 'vite/runtime'; | ||
import 'node:fs/promises'; | ||
@@ -9,0 +9,0 @@ import 'node:path'; |
@@ -1,3 +0,3 @@ | ||
import { a as ViteModuleRunner, e as ViteRuntimeModuleContext } from './types.d-jgA8ss1A.js'; | ||
export { d as FetchFunction, F as FetchResult, f as HMRConnection, H as HMRLogger, c as HMRRuntimeConnection, g as ModuleCache, M as ModuleCacheMap, R as ResolvedResult, S as SSRImportMetadata, b as ViteRuntime, h as ViteRuntimeImportMeta, V as ViteRuntimeOptions, s as ssrDynamicImportKey, i as ssrExportAllKey, j as ssrImportKey, k as ssrImportMetaKey, l as ssrModuleExportsKey } from './types.d-jgA8ss1A.js'; | ||
import { V as ViteRuntimeOptions, b as ViteModuleRunner, M as ModuleCacheMap, c as HMRClient, R as ResolvedResult, d as ViteRuntimeModuleContext } from './types.d-AKzkD8vd.js'; | ||
export { a as FetchFunction, F as FetchResult, e as HMRConnection, H as HMRLogger, g as HMRRuntimeConnection, f as ModuleCache, S as SSRImportMetadata, h as ViteRuntimeImportMeta, s as ssrDynamicImportKey, i as ssrExportAllKey, j as ssrImportKey, k as ssrImportMetaKey, l as ssrModuleExportsKey } from './types.d-AKzkD8vd.js'; | ||
import '../../types/hot.js'; | ||
@@ -7,2 +7,53 @@ import '../../types/hmrPayload.js'; | ||
interface ViteRuntimeDebugger { | ||
(formatter: unknown, ...args: unknown[]): void; | ||
} | ||
declare class ViteRuntime { | ||
options: ViteRuntimeOptions; | ||
runner: ViteModuleRunner; | ||
private debug?; | ||
/** | ||
* Holds the cache of modules | ||
* Keys of the map are ids | ||
*/ | ||
moduleCache: ModuleCacheMap; | ||
hmrClient?: HMRClient; | ||
entrypoints: Set<string>; | ||
private idToUrlMap; | ||
private fileToIdMap; | ||
private envProxy; | ||
private _destroyed; | ||
private _resetSourceMapSupport?; | ||
constructor(options: ViteRuntimeOptions, runner: ViteModuleRunner, debug?: ViteRuntimeDebugger | undefined); | ||
/** | ||
* URL to execute. Accepts file path, server path or id relative to the root. | ||
*/ | ||
executeUrl<T = any>(url: string): Promise<T>; | ||
/** | ||
* Entrypoint URL to execute. Accepts file path, server path or id relative to the root. | ||
* In the case of a full reload triggered by HMR, this is the module that will be reloaded. | ||
* If this method is called multiple times, all entrypoints will be reloaded one at a time. | ||
*/ | ||
executeEntrypoint<T = any>(url: string): Promise<T>; | ||
/** | ||
* Clear all caches including HMR listeners. | ||
*/ | ||
clearCache(): void; | ||
/** | ||
* Clears all caches, removes all HMR listeners, and resets source map support. | ||
* This method doesn't stop the HMR connection. | ||
*/ | ||
destroy(): Promise<void>; | ||
/** | ||
* Returns `true` if the runtime has been destroyed by calling `destroy()` method. | ||
*/ | ||
isDestroyed(): boolean; | ||
private invalidateFiles; | ||
private normalizeEntryUrl; | ||
private processImport; | ||
private cachedRequest; | ||
private cachedModule; | ||
protected directRequest(id: string, fetchResult: ResolvedResult, _callstack: string[]): Promise<any>; | ||
} | ||
declare class ESModulesRunner implements ViteModuleRunner { | ||
@@ -13,2 +64,2 @@ runViteModule(context: ViteRuntimeModuleContext, code: string): Promise<any>; | ||
export { ESModulesRunner, ViteModuleRunner, ViteRuntimeModuleContext }; | ||
export { ESModulesRunner, ModuleCacheMap, ResolvedResult, ViteModuleRunner, ViteRuntime, ViteRuntimeModuleContext, ViteRuntimeOptions }; |
@@ -1,1617 +0,1021 @@ | ||
class HMRContext { | ||
hmrClient; | ||
ownerPath; | ||
newListeners; | ||
constructor(hmrClient, ownerPath) { | ||
this.hmrClient = hmrClient; | ||
this.ownerPath = ownerPath; | ||
if (!hmrClient.dataMap.has(ownerPath)) { | ||
hmrClient.dataMap.set(ownerPath, {}); | ||
} | ||
// when a file is hot updated, a new context is created | ||
// clear its stale callbacks | ||
const mod = hmrClient.hotModulesMap.get(ownerPath); | ||
if (mod) { | ||
mod.callbacks = []; | ||
} | ||
// clear stale custom event listeners | ||
const staleListeners = hmrClient.ctxToListenersMap.get(ownerPath); | ||
if (staleListeners) { | ||
for (const [event, staleFns] of staleListeners) { | ||
const listeners = hmrClient.customListenersMap.get(event); | ||
if (listeners) { | ||
hmrClient.customListenersMap.set(event, listeners.filter((l) => !staleFns.includes(l))); | ||
} | ||
} | ||
} | ||
this.newListeners = new Map(); | ||
hmrClient.ctxToListenersMap.set(ownerPath, this.newListeners); | ||
} | ||
get data() { | ||
return this.hmrClient.dataMap.get(this.ownerPath); | ||
} | ||
accept(deps, callback) { | ||
if (typeof deps === 'function' || !deps) { | ||
// self-accept: hot.accept(() => {}) | ||
this.acceptDeps([this.ownerPath], ([mod]) => deps?.(mod)); | ||
} | ||
else if (typeof deps === 'string') { | ||
// explicit deps | ||
this.acceptDeps([deps], ([mod]) => callback?.(mod)); | ||
} | ||
else if (Array.isArray(deps)) { | ||
this.acceptDeps(deps, callback); | ||
} | ||
else { | ||
throw new Error(`invalid hot.accept() usage.`); | ||
} | ||
} | ||
// export names (first arg) are irrelevant on the client side, they're | ||
// extracted in the server for propagation | ||
acceptExports(_, callback) { | ||
this.acceptDeps([this.ownerPath], ([mod]) => callback?.(mod)); | ||
} | ||
dispose(cb) { | ||
this.hmrClient.disposeMap.set(this.ownerPath, cb); | ||
} | ||
prune(cb) { | ||
this.hmrClient.pruneMap.set(this.ownerPath, cb); | ||
} | ||
// Kept for backward compatibility (#11036) | ||
// eslint-disable-next-line @typescript-eslint/no-empty-function | ||
decline() { } | ||
invalidate(message) { | ||
this.hmrClient.notifyListeners('vite:invalidate', { | ||
path: this.ownerPath, | ||
message, | ||
}); | ||
this.send('vite:invalidate', { path: this.ownerPath, message }); | ||
this.hmrClient.logger.debug(`[vite] invalidate ${this.ownerPath}${message ? `: ${message}` : ''}`); | ||
} | ||
on(event, cb) { | ||
const addToMap = (map) => { | ||
const existing = map.get(event) || []; | ||
existing.push(cb); | ||
map.set(event, existing); | ||
}; | ||
addToMap(this.hmrClient.customListenersMap); | ||
addToMap(this.newListeners); | ||
} | ||
off(event, cb) { | ||
const removeFromMap = (map) => { | ||
const existing = map.get(event); | ||
if (existing === undefined) { | ||
return; | ||
} | ||
const pruned = existing.filter((l) => l !== cb); | ||
if (pruned.length === 0) { | ||
map.delete(event); | ||
return; | ||
} | ||
map.set(event, pruned); | ||
}; | ||
removeFromMap(this.hmrClient.customListenersMap); | ||
removeFromMap(this.newListeners); | ||
} | ||
send(event, data) { | ||
this.hmrClient.messenger.send(JSON.stringify({ type: 'custom', event, data })); | ||
} | ||
acceptDeps(deps, callback = () => { }) { | ||
const mod = this.hmrClient.hotModulesMap.get(this.ownerPath) || { | ||
id: this.ownerPath, | ||
callbacks: [], | ||
}; | ||
mod.callbacks.push({ | ||
deps, | ||
fn: callback, | ||
}); | ||
this.hmrClient.hotModulesMap.set(this.ownerPath, mod); | ||
} | ||
} | ||
class HMRMessenger { | ||
connection; | ||
constructor(connection) { | ||
this.connection = connection; | ||
} | ||
queue = []; | ||
send(message) { | ||
this.queue.push(message); | ||
this.flush(); | ||
} | ||
flush() { | ||
if (this.connection.isReady()) { | ||
this.queue.forEach((msg) => this.connection.send(msg)); | ||
this.queue = []; | ||
} | ||
} | ||
} | ||
class HMRClient { | ||
logger; | ||
importUpdatedModule; | ||
hotModulesMap = new Map(); | ||
disposeMap = new Map(); | ||
pruneMap = new Map(); | ||
dataMap = new Map(); | ||
customListenersMap = new Map(); | ||
ctxToListenersMap = new Map(); | ||
messenger; | ||
constructor(logger, connection, | ||
// This allows implementing reloading via different methods depending on the environment | ||
importUpdatedModule) { | ||
this.logger = logger; | ||
this.importUpdatedModule = importUpdatedModule; | ||
this.messenger = new HMRMessenger(connection); | ||
} | ||
async notifyListeners(event, data) { | ||
const cbs = this.customListenersMap.get(event); | ||
if (cbs) { | ||
await Promise.allSettled(cbs.map((cb) => cb(data))); | ||
} | ||
} | ||
clear() { | ||
this.hotModulesMap.clear(); | ||
this.disposeMap.clear(); | ||
this.pruneMap.clear(); | ||
this.dataMap.clear(); | ||
this.customListenersMap.clear(); | ||
this.ctxToListenersMap.clear(); | ||
} | ||
// After an HMR update, some modules are no longer imported on the page | ||
// but they may have left behind side effects that need to be cleaned up | ||
// (.e.g style injections) | ||
// TODO Trigger their dispose callbacks. | ||
prunePaths(paths) { | ||
paths.forEach((path) => { | ||
const fn = this.pruneMap.get(path); | ||
if (fn) { | ||
fn(this.dataMap.get(path)); | ||
} | ||
}); | ||
} | ||
warnFailedUpdate(err, path) { | ||
if (!err.message.includes('fetch')) { | ||
this.logger.error(err); | ||
} | ||
this.logger.error(`[hmr] Failed to reload ${path}. ` + | ||
`This could be due to syntax errors or importing non-existent ` + | ||
`modules. (see errors above)`); | ||
} | ||
updateQueue = []; | ||
pendingUpdateQueue = false; | ||
/** | ||
* buffer multiple hot updates triggered by the same src change | ||
* so that they are invoked in the same order they were sent. | ||
* (otherwise the order may be inconsistent because of the http request round trip) | ||
*/ | ||
async queueUpdate(payload) { | ||
this.updateQueue.push(this.fetchUpdate(payload)); | ||
if (!this.pendingUpdateQueue) { | ||
this.pendingUpdateQueue = true; | ||
await Promise.resolve(); | ||
this.pendingUpdateQueue = false; | ||
const loading = [...this.updateQueue]; | ||
this.updateQueue = []; | ||
(await Promise.all(loading)).forEach((fn) => fn && fn()); | ||
} | ||
} | ||
async fetchUpdate(update) { | ||
const { path, acceptedPath } = update; | ||
const mod = this.hotModulesMap.get(path); | ||
if (!mod) { | ||
// In a code-splitting project, | ||
// it is common that the hot-updating module is not loaded yet. | ||
// https://github.com/vitejs/vite/issues/721 | ||
return; | ||
} | ||
let fetchedModule; | ||
const isSelfUpdate = path === acceptedPath; | ||
// determine the qualified callbacks before we re-import the modules | ||
const qualifiedCallbacks = mod.callbacks.filter(({ deps }) => deps.includes(acceptedPath)); | ||
if (isSelfUpdate || qualifiedCallbacks.length > 0) { | ||
const disposer = this.disposeMap.get(acceptedPath); | ||
if (disposer) | ||
await disposer(this.dataMap.get(acceptedPath)); | ||
try { | ||
fetchedModule = await this.importUpdatedModule(update); | ||
} | ||
catch (e) { | ||
this.warnFailedUpdate(e, acceptedPath); | ||
} | ||
} | ||
return () => { | ||
for (const { deps, fn } of qualifiedCallbacks) { | ||
fn(deps.map((dep) => (dep === acceptedPath ? fetchedModule : undefined))); | ||
} | ||
const loggedPath = isSelfUpdate ? path : `${acceptedPath} via ${path}`; | ||
this.logger.debug(`[vite] hot updated: ${loggedPath}`); | ||
}; | ||
} | ||
} | ||
const isWindows = typeof process !== 'undefined' && process.platform === 'win32'; | ||
const decodeBase64 = typeof atob !== 'undefined' | ||
? atob | ||
: (str) => Buffer.from(str, 'base64').toString('utf-8'); | ||
// currently we copy this from '../../constants' - maybe we can inline it somewhow? | ||
const NULL_BYTE_PLACEHOLDER = `__x00__`; | ||
const VALID_ID_PREFIX = `/@id/`; | ||
const VALID_ID_PREFIX = "/@id/", NULL_BYTE_PLACEHOLDER = "__x00__"; | ||
let SOURCEMAPPING_URL = "sourceMa"; | ||
SOURCEMAPPING_URL += "ppingURL"; | ||
const VITE_RUNTIME_SOURCEMAPPING_URL = `${SOURCEMAPPING_URL}=data:application/json;charset=utf-8`, isWindows = typeof process < "u" && process.platform === "win32"; | ||
function wrapId(id) { | ||
return id.startsWith(VALID_ID_PREFIX) | ||
? id | ||
: VALID_ID_PREFIX + id.replace('\0', NULL_BYTE_PLACEHOLDER); | ||
return id.startsWith(VALID_ID_PREFIX) ? id : VALID_ID_PREFIX + id.replace("\0", NULL_BYTE_PLACEHOLDER); | ||
} | ||
function unwrapId(id) { | ||
return id.startsWith(VALID_ID_PREFIX) | ||
? id.slice(VALID_ID_PREFIX.length).replace(NULL_BYTE_PLACEHOLDER, '\0') | ||
: id; | ||
return id.startsWith(VALID_ID_PREFIX) ? id.slice(VALID_ID_PREFIX.length).replace(NULL_BYTE_PLACEHOLDER, "\0") : id; | ||
} | ||
const windowsSlashRE = /\\/g; | ||
function slash(p) { | ||
return p.replace(windowsSlashRE, '/'); | ||
} | ||
const postfixRE = /[?#].*$/; | ||
function cleanUrl(url) { | ||
return url.replace(postfixRE, ''); | ||
return url.replace(postfixRE, ""); | ||
} | ||
function isPrimitive(value) { | ||
return !value || (typeof value !== 'object' && typeof value !== 'function'); | ||
return !value || typeof value != "object" && typeof value != "function"; | ||
} | ||
const CHAR_FORWARD_SLASH = 47; | ||
const CHAR_BACKWARD_SLASH = 92; | ||
const percentRegEx = /%/g; | ||
const backslashRegEx = /\\/g; | ||
const newlineRegEx = /\n/g; | ||
const carriageReturnRegEx = /\r/g; | ||
const tabRegEx = /\t/g; | ||
const questionRegex = /\?/g; | ||
const hashRegex = /#/g; | ||
function encodePathChars(filepath) { | ||
if (filepath.indexOf('%') !== -1) | ||
filepath = filepath.replace(percentRegEx, '%25'); | ||
// In posix, backslash is a valid character in paths: | ||
if (!isWindows && filepath.indexOf('\\') !== -1) | ||
filepath = filepath.replace(backslashRegEx, '%5C'); | ||
if (filepath.indexOf('\n') !== -1) | ||
filepath = filepath.replace(newlineRegEx, '%0A'); | ||
if (filepath.indexOf('\r') !== -1) | ||
filepath = filepath.replace(carriageReturnRegEx, '%0D'); | ||
if (filepath.indexOf('\t') !== -1) | ||
filepath = filepath.replace(tabRegEx, '%09'); | ||
return filepath; | ||
function withTrailingSlash(path) { | ||
return path[path.length - 1] !== "/" ? `${path}/` : path; | ||
} | ||
function posixPathToFileHref(posixPath) { | ||
let resolved = posixResolve(posixPath); | ||
// path.resolve strips trailing slashes so we must add them back | ||
const filePathLast = posixPath.charCodeAt(posixPath.length - 1); | ||
if ((filePathLast === CHAR_FORWARD_SLASH || | ||
(isWindows && filePathLast === CHAR_BACKWARD_SLASH)) && | ||
resolved[resolved.length - 1] !== '/') | ||
resolved += '/'; | ||
// Call encodePathChars first to avoid encoding % again for ? and #. | ||
resolved = encodePathChars(resolved); | ||
// Question and hash character should be included in pathname. | ||
// Therefore, encoding is required to eliminate parsing them in different states. | ||
// This is done as an optimization to not creating a URL instance and | ||
// later triggering pathname setter, which impacts performance | ||
if (resolved.indexOf('?') !== -1) | ||
resolved = resolved.replace(questionRegex, '%3F'); | ||
if (resolved.indexOf('#') !== -1) | ||
resolved = resolved.replace(hashRegex, '%23'); | ||
return new URL(`file://${resolved}`).href; | ||
const _DRIVE_LETTER_START_RE = /^[A-Za-z]:\//; | ||
function normalizeWindowsPath(input = "") { | ||
return input && input.replace(/\\/g, "/").replace(_DRIVE_LETTER_START_RE, (r) => r.toUpperCase()); | ||
} | ||
function posixDirname(filepath) { | ||
const normalizedPath = filepath.endsWith('/') | ||
? filepath.substring(0, filepath.length - 1) | ||
: filepath; | ||
return normalizedPath.substring(0, normalizedPath.lastIndexOf('/')) || '/'; | ||
} | ||
function toWindowsPath(path) { | ||
return path.replace(/\//g, '\\'); | ||
} | ||
// inlined from pathe to support environments without access to node:path | ||
const _IS_ABSOLUTE_RE = /^[/\\](?![/\\])|^[/\\]{2}(?!\.)|^[A-Za-z]:[/\\]/, _DRIVE_LETTER_RE = /^[A-Za-z]:$/; | ||
function cwd() { | ||
if (typeof process !== 'undefined' && typeof process.cwd === 'function') { | ||
return slash(process.cwd()); | ||
} | ||
return '/'; | ||
return typeof process < "u" && typeof process.cwd == "function" ? process.cwd().replace(/\\/g, "/") : "/"; | ||
} | ||
function posixResolve(...segments) { | ||
// Normalize windows arguments | ||
segments = segments.map((argument) => slash(argument)); | ||
let resolvedPath = ''; | ||
let resolvedAbsolute = false; | ||
for (let index = segments.length - 1; index >= -1 && !resolvedAbsolute; index--) { | ||
const path = index >= 0 ? segments[index] : cwd(); | ||
// Skip empty entries | ||
if (!path || path.length === 0) { | ||
continue; | ||
} | ||
resolvedPath = `${path}/${resolvedPath}`; | ||
resolvedAbsolute = isAbsolute(path); | ||
const resolve = function(...arguments_) { | ||
arguments_ = arguments_.map((argument) => normalizeWindowsPath(argument)); | ||
let resolvedPath = "", resolvedAbsolute = !1; | ||
for (let index = arguments_.length - 1; index >= -1 && !resolvedAbsolute; index--) { | ||
const path = index >= 0 ? arguments_[index] : cwd(); | ||
!path || path.length === 0 || (resolvedPath = `${path}/${resolvedPath}`, resolvedAbsolute = isAbsolute(path)); | ||
} | ||
return resolvedPath = normalizeString(resolvedPath, !resolvedAbsolute), resolvedAbsolute && !isAbsolute(resolvedPath) ? `/${resolvedPath}` : resolvedPath.length > 0 ? resolvedPath : "."; | ||
}; | ||
function normalizeString(path, allowAboveRoot) { | ||
let res = "", lastSegmentLength = 0, lastSlash = -1, dots = 0, char = null; | ||
for (let index = 0; index <= path.length; ++index) { | ||
if (index < path.length) | ||
char = path[index]; | ||
else { | ||
if (char === "/") | ||
break; | ||
char = "/"; | ||
} | ||
// At this point the path should be resolved to a full absolute path, but | ||
// handle relative paths to be safe (might happen when process.cwd() fails) | ||
// Normalize the path | ||
resolvedPath = normalizeString(resolvedPath, !resolvedAbsolute); | ||
if (resolvedAbsolute && !isAbsolute(resolvedPath)) { | ||
return `/${resolvedPath}`; | ||
} | ||
return resolvedPath.length > 0 ? resolvedPath : '.'; | ||
if (char === "/") { | ||
if (!(lastSlash === index - 1 || dots === 1)) | ||
if (dots === 2) { | ||
if (res.length < 2 || lastSegmentLength !== 2 || res[res.length - 1] !== "." || res[res.length - 2] !== ".") { | ||
if (res.length > 2) { | ||
const lastSlashIndex = res.lastIndexOf("/"); | ||
lastSlashIndex === -1 ? (res = "", lastSegmentLength = 0) : (res = res.slice(0, lastSlashIndex), lastSegmentLength = res.length - 1 - res.lastIndexOf("/")), lastSlash = index, dots = 0; | ||
continue; | ||
} else if (res.length > 0) { | ||
res = "", lastSegmentLength = 0, lastSlash = index, dots = 0; | ||
continue; | ||
} | ||
} | ||
allowAboveRoot && (res += res.length > 0 ? "/.." : "..", lastSegmentLength = 2); | ||
} else | ||
res.length > 0 ? res += `/${path.slice(lastSlash + 1, index)}` : res = path.slice(lastSlash + 1, index), lastSegmentLength = index - lastSlash - 1; | ||
lastSlash = index, dots = 0; | ||
} else | ||
char === "." && dots !== -1 ? ++dots : dots = -1; | ||
} | ||
return res; | ||
} | ||
const _IS_ABSOLUTE_RE = /^[/\\](?![/\\])|^[/\\]{2}(?!\.)|^[A-Za-z]:[/\\]/; | ||
function isAbsolute(p) { | ||
return _IS_ABSOLUTE_RE.test(p); | ||
const isAbsolute = function(p) { | ||
return _IS_ABSOLUTE_RE.test(p); | ||
}, dirname = function(p) { | ||
const segments = normalizeWindowsPath(p).replace(/\/$/, "").split("/").slice(0, -1); | ||
return segments.length === 1 && _DRIVE_LETTER_RE.test(segments[0]) && (segments[0] += "/"), segments.join("/") || (isAbsolute(p) ? "/" : "."); | ||
}, decodeBase64 = typeof atob < "u" ? atob : (str) => Buffer.from(str, "base64").toString("utf-8"), CHAR_FORWARD_SLASH = 47, CHAR_BACKWARD_SLASH = 92, percentRegEx = /%/g, backslashRegEx = /\\/g, newlineRegEx = /\n/g, carriageReturnRegEx = /\r/g, tabRegEx = /\t/g, questionRegex = /\?/g, hashRegex = /#/g; | ||
function encodePathChars(filepath) { | ||
return filepath.indexOf("%") !== -1 && (filepath = filepath.replace(percentRegEx, "%25")), !isWindows && filepath.indexOf("\\") !== -1 && (filepath = filepath.replace(backslashRegEx, "%5C")), filepath.indexOf(` | ||
`) !== -1 && (filepath = filepath.replace(newlineRegEx, "%0A")), filepath.indexOf("\r") !== -1 && (filepath = filepath.replace(carriageReturnRegEx, "%0D")), filepath.indexOf(" ") !== -1 && (filepath = filepath.replace(tabRegEx, "%09")), filepath; | ||
} | ||
// Resolves . and .. elements in a path with directory names | ||
function normalizeString(path, allowAboveRoot) { | ||
let res = ''; | ||
let lastSegmentLength = 0; | ||
let lastSlash = -1; | ||
let dots = 0; | ||
let char = null; | ||
for (let index = 0; index <= path.length; ++index) { | ||
if (index < path.length) { | ||
char = path[index]; | ||
} | ||
else if (char === '/') { | ||
break; | ||
} | ||
else { | ||
char = '/'; | ||
} | ||
if (char === '/') { | ||
if (lastSlash === index - 1 || dots === 1) ; | ||
else if (dots === 2) { | ||
if (res.length < 2 || | ||
lastSegmentLength !== 2 || | ||
res[res.length - 1] !== '.' || | ||
res[res.length - 2] !== '.') { | ||
if (res.length > 2) { | ||
const lastSlashIndex = res.lastIndexOf('/'); | ||
if (lastSlashIndex === -1) { | ||
res = ''; | ||
lastSegmentLength = 0; | ||
} | ||
else { | ||
res = res.slice(0, lastSlashIndex); | ||
lastSegmentLength = res.length - 1 - res.lastIndexOf('/'); | ||
} | ||
lastSlash = index; | ||
dots = 0; | ||
continue; | ||
} | ||
else if (res.length > 0) { | ||
res = ''; | ||
lastSegmentLength = 0; | ||
lastSlash = index; | ||
dots = 0; | ||
continue; | ||
} | ||
} | ||
if (allowAboveRoot) { | ||
res += res.length > 0 ? '/..' : '..'; | ||
lastSegmentLength = 2; | ||
} | ||
} | ||
else { | ||
if (res.length > 0) { | ||
res += `/${path.slice(lastSlash + 1, index)}`; | ||
} | ||
else { | ||
res = path.slice(lastSlash + 1, index); | ||
} | ||
lastSegmentLength = index - lastSlash - 1; | ||
} | ||
lastSlash = index; | ||
dots = 0; | ||
} | ||
else if (char === '.' && dots !== -1) { | ||
++dots; | ||
} | ||
else { | ||
dots = -1; | ||
} | ||
} | ||
return res; | ||
const posixDirname = dirname, posixResolve = resolve; | ||
function posixPathToFileHref(posixPath) { | ||
let resolved = posixResolve(posixPath); | ||
const filePathLast = posixPath.charCodeAt(posixPath.length - 1); | ||
return (filePathLast === CHAR_FORWARD_SLASH || isWindows && filePathLast === CHAR_BACKWARD_SLASH) && resolved[resolved.length - 1] !== "/" && (resolved += "/"), resolved = encodePathChars(resolved), resolved.indexOf("?") !== -1 && (resolved = resolved.replace(questionRegex, "%3F")), resolved.indexOf("#") !== -1 && (resolved = resolved.replace(hashRegex, "%23")), new URL(`file://${resolved}`).href; | ||
} | ||
class DecodedMap { | ||
map; | ||
_encoded; | ||
_decoded; | ||
_decodedMemo; | ||
url; | ||
version; | ||
names = []; | ||
resolvedSources; | ||
constructor(map, from) { | ||
this.map = map; | ||
const { mappings, names, sources } = map; | ||
this.version = map.version; | ||
this.names = names || []; | ||
this._encoded = mappings || ''; | ||
this._decodedMemo = memoizedState(); | ||
this.url = from; | ||
this.resolvedSources = (sources || []).map((s) => posixResolve(s || '', from)); | ||
function toWindowsPath(path) { | ||
return path.replace(/\//g, "\\"); | ||
} | ||
const comma = ",".charCodeAt(0), chars = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/", intToChar = new Uint8Array(64), charToInt = new Uint8Array(128); | ||
for (let i = 0; i < chars.length; i++) { | ||
const c = chars.charCodeAt(i); | ||
intToChar[i] = c, charToInt[c] = i; | ||
} | ||
function decode(mappings) { | ||
const state = new Int32Array(5), decoded = []; | ||
let index = 0; | ||
do { | ||
const semi = indexOf(mappings, index), line = []; | ||
let sorted = !0, lastCol = 0; | ||
state[0] = 0; | ||
for (let i = index; i < semi; i++) { | ||
let seg; | ||
i = decodeInteger(mappings, i, state, 0); | ||
const col = state[0]; | ||
col < lastCol && (sorted = !1), lastCol = col, hasMoreVlq(mappings, i, semi) ? (i = decodeInteger(mappings, i, state, 1), i = decodeInteger(mappings, i, state, 2), i = decodeInteger(mappings, i, state, 3), hasMoreVlq(mappings, i, semi) ? (i = decodeInteger(mappings, i, state, 4), seg = [col, state[1], state[2], state[3], state[4]]) : seg = [col, state[1], state[2], state[3]]) : seg = [col], line.push(seg); | ||
} | ||
sorted || sort(line), decoded.push(line), index = semi + 1; | ||
} while (index <= mappings.length); | ||
return decoded; | ||
} | ||
// This is a copy of all methods that we need for decoding a source map from "@jridgewell/trace-mapping" | ||
function indexOf(mappings, index) { | ||
const idx = mappings.indexOf(';', index); | ||
return idx === -1 ? mappings.length : idx; | ||
const idx = mappings.indexOf(";", index); | ||
return idx === -1 ? mappings.length : idx; | ||
} | ||
const chars = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/'; | ||
const charToInt = new Uint8Array(128); // z is 122 in ASCII | ||
for (let i = 0; i < chars.length; i++) { | ||
const c = chars.charCodeAt(i); | ||
charToInt[c] = i; | ||
} | ||
function decodeInteger(mappings, pos, state, j) { | ||
let value = 0; | ||
let shift = 0; | ||
let integer = 0; | ||
do { | ||
const c = mappings.charCodeAt(pos++); | ||
integer = charToInt[c]; | ||
value |= (integer & 31) << shift; | ||
shift += 5; | ||
} while (integer & 32); | ||
const shouldNegate = value & 1; | ||
value >>>= 1; | ||
if (shouldNegate) { | ||
value = -0x80000000 | -value; | ||
} | ||
state[j] += value; | ||
return pos; | ||
let value = 0, shift = 0, integer = 0; | ||
do { | ||
const c = mappings.charCodeAt(pos++); | ||
integer = charToInt[c], value |= (integer & 31) << shift, shift += 5; | ||
} while (integer & 32); | ||
const shouldNegate = value & 1; | ||
return value >>>= 1, shouldNegate && (value = -2147483648 | -value), state[j] += value, pos; | ||
} | ||
const comma = ','.charCodeAt(0); | ||
function hasMoreVlq(mappings, i, length) { | ||
if (i >= length) | ||
return false; | ||
return mappings.charCodeAt(i) !== comma; | ||
return i >= length ? !1 : mappings.charCodeAt(i) !== comma; | ||
} | ||
function decode(mappings) { | ||
const state = new Int32Array(5); | ||
const decoded = []; | ||
let index = 0; | ||
do { | ||
const semi = indexOf(mappings, index); | ||
const line = []; | ||
let sorted = true; | ||
let lastCol = 0; | ||
state[0] = 0; | ||
for (let i = index; i < semi; i++) { | ||
let seg; | ||
i = decodeInteger(mappings, i, state, 0); // genColumn | ||
const col = state[0]; | ||
if (col < lastCol) | ||
sorted = false; | ||
lastCol = col; | ||
if (hasMoreVlq(mappings, i, semi)) { | ||
i = decodeInteger(mappings, i, state, 1); // sourcesIndex | ||
i = decodeInteger(mappings, i, state, 2); // sourceLine | ||
i = decodeInteger(mappings, i, state, 3); // sourceColumn | ||
if (hasMoreVlq(mappings, i, semi)) { | ||
i = decodeInteger(mappings, i, state, 4); // namesIndex | ||
seg = [col, state[1], state[2], state[3], state[4]]; | ||
} | ||
else { | ||
seg = [col, state[1], state[2], state[3]]; | ||
} | ||
} | ||
else { | ||
seg = [col]; | ||
} | ||
line.push(seg); | ||
} | ||
if (!sorted) | ||
line.sort((a, b) => a[0] - b[0]); | ||
decoded.push(line); | ||
index = semi + 1; | ||
} while (index <= mappings.length); | ||
return decoded; | ||
function sort(line) { | ||
line.sort(sortComparator); | ||
} | ||
const LINE_GTR_ZERO = '`line` must be greater than 0 (lines start at line 1)'; | ||
const COL_GTR_EQ_ZERO = '`column` must be greater than or equal to 0 (columns start at column 0)'; | ||
const COLUMN = 0; | ||
const SOURCES_INDEX = 1; | ||
const SOURCE_LINE = 2; | ||
const SOURCE_COLUMN = 3; | ||
const NAMES_INDEX = 4; | ||
function OMapping(source, line, column, name) { | ||
return { source, line, column, name }; | ||
function sortComparator(a, b) { | ||
return a[0] - b[0]; | ||
} | ||
const COLUMN = 0, SOURCES_INDEX = 1, SOURCE_LINE = 2, SOURCE_COLUMN = 3, NAMES_INDEX = 4; | ||
let found = !1; | ||
function binarySearch(haystack, needle, low, high) { | ||
for (; low <= high; ) { | ||
const mid = low + (high - low >> 1), cmp = haystack[mid][COLUMN] - needle; | ||
if (cmp === 0) | ||
return found = !0, mid; | ||
cmp < 0 ? low = mid + 1 : high = mid - 1; | ||
} | ||
return found = !1, low - 1; | ||
} | ||
function upperBound(haystack, needle, index) { | ||
for (let i = index + 1; i < haystack.length && haystack[i][COLUMN] === needle; index = i++) | ||
; | ||
return index; | ||
} | ||
function memoizedBinarySearch(haystack, needle, state, key) { | ||
const { lastKey, lastNeedle, lastIndex } = state; | ||
let low = 0, high = haystack.length - 1; | ||
if (key === lastKey) { | ||
if (needle === lastNeedle) | ||
return found = lastIndex !== -1 && haystack[lastIndex][COLUMN] === needle, lastIndex; | ||
needle >= lastNeedle ? low = lastIndex === -1 ? 0 : lastIndex : high = lastIndex; | ||
} | ||
return state.lastKey = key, state.lastNeedle = needle, state.lastIndex = binarySearch(haystack, needle, low, high); | ||
} | ||
const LINE_GTR_ZERO = "`line` must be greater than 0 (lines start at line 1)", COL_GTR_EQ_ZERO = "`column` must be greater than or equal to 0 (columns start at column 0)"; | ||
function cast(map) { | ||
return map; | ||
} | ||
function decodedMappings(map) { | ||
return map._decoded || (map._decoded = decode(map._encoded)); | ||
var _a; | ||
return (_a = map)._decoded || (_a._decoded = decode(map._encoded)); | ||
} | ||
let found = false; | ||
function binarySearch(haystack, needle, low, high) { | ||
while (low <= high) { | ||
const mid = low + ((high - low) >> 1); | ||
const cmp = haystack[mid][COLUMN] - needle; | ||
if (cmp === 0) { | ||
found = true; | ||
return mid; | ||
} | ||
if (cmp < 0) { | ||
low = mid + 1; | ||
} | ||
else { | ||
high = mid - 1; | ||
} | ||
} | ||
found = false; | ||
return low - 1; | ||
function originalPositionFor(map, needle) { | ||
let { line, column, bias } = needle; | ||
if (line--, line < 0) | ||
throw new Error(LINE_GTR_ZERO); | ||
if (column < 0) | ||
throw new Error(COL_GTR_EQ_ZERO); | ||
const decoded = decodedMappings(map); | ||
if (line >= decoded.length) | ||
return OMapping(null, null, null, null); | ||
const segments = decoded[line], index = traceSegmentInternal(segments, map._decodedMemo, line, column); | ||
if (index === -1) | ||
return OMapping(null, null, null, null); | ||
const segment = segments[index]; | ||
if (segment.length === 1) | ||
return OMapping(null, null, null, null); | ||
const { names, resolvedSources } = map; | ||
return OMapping(resolvedSources[segment[SOURCES_INDEX]], segment[SOURCE_LINE] + 1, segment[SOURCE_COLUMN], segment.length === 5 ? names[segment[NAMES_INDEX]] : null); | ||
} | ||
function lowerBound(haystack, needle, index) { | ||
for (let i = index - 1; i >= 0; index = i--) { | ||
if (haystack[i][COLUMN] !== needle) | ||
break; | ||
} | ||
return index; | ||
function OMapping(source, line, column, name) { | ||
return { source, line, column, name }; | ||
} | ||
function memoizedState() { | ||
return { | ||
lastKey: -1, | ||
lastNeedle: -1, | ||
lastIndex: -1, | ||
}; | ||
function traceSegmentInternal(segments, memo, line, column, bias) { | ||
let index = memoizedBinarySearch(segments, column, memo, line); | ||
return found ? index = upperBound(segments, column, index) : index++, index === -1 || index === segments.length ? -1 : index; | ||
} | ||
function memoizedBinarySearch(haystack, needle, state, key) { | ||
const { lastKey, lastNeedle, lastIndex } = state; | ||
let low = 0; | ||
let high = haystack.length - 1; | ||
if (key === lastKey) { | ||
if (needle === lastNeedle) { | ||
found = lastIndex !== -1 && haystack[lastIndex][COLUMN] === needle; | ||
return lastIndex; | ||
} | ||
if (needle >= lastNeedle) { | ||
// lastIndex may be -1 if the previous needle was not found. | ||
low = lastIndex === -1 ? 0 : lastIndex; | ||
} | ||
else { | ||
high = lastIndex; | ||
} | ||
} | ||
state.lastKey = key; | ||
state.lastNeedle = needle; | ||
return (state.lastIndex = binarySearch(haystack, needle, low, high)); | ||
class DecodedMap { | ||
map; | ||
_encoded; | ||
_decoded; | ||
_decodedMemo; | ||
url; | ||
version; | ||
names = []; | ||
resolvedSources; | ||
constructor(map, from) { | ||
this.map = map; | ||
const { mappings, names, sources } = map; | ||
this.version = map.version, this.names = names || [], this._encoded = mappings || "", this._decodedMemo = memoizedState(), this.url = from, this.resolvedSources = (sources || []).map((s) => posixResolve(s || "", from)); | ||
} | ||
} | ||
function traceSegmentInternal(segments, memo, line, column) { | ||
let index = memoizedBinarySearch(segments, column, memo, line); | ||
if (found) { | ||
index = lowerBound(segments, column, index); | ||
} | ||
if (index === -1 || index === segments.length) | ||
return -1; | ||
return index; | ||
function memoizedState() { | ||
return { | ||
lastKey: -1, | ||
lastNeedle: -1, | ||
lastIndex: -1 | ||
}; | ||
} | ||
function getOriginalPosition(map, { line, column }) { | ||
line--; | ||
if (line < 0) | ||
throw new Error(LINE_GTR_ZERO); | ||
if (column < 0) | ||
throw new Error(COL_GTR_EQ_ZERO); | ||
map._decodedMemo ??= memoizedState(); | ||
const decoded = decodedMappings(map); | ||
// It's common for parent source maps to have pointers to lines that have no | ||
// mapping (like a "//# sourceMappingURL=") at the end of the child file. | ||
if (line >= decoded.length) | ||
return null; | ||
const segments = decoded[line]; | ||
const index = traceSegmentInternal(segments, map._decodedMemo, line, column); | ||
if (index === -1) | ||
return null; | ||
const segment = segments[index]; | ||
if (segment.length === 1) | ||
return null; | ||
const { names, resolvedSources } = map; | ||
return OMapping(resolvedSources[segment[SOURCES_INDEX]], segment[SOURCE_LINE] + 1, segment[SOURCE_COLUMN], segment.length === 5 ? names[segment[NAMES_INDEX]] : null); | ||
function getOriginalPosition(map, needle) { | ||
const result = originalPositionFor(map, needle); | ||
return result.column == null ? null : result; | ||
} | ||
let SOURCEMAPPING_URL = 'sourceMa'; | ||
SOURCEMAPPING_URL += 'ppingURL'; | ||
const VITE_RUNTIME_SOURCEMAPPING_URL = `${SOURCEMAPPING_URL}=data:application/json;charset=utf-8`; | ||
const VITE_RUNTIME_SOURCEMAPPING_REGEXP = new RegExp(`//# ${VITE_RUNTIME_SOURCEMAPPING_URL};base64,(.+)`); | ||
class ModuleCacheMap extends Map { | ||
root; | ||
constructor(root, entries) { | ||
super(entries); | ||
this.root = withTrailingSlash(root); | ||
root; | ||
constructor(root, entries) { | ||
super(entries), this.root = withTrailingSlash(root); | ||
} | ||
normalize(fsPath) { | ||
return normalizeModuleId(fsPath, this.root); | ||
} | ||
/** | ||
* Assign partial data to the map | ||
*/ | ||
update(fsPath, mod) { | ||
return fsPath = this.normalize(fsPath), super.has(fsPath) ? Object.assign(super.get(fsPath), mod) : this.setByModuleId(fsPath, mod), this; | ||
} | ||
setByModuleId(modulePath, mod) { | ||
return super.set(modulePath, mod); | ||
} | ||
set(fsPath, mod) { | ||
return this.setByModuleId(this.normalize(fsPath), mod); | ||
} | ||
getByModuleId(modulePath) { | ||
super.has(modulePath) || this.setByModuleId(modulePath, {}); | ||
const mod = super.get(modulePath); | ||
return mod.imports || Object.assign(mod, { | ||
imports: /* @__PURE__ */ new Set(), | ||
importers: /* @__PURE__ */ new Set() | ||
}), mod; | ||
} | ||
get(fsPath) { | ||
return this.getByModuleId(this.normalize(fsPath)); | ||
} | ||
deleteByModuleId(modulePath) { | ||
return super.delete(modulePath); | ||
} | ||
delete(fsPath) { | ||
return this.deleteByModuleId(this.normalize(fsPath)); | ||
} | ||
invalidate(id) { | ||
const module = this.get(id); | ||
module.evaluated = !1, module.meta = void 0, module.map = void 0, module.promise = void 0, module.exports = void 0, module.imports?.clear(); | ||
} | ||
isImported({ importedId, importedBy }, seen = /* @__PURE__ */ new Set()) { | ||
if (importedId = this.normalize(importedId), importedBy = this.normalize(importedBy), importedBy === importedId) | ||
return !0; | ||
if (seen.has(importedId)) | ||
return !1; | ||
seen.add(importedId); | ||
const importers = this.getByModuleId(importedId)?.importers; | ||
if (!importers) | ||
return !1; | ||
if (importers.has(importedBy)) | ||
return !0; | ||
for (const importer of importers) | ||
if (this.isImported({ | ||
importedBy, | ||
importedId: importer | ||
})) | ||
return !0; | ||
return !1; | ||
} | ||
/** | ||
* Invalidate modules that dependent on the given modules, up to the main entry | ||
*/ | ||
invalidateDepTree(ids, invalidated = /* @__PURE__ */ new Set()) { | ||
for (const _id of ids) { | ||
const id = this.normalize(_id); | ||
if (invalidated.has(id)) | ||
continue; | ||
invalidated.add(id); | ||
const mod = super.get(id); | ||
mod?.importers && this.invalidateDepTree(mod.importers, invalidated), super.delete(id); | ||
} | ||
normalize(fsPath) { | ||
return normalizeModuleId(fsPath, this.root); | ||
return invalidated; | ||
} | ||
/** | ||
* Invalidate dependency modules of the given modules, down to the bottom-level dependencies | ||
*/ | ||
invalidateSubDepTree(ids, invalidated = /* @__PURE__ */ new Set()) { | ||
for (const _id of ids) { | ||
const id = this.normalize(_id); | ||
if (invalidated.has(id)) | ||
continue; | ||
invalidated.add(id); | ||
const subIds = Array.from(super.entries()).filter(([, mod]) => mod.importers?.has(id)).map(([key]) => key); | ||
subIds.length && this.invalidateSubDepTree(subIds, invalidated), super.delete(id); | ||
} | ||
/** | ||
* Assign partial data to the map | ||
*/ | ||
update(fsPath, mod) { | ||
fsPath = this.normalize(fsPath); | ||
if (!super.has(fsPath)) | ||
this.setByModuleId(fsPath, mod); | ||
else | ||
Object.assign(super.get(fsPath), mod); | ||
return this; | ||
} | ||
setByModuleId(modulePath, mod) { | ||
return super.set(modulePath, mod); | ||
} | ||
set(fsPath, mod) { | ||
return this.setByModuleId(this.normalize(fsPath), mod); | ||
} | ||
getByModuleId(modulePath) { | ||
if (!super.has(modulePath)) | ||
this.setByModuleId(modulePath, {}); | ||
const mod = super.get(modulePath); | ||
if (!mod.imports) { | ||
Object.assign(mod, { | ||
imports: new Set(), | ||
importers: new Set(), | ||
}); | ||
} | ||
return mod; | ||
} | ||
get(fsPath) { | ||
return this.getByModuleId(this.normalize(fsPath)); | ||
} | ||
deleteByModuleId(modulePath) { | ||
return super.delete(modulePath); | ||
} | ||
delete(fsPath) { | ||
return this.deleteByModuleId(this.normalize(fsPath)); | ||
} | ||
/** | ||
* Invalidate modules that dependent on the given modules, up to the main entry | ||
*/ | ||
invalidateDepTree(ids, invalidated = new Set()) { | ||
for (const _id of ids) { | ||
const id = this.normalize(_id); | ||
if (invalidated.has(id)) | ||
continue; | ||
invalidated.add(id); | ||
const mod = super.get(id); | ||
if (mod?.importers) | ||
this.invalidateDepTree(mod.importers, invalidated); | ||
super.delete(id); | ||
} | ||
return invalidated; | ||
} | ||
/** | ||
* Invalidate dependency modules of the given modules, down to the bottom-level dependencies | ||
*/ | ||
invalidateSubDepTree(ids, invalidated = new Set()) { | ||
for (const _id of ids) { | ||
const id = this.normalize(_id); | ||
if (invalidated.has(id)) | ||
continue; | ||
invalidated.add(id); | ||
const subIds = Array.from(super.entries()) | ||
.filter(([, mod]) => mod.importers?.has(id)) | ||
.map(([key]) => key); | ||
subIds.length && this.invalidateSubDepTree(subIds, invalidated); | ||
super.delete(id); | ||
} | ||
return invalidated; | ||
} | ||
getSourceMap(moduleId) { | ||
const mod = this.get(moduleId); | ||
if (mod.map) | ||
return mod.map; | ||
if (!mod.meta || !('code' in mod.meta)) | ||
return null; | ||
const mapString = mod.meta.code.match(VITE_RUNTIME_SOURCEMAPPING_REGEXP)?.[1]; | ||
if (!mapString) | ||
return null; | ||
const baseFile = mod.meta.file || moduleId.split('?')[0]; | ||
mod.map = new DecodedMap(JSON.parse(decodeBase64(mapString)), baseFile); | ||
return mod.map; | ||
} | ||
return invalidated; | ||
} | ||
getSourceMap(moduleId) { | ||
const mod = this.get(moduleId); | ||
if (mod.map) | ||
return mod.map; | ||
if (!mod.meta || !("code" in mod.meta)) | ||
return null; | ||
const mapString = mod.meta.code.match(VITE_RUNTIME_SOURCEMAPPING_REGEXP)?.[1]; | ||
if (!mapString) | ||
return null; | ||
const baseFile = mod.meta.file || moduleId.split("?")[0]; | ||
return mod.map = new DecodedMap(JSON.parse(decodeBase64(mapString)), baseFile), mod.map; | ||
} | ||
} | ||
function withTrailingSlash(path) { | ||
if (path[path.length - 1] !== '/') { | ||
return `${path}/`; | ||
} | ||
return path; | ||
const prefixedBuiltins = /* @__PURE__ */ new Set(["node:test"]); | ||
function normalizeModuleId(file, root) { | ||
if (prefixedBuiltins.has(file)) | ||
return file; | ||
let unixFile = file.replace(/\\/g, "/").replace(/^\/@fs\//, isWindows ? "" : "/").replace(/^node:/, "").replace(/^\/+/, "/"); | ||
return unixFile.startsWith(root) && (unixFile = unixFile.slice(root.length - 1)), unixFile.replace(/^file:\//, "/"); | ||
} | ||
// unique id that is not available as "$bare_import" like "test" | ||
const prefixedBuiltins = new Set(['node:test']); | ||
// transform file url to id | ||
// virtual:custom -> virtual:custom | ||
// \0custom -> \0custom | ||
// /root/id -> /id | ||
// /root/id.js -> /id.js | ||
// C:/root/id.js -> /id.js | ||
// C:\root\id.js -> /id.js | ||
function normalizeModuleId(file, root) { | ||
if (prefixedBuiltins.has(file)) | ||
return file; | ||
// unix style, but Windows path still starts with the drive letter to check the root | ||
let unixFile = file | ||
.replace(/\\/g, '/') | ||
.replace(/^\/@fs\//, isWindows ? '' : '/') | ||
.replace(/^node:/, '') | ||
.replace(/^\/+/, '/'); | ||
if (unixFile.startsWith(root)) { | ||
// keep slash | ||
unixFile = unixFile.slice(root.length - 1); | ||
class HMRContext { | ||
hmrClient; | ||
ownerPath; | ||
newListeners; | ||
constructor(hmrClient, ownerPath) { | ||
this.hmrClient = hmrClient, this.ownerPath = ownerPath, hmrClient.dataMap.has(ownerPath) || hmrClient.dataMap.set(ownerPath, {}); | ||
const mod = hmrClient.hotModulesMap.get(ownerPath); | ||
mod && (mod.callbacks = []); | ||
const staleListeners = hmrClient.ctxToListenersMap.get(ownerPath); | ||
if (staleListeners) | ||
for (const [event, staleFns] of staleListeners) { | ||
const listeners = hmrClient.customListenersMap.get(event); | ||
listeners && hmrClient.customListenersMap.set(event, listeners.filter((l) => !staleFns.includes(l))); | ||
} | ||
this.newListeners = /* @__PURE__ */ new Map(), hmrClient.ctxToListenersMap.set(ownerPath, this.newListeners); | ||
} | ||
get data() { | ||
return this.hmrClient.dataMap.get(this.ownerPath); | ||
} | ||
accept(deps, callback) { | ||
if (typeof deps == "function" || !deps) | ||
this.acceptDeps([this.ownerPath], ([mod]) => deps?.(mod)); | ||
else if (typeof deps == "string") | ||
this.acceptDeps([deps], ([mod]) => callback?.(mod)); | ||
else if (Array.isArray(deps)) | ||
this.acceptDeps(deps, callback); | ||
else | ||
throw new Error("invalid hot.accept() usage."); | ||
} | ||
// export names (first arg) are irrelevant on the client side, they're | ||
// extracted in the server for propagation | ||
acceptExports(_, callback) { | ||
this.acceptDeps([this.ownerPath], ([mod]) => callback?.(mod)); | ||
} | ||
dispose(cb) { | ||
this.hmrClient.disposeMap.set(this.ownerPath, cb); | ||
} | ||
prune(cb) { | ||
this.hmrClient.pruneMap.set(this.ownerPath, cb); | ||
} | ||
// Kept for backward compatibility (#11036) | ||
// eslint-disable-next-line @typescript-eslint/no-empty-function | ||
decline() { | ||
} | ||
invalidate(message) { | ||
this.hmrClient.notifyListeners("vite:invalidate", { | ||
path: this.ownerPath, | ||
message | ||
}), this.send("vite:invalidate", { path: this.ownerPath, message }), this.hmrClient.logger.debug(`[vite] invalidate ${this.ownerPath}${message ? `: ${message}` : ""}`); | ||
} | ||
on(event, cb) { | ||
const addToMap = (map) => { | ||
const existing = map.get(event) || []; | ||
existing.push(cb), map.set(event, existing); | ||
}; | ||
addToMap(this.hmrClient.customListenersMap), addToMap(this.newListeners); | ||
} | ||
off(event, cb) { | ||
const removeFromMap = (map) => { | ||
const existing = map.get(event); | ||
if (existing === void 0) | ||
return; | ||
const pruned = existing.filter((l) => l !== cb); | ||
if (pruned.length === 0) { | ||
map.delete(event); | ||
return; | ||
} | ||
map.set(event, pruned); | ||
}; | ||
removeFromMap(this.hmrClient.customListenersMap), removeFromMap(this.newListeners); | ||
} | ||
send(event, data) { | ||
this.hmrClient.messenger.send(JSON.stringify({ type: "custom", event, data })); | ||
} | ||
acceptDeps(deps, callback = () => { | ||
}) { | ||
const mod = this.hmrClient.hotModulesMap.get(this.ownerPath) || { | ||
id: this.ownerPath, | ||
callbacks: [] | ||
}; | ||
mod.callbacks.push({ | ||
deps, | ||
fn: callback | ||
}), this.hmrClient.hotModulesMap.set(this.ownerPath, mod); | ||
} | ||
} | ||
class HMRMessenger { | ||
connection; | ||
constructor(connection) { | ||
this.connection = connection; | ||
} | ||
queue = []; | ||
send(message) { | ||
this.queue.push(message), this.flush(); | ||
} | ||
flush() { | ||
this.connection.isReady() && (this.queue.forEach((msg) => this.connection.send(msg)), this.queue = []); | ||
} | ||
} | ||
class HMRClient { | ||
logger; | ||
importUpdatedModule; | ||
hotModulesMap = /* @__PURE__ */ new Map(); | ||
disposeMap = /* @__PURE__ */ new Map(); | ||
pruneMap = /* @__PURE__ */ new Map(); | ||
dataMap = /* @__PURE__ */ new Map(); | ||
customListenersMap = /* @__PURE__ */ new Map(); | ||
ctxToListenersMap = /* @__PURE__ */ new Map(); | ||
messenger; | ||
constructor(logger, connection, importUpdatedModule) { | ||
this.logger = logger, this.importUpdatedModule = importUpdatedModule, this.messenger = new HMRMessenger(connection); | ||
} | ||
async notifyListeners(event, data) { | ||
const cbs = this.customListenersMap.get(event); | ||
cbs && await Promise.allSettled(cbs.map((cb) => cb(data))); | ||
} | ||
clear() { | ||
this.hotModulesMap.clear(), this.disposeMap.clear(), this.pruneMap.clear(), this.dataMap.clear(), this.customListenersMap.clear(), this.ctxToListenersMap.clear(); | ||
} | ||
// After an HMR update, some modules are no longer imported on the page | ||
// but they may have left behind side effects that need to be cleaned up | ||
// (.e.g style injections) | ||
// TODO Trigger their dispose callbacks. | ||
prunePaths(paths) { | ||
paths.forEach((path) => { | ||
const fn = this.pruneMap.get(path); | ||
fn && fn(this.dataMap.get(path)); | ||
}); | ||
} | ||
warnFailedUpdate(err, path) { | ||
err.message.includes("fetch") || this.logger.error(err), this.logger.error(`[hmr] Failed to reload ${path}. This could be due to syntax errors or importing non-existent modules. (see errors above)`); | ||
} | ||
updateQueue = []; | ||
pendingUpdateQueue = !1; | ||
/** | ||
* buffer multiple hot updates triggered by the same src change | ||
* so that they are invoked in the same order they were sent. | ||
* (otherwise the order may be inconsistent because of the http request round trip) | ||
*/ | ||
async queueUpdate(payload) { | ||
if (this.updateQueue.push(this.fetchUpdate(payload)), !this.pendingUpdateQueue) { | ||
this.pendingUpdateQueue = !0, await Promise.resolve(), this.pendingUpdateQueue = !1; | ||
const loading = [...this.updateQueue]; | ||
this.updateQueue = [], (await Promise.all(loading)).forEach((fn) => fn && fn()); | ||
} | ||
// if it's not in the root, keep it as a path, not a URL | ||
return unixFile.replace(/^file:\//, '/'); | ||
} | ||
async fetchUpdate(update) { | ||
const { path, acceptedPath } = update, mod = this.hotModulesMap.get(path); | ||
if (!mod) | ||
return; | ||
let fetchedModule; | ||
const isSelfUpdate = path === acceptedPath, qualifiedCallbacks = mod.callbacks.filter(({ deps }) => deps.includes(acceptedPath)); | ||
if (isSelfUpdate || qualifiedCallbacks.length > 0) { | ||
const disposer = this.disposeMap.get(acceptedPath); | ||
disposer && await disposer(this.dataMap.get(acceptedPath)); | ||
try { | ||
fetchedModule = await this.importUpdatedModule(update); | ||
} catch (e) { | ||
this.warnFailedUpdate(e, acceptedPath); | ||
} | ||
} | ||
return () => { | ||
for (const { deps, fn } of qualifiedCallbacks) | ||
fn(deps.map((dep) => dep === acceptedPath ? fetchedModule : void 0)); | ||
const loggedPath = isSelfUpdate ? path : `${acceptedPath} via ${path}`; | ||
this.logger.debug(`[vite] hot updated: ${loggedPath}`); | ||
}; | ||
} | ||
} | ||
// they are exported from ssrTransform plugin, but we can't import from there for performance reasons | ||
const ssrModuleExportsKey = `__vite_ssr_exports__`; | ||
const ssrImportKey = `__vite_ssr_import__`; | ||
const ssrDynamicImportKey = `__vite_ssr_dynamic_import__`; | ||
const ssrExportAllKey = `__vite_ssr_exportAll__`; | ||
const ssrImportMetaKey = `__vite_ssr_import_meta__`; | ||
const noop = () => { }; | ||
const silentConsole = { | ||
debug: noop, | ||
error: noop, | ||
const ssrModuleExportsKey = "__vite_ssr_exports__", ssrImportKey = "__vite_ssr_import__", ssrDynamicImportKey = "__vite_ssr_dynamic_import__", ssrExportAllKey = "__vite_ssr_exportAll__", ssrImportMetaKey = "__vite_ssr_import_meta__", noop = () => { | ||
}, silentConsole = { | ||
debug: noop, | ||
error: noop | ||
}; | ||
// updates to HMR should go one after another. It is possible to trigger another update during the invalidation for example. | ||
function createHMRHandler(runtime) { | ||
const queue = new Queue(); | ||
return (payload) => queue.enqueue(() => handleHMRPayload(runtime, payload)); | ||
const queue = new Queue(); | ||
return (payload) => queue.enqueue(() => handleHMRPayload(runtime, payload)); | ||
} | ||
async function handleHMRPayload(runtime, payload) { | ||
const hmrClient = runtime.hmrClient; | ||
if (!hmrClient || runtime.isDestroyed()) | ||
return; | ||
const hmrClient = runtime.hmrClient; | ||
if (!(!hmrClient || runtime.isDestroyed())) | ||
switch (payload.type) { | ||
case 'connected': | ||
hmrClient.logger.debug(`[vite] connected.`); | ||
hmrClient.messenger.flush(); | ||
break; | ||
case 'update': | ||
await hmrClient.notifyListeners('vite:beforeUpdate', payload); | ||
await Promise.all(payload.updates.map(async (update) => { | ||
if (update.type === 'js-update') { | ||
// runtime always caches modules by their full path without /@id/ prefix | ||
update.acceptedPath = unwrapId(update.acceptedPath); | ||
update.path = unwrapId(update.path); | ||
return hmrClient.queueUpdate(update); | ||
} | ||
hmrClient.logger.error('[vite] css hmr is not supported in runtime mode.'); | ||
})); | ||
await hmrClient.notifyListeners('vite:afterUpdate', payload); | ||
break; | ||
case 'custom': { | ||
await hmrClient.notifyListeners(payload.event, payload.data); | ||
break; | ||
} | ||
case 'full-reload': | ||
hmrClient.logger.debug(`[vite] program reload`); | ||
await hmrClient.notifyListeners('vite:beforeFullReload', payload); | ||
Array.from(runtime.moduleCache.keys()).forEach((id) => { | ||
if (!id.includes('node_modules')) { | ||
runtime.moduleCache.deleteByModuleId(id); | ||
} | ||
}); | ||
for (const id of runtime.entrypoints) { | ||
await runtime.executeUrl(id); | ||
} | ||
break; | ||
case 'prune': | ||
await hmrClient.notifyListeners('vite:beforePrune', payload); | ||
hmrClient.prunePaths(payload.paths); | ||
break; | ||
case 'error': { | ||
await hmrClient.notifyListeners('vite:error', payload); | ||
const err = payload.err; | ||
hmrClient.logger.error(`[vite] Internal Server Error\n${err.message}\n${err.stack}`); | ||
break; | ||
} | ||
default: { | ||
const check = payload; | ||
return check; | ||
} | ||
case "connected": | ||
hmrClient.logger.debug("[vite] connected."), hmrClient.messenger.flush(); | ||
break; | ||
case "update": | ||
await hmrClient.notifyListeners("vite:beforeUpdate", payload), await Promise.all(payload.updates.map(async (update) => { | ||
if (update.type === "js-update") | ||
return update.acceptedPath = unwrapId(update.acceptedPath), update.path = unwrapId(update.path), hmrClient.queueUpdate(update); | ||
hmrClient.logger.error("[vite] css hmr is not supported in runtime mode."); | ||
})), await hmrClient.notifyListeners("vite:afterUpdate", payload); | ||
break; | ||
case "custom": { | ||
await hmrClient.notifyListeners(payload.event, payload.data); | ||
break; | ||
} | ||
case "full-reload": { | ||
const { triggeredBy } = payload, clearEntrypoints = triggeredBy ? [...runtime.entrypoints].filter((entrypoint) => runtime.moduleCache.isImported({ | ||
importedId: triggeredBy, | ||
importedBy: entrypoint | ||
})) : [...runtime.entrypoints]; | ||
if (!clearEntrypoints.length) | ||
break; | ||
hmrClient.logger.debug("[vite] program reload"), await hmrClient.notifyListeners("vite:beforeFullReload", payload), runtime.moduleCache.clear(); | ||
for (const id of clearEntrypoints) | ||
await runtime.executeUrl(id); | ||
break; | ||
} | ||
case "prune": | ||
await hmrClient.notifyListeners("vite:beforePrune", payload), hmrClient.prunePaths(payload.paths); | ||
break; | ||
case "error": { | ||
await hmrClient.notifyListeners("vite:error", payload); | ||
const err = payload.err; | ||
hmrClient.logger.error(`[vite] Internal Server Error | ||
${err.message} | ||
${err.stack}`); | ||
break; | ||
} | ||
default: | ||
return payload; | ||
} | ||
} | ||
class Queue { | ||
queue = []; | ||
pending = false; | ||
enqueue(promise) { | ||
return new Promise((resolve, reject) => { | ||
this.queue.push({ | ||
promise, | ||
resolve, | ||
reject, | ||
}); | ||
this.dequeue(); | ||
}); | ||
} | ||
dequeue() { | ||
if (this.pending) { | ||
return false; | ||
} | ||
const item = this.queue.shift(); | ||
if (!item) { | ||
return false; | ||
} | ||
this.pending = true; | ||
item | ||
.promise() | ||
.then(item.resolve) | ||
.catch(item.reject) | ||
.finally(() => { | ||
this.pending = false; | ||
this.dequeue(); | ||
}); | ||
return true; | ||
} | ||
queue = []; | ||
pending = !1; | ||
enqueue(promise) { | ||
return new Promise((resolve2, reject) => { | ||
this.queue.push({ | ||
promise, | ||
resolve: resolve2, | ||
reject | ||
}), this.dequeue(); | ||
}); | ||
} | ||
dequeue() { | ||
if (this.pending) | ||
return !1; | ||
const item = this.queue.shift(); | ||
return item ? (this.pending = !0, item.promise().then(item.resolve).catch(item.reject).finally(() => { | ||
this.pending = !1, this.dequeue(); | ||
}), !0) : !1; | ||
} | ||
} | ||
const sourceMapCache = {}; | ||
const fileContentsCache = {}; | ||
const moduleGraphs = new Set(); | ||
const retrieveFileHandlers = new Set(); | ||
const retrieveSourceMapHandlers = new Set(); | ||
const createExecHandlers = (handlers) => { | ||
return ((...args) => { | ||
for (const handler of handlers) { | ||
const result = handler(...args); | ||
if (result) | ||
return result; | ||
} | ||
return null; | ||
}); | ||
}; | ||
const retrieveFileFromHandlers = createExecHandlers(retrieveFileHandlers); | ||
const retrievSourceMapFromHandlers = createExecHandlers(retrieveSourceMapHandlers); | ||
let overriden = false; | ||
const sourceMapCache = {}, fileContentsCache = {}, moduleGraphs = /* @__PURE__ */ new Set(), retrieveFileHandlers = /* @__PURE__ */ new Set(), retrieveSourceMapHandlers = /* @__PURE__ */ new Set(), createExecHandlers = (handlers) => (...args) => { | ||
for (const handler of handlers) { | ||
const result = handler(...args); | ||
if (result) | ||
return result; | ||
} | ||
return null; | ||
}, retrieveFileFromHandlers = createExecHandlers(retrieveFileHandlers), retrievSourceMapFromHandlers = createExecHandlers(retrieveSourceMapHandlers); | ||
let overriden = !1; | ||
const originalPrepare = Error.prepareStackTrace; | ||
function resetInterceptor(runtime, options) { | ||
moduleGraphs.delete(runtime.moduleCache); | ||
if (options.retrieveFile) | ||
retrieveFileHandlers.delete(options.retrieveFile); | ||
if (options.retrieveSourceMap) | ||
retrieveSourceMapHandlers.delete(options.retrieveSourceMap); | ||
if (moduleGraphs.size === 0) { | ||
Error.prepareStackTrace = originalPrepare; | ||
overriden = false; | ||
} | ||
moduleGraphs.delete(runtime.moduleCache), options.retrieveFile && retrieveFileHandlers.delete(options.retrieveFile), options.retrieveSourceMap && retrieveSourceMapHandlers.delete(options.retrieveSourceMap), moduleGraphs.size === 0 && (Error.prepareStackTrace = originalPrepare, overriden = !1); | ||
} | ||
function interceptStackTrace(runtime, options = {}) { | ||
if (!overriden) { | ||
Error.prepareStackTrace = prepareStackTrace; | ||
overriden = true; | ||
} | ||
moduleGraphs.add(runtime.moduleCache); | ||
if (options.retrieveFile) | ||
retrieveFileHandlers.add(options.retrieveFile); | ||
if (options.retrieveSourceMap) | ||
retrieveSourceMapHandlers.add(options.retrieveSourceMap); | ||
return () => resetInterceptor(runtime, options); | ||
return overriden || (Error.prepareStackTrace = prepareStackTrace, overriden = !0), moduleGraphs.add(runtime.moduleCache), options.retrieveFile && retrieveFileHandlers.add(options.retrieveFile), options.retrieveSourceMap && retrieveSourceMapHandlers.add(options.retrieveSourceMap), () => resetInterceptor(runtime, options); | ||
} | ||
// Support URLs relative to a directory, but be careful about a protocol prefix | ||
function supportRelativeURL(file, url) { | ||
if (!file) | ||
return url; | ||
const dir = posixDirname(file.replace(/\\/g, '/')); | ||
const match = /^\w+:\/\/[^/]*/.exec(dir); | ||
let protocol = match ? match[0] : ''; | ||
const startPath = dir.slice(protocol.length); | ||
if (protocol && /^\/\w:/.test(startPath)) { | ||
// handle file:///C:/ paths | ||
protocol += '/'; | ||
return (protocol + | ||
posixResolve(dir.slice(protocol.length), url).replace(/\\/g, '/')); | ||
} | ||
return protocol + posixResolve(dir.slice(protocol.length), url); | ||
if (!file) | ||
return url; | ||
const dir = posixDirname(file.replace(/\\/g, "/")), match = /^\w+:\/\/[^/]*/.exec(dir); | ||
let protocol = match ? match[0] : ""; | ||
const startPath = dir.slice(protocol.length); | ||
return protocol && /^\/\w:/.test(startPath) ? (protocol += "/", protocol + posixResolve(dir.slice(protocol.length), url).replace(/\\/g, "/")) : protocol + posixResolve(dir.slice(protocol.length), url); | ||
} | ||
function getRuntimeSourceMap(position) { | ||
for (const moduleCache of moduleGraphs) { | ||
const sourceMap = moduleCache.getSourceMap(position.source); | ||
if (sourceMap) { | ||
return { | ||
url: position.source, | ||
map: sourceMap, | ||
vite: true, | ||
}; | ||
} | ||
} | ||
return null; | ||
for (const moduleCache of moduleGraphs) { | ||
const sourceMap = moduleCache.getSourceMap(position.source); | ||
if (sourceMap) | ||
return { | ||
url: position.source, | ||
map: sourceMap, | ||
vite: !0 | ||
}; | ||
} | ||
return null; | ||
} | ||
function retrieveFile(path) { | ||
if (path in fileContentsCache) | ||
return fileContentsCache[path]; | ||
const content = retrieveFileFromHandlers(path); | ||
if (typeof content === 'string') { | ||
fileContentsCache[path] = content; | ||
return content; | ||
} | ||
return null; | ||
if (path in fileContentsCache) | ||
return fileContentsCache[path]; | ||
const content = retrieveFileFromHandlers(path); | ||
return typeof content == "string" ? (fileContentsCache[path] = content, content) : null; | ||
} | ||
function retrieveSourceMapURL(source) { | ||
// Get the URL of the source map | ||
const fileData = retrieveFile(source); | ||
if (!fileData) | ||
return null; | ||
const re = /\/\/[@#]\s*sourceMappingURL=([^\s'"]+)\s*$|\/\*[@#]\s*sourceMappingURL=[^\s*'"]+\s*\*\/\s*$/gm; | ||
// Keep executing the search to find the *last* sourceMappingURL to avoid | ||
// picking up sourceMappingURLs from comments, strings, etc. | ||
let lastMatch, match; | ||
while ((match = re.exec(fileData))) | ||
lastMatch = match; | ||
if (!lastMatch) | ||
return null; | ||
return lastMatch[1]; | ||
const fileData = retrieveFile(source); | ||
if (!fileData) | ||
return null; | ||
const re = /\/\/[@#]\s*sourceMappingURL=([^\s'"]+)\s*$|\/\*[@#]\s*sourceMappingURL=[^\s*'"]+\s*\*\/\s*$/gm; | ||
let lastMatch, match; | ||
for (; match = re.exec(fileData); ) | ||
lastMatch = match; | ||
return lastMatch ? lastMatch[1] : null; | ||
} | ||
const reSourceMap = /^data:application\/json[^,]+base64,/; | ||
function retrieveSourceMap(source) { | ||
const urlAndMap = retrievSourceMapFromHandlers(source); | ||
if (urlAndMap) | ||
return urlAndMap; | ||
let sourceMappingURL = retrieveSourceMapURL(source); | ||
if (!sourceMappingURL) | ||
return null; | ||
// Read the contents of the source map | ||
let sourceMapData; | ||
if (reSourceMap.test(sourceMappingURL)) { | ||
// Support source map URL as a data url | ||
const rawData = sourceMappingURL.slice(sourceMappingURL.indexOf(',') + 1); | ||
sourceMapData = Buffer.from(rawData, 'base64').toString(); | ||
sourceMappingURL = source; | ||
} | ||
else { | ||
// Support source map URLs relative to the source URL | ||
sourceMappingURL = supportRelativeURL(source, sourceMappingURL); | ||
sourceMapData = retrieveFile(sourceMappingURL); | ||
} | ||
if (!sourceMapData) | ||
return null; | ||
return { | ||
url: sourceMappingURL, | ||
map: sourceMapData, | ||
}; | ||
const urlAndMap = retrievSourceMapFromHandlers(source); | ||
if (urlAndMap) | ||
return urlAndMap; | ||
let sourceMappingURL = retrieveSourceMapURL(source); | ||
if (!sourceMappingURL) | ||
return null; | ||
let sourceMapData; | ||
if (reSourceMap.test(sourceMappingURL)) { | ||
const rawData = sourceMappingURL.slice(sourceMappingURL.indexOf(",") + 1); | ||
sourceMapData = Buffer.from(rawData, "base64").toString(), sourceMappingURL = source; | ||
} else | ||
sourceMappingURL = supportRelativeURL(source, sourceMappingURL), sourceMapData = retrieveFile(sourceMappingURL); | ||
return sourceMapData ? { | ||
url: sourceMappingURL, | ||
map: sourceMapData | ||
} : null; | ||
} | ||
function mapSourcePosition(position) { | ||
if (!position.source) | ||
return position; | ||
let sourceMap = getRuntimeSourceMap(position); | ||
if (!sourceMap) | ||
sourceMap = sourceMapCache[position.source]; | ||
if (!sourceMap) { | ||
// Call the (overrideable) retrieveSourceMap function to get the source map. | ||
const urlAndMap = retrieveSourceMap(position.source); | ||
if (urlAndMap && urlAndMap.map) { | ||
const url = urlAndMap.url; | ||
sourceMap = sourceMapCache[position.source] = { | ||
url, | ||
map: new DecodedMap(typeof urlAndMap.map === 'string' | ||
? JSON.parse(urlAndMap.map) | ||
: urlAndMap.map, url), | ||
}; | ||
const contents = sourceMap.map?.map.sourcesContent; | ||
// Load all sources stored inline with the source map into the file cache | ||
// to pretend like they are already loaded. They may not exist on disk. | ||
if (sourceMap.map && contents) { | ||
sourceMap.map.resolvedSources.forEach((source, i) => { | ||
const content = contents[i]; | ||
if (content && source && url) { | ||
const contentUrl = supportRelativeURL(url, source); | ||
fileContentsCache[contentUrl] = content; | ||
} | ||
}); | ||
} | ||
if (!position.source) | ||
return position; | ||
let sourceMap = getRuntimeSourceMap(position); | ||
if (sourceMap || (sourceMap = sourceMapCache[position.source]), !sourceMap) { | ||
const urlAndMap = retrieveSourceMap(position.source); | ||
if (urlAndMap && urlAndMap.map) { | ||
const url = urlAndMap.url; | ||
sourceMap = sourceMapCache[position.source] = { | ||
url, | ||
map: new DecodedMap(typeof urlAndMap.map == "string" ? JSON.parse(urlAndMap.map) : urlAndMap.map, url) | ||
}; | ||
const contents = sourceMap.map?.map.sourcesContent; | ||
sourceMap.map && contents && sourceMap.map.resolvedSources.forEach((source, i) => { | ||
const content = contents[i]; | ||
if (content && source && url) { | ||
const contentUrl = supportRelativeURL(url, source); | ||
fileContentsCache[contentUrl] = content; | ||
} | ||
else { | ||
sourceMap = sourceMapCache[position.source] = { | ||
url: null, | ||
map: null, | ||
}; | ||
} | ||
} | ||
// Resolve the source URL relative to the URL of the source map | ||
if (sourceMap && sourceMap.map && sourceMap.url) { | ||
const originalPosition = getOriginalPosition(sourceMap.map, position); | ||
// Only return the original position if a matching line was found. If no | ||
// matching line is found then we return position instead, which will cause | ||
// the stack trace to print the path and line for the compiled file. It is | ||
// better to give a precise location in the compiled file than a vague | ||
// location in the original file. | ||
if (originalPosition && originalPosition.source != null) { | ||
originalPosition.source = supportRelativeURL(sourceMap.url, originalPosition.source); | ||
if (sourceMap.vite) { | ||
// @ts-expect-error vite is not defined | ||
originalPosition._vite = true; | ||
} | ||
return originalPosition; | ||
} | ||
} | ||
return position; | ||
}); | ||
} else | ||
sourceMap = sourceMapCache[position.source] = { | ||
url: null, | ||
map: null | ||
}; | ||
} | ||
if (sourceMap && sourceMap.map && sourceMap.url) { | ||
const originalPosition = getOriginalPosition(sourceMap.map, position); | ||
if (originalPosition && originalPosition.source != null) | ||
return originalPosition.source = supportRelativeURL(sourceMap.url, originalPosition.source), sourceMap.vite && (originalPosition._vite = !0), originalPosition; | ||
} | ||
return position; | ||
} | ||
// Parses code generated by FormatEvalOrigin(), a function inside V8: | ||
// https://code.google.com/p/v8/source/browse/trunk/src/messages.js | ||
function mapEvalOrigin(origin) { | ||
// Most eval() calls are in this format | ||
let match = /^eval at ([^(]+) \((.+):(\d+):(\d+)\)$/.exec(origin); | ||
if (match) { | ||
const position = mapSourcePosition({ | ||
name: null, | ||
source: match[2], | ||
line: +match[3], | ||
column: +match[4] - 1, | ||
}); | ||
return `eval at ${match[1]} (${position.source}:${position.line}:${position.column + 1})`; | ||
} | ||
// Parse nested eval() calls using recursion | ||
match = /^eval at ([^(]+) \((.+)\)$/.exec(origin); | ||
if (match) | ||
return `eval at ${match[1]} (${mapEvalOrigin(match[2])})`; | ||
// Make sure we still return useful information if we didn't find anything | ||
return origin; | ||
let match = /^eval at ([^(]+) \((.+):(\d+):(\d+)\)$/.exec(origin); | ||
if (match) { | ||
const position = mapSourcePosition({ | ||
name: null, | ||
source: match[2], | ||
line: +match[3], | ||
column: +match[4] - 1 | ||
}); | ||
return `eval at ${match[1]} (${position.source}:${position.line}:${position.column + 1})`; | ||
} | ||
return match = /^eval at ([^(]+) \((.+)\)$/.exec(origin), match ? `eval at ${match[1]} (${mapEvalOrigin(match[2])})` : origin; | ||
} | ||
// This is copied almost verbatim from the V8 source code at | ||
// https://code.google.com/p/v8/source/browse/trunk/src/messages.js. The | ||
// implementation of wrapCallSite() used to just forward to the actual source | ||
// code of CallSite.prototype.toString but unfortunately a new release of V8 | ||
// did something to the prototype chain and broke the shim. The only fix I | ||
// could find was copy/paste. | ||
function CallSiteToString() { | ||
let fileName; | ||
let fileLocation = ''; | ||
if (this.isNative()) { | ||
fileLocation = 'native'; | ||
let fileName, fileLocation = ""; | ||
if (this.isNative()) | ||
fileLocation = "native"; | ||
else { | ||
fileName = this.getScriptNameOrSourceURL(), !fileName && this.isEval() && (fileLocation = this.getEvalOrigin(), fileLocation += ", "), fileName ? fileLocation += fileName : fileLocation += "<anonymous>"; | ||
const lineNumber = this.getLineNumber(); | ||
if (lineNumber != null) { | ||
fileLocation += `:${lineNumber}`; | ||
const columnNumber = this.getColumnNumber(); | ||
columnNumber && (fileLocation += `:${columnNumber}`); | ||
} | ||
else { | ||
fileName = this.getScriptNameOrSourceURL(); | ||
if (!fileName && this.isEval()) { | ||
fileLocation = this.getEvalOrigin(); | ||
fileLocation += ', '; // Expecting source position to follow. | ||
} | ||
if (fileName) { | ||
fileLocation += fileName; | ||
} | ||
else { | ||
// Source code does not originate from a file and is not native, but we | ||
// can still get the source position inside the source string, e.g. in | ||
// an eval string. | ||
fileLocation += '<anonymous>'; | ||
} | ||
const lineNumber = this.getLineNumber(); | ||
if (lineNumber != null) { | ||
fileLocation += `:${lineNumber}`; | ||
const columnNumber = this.getColumnNumber(); | ||
if (columnNumber) | ||
fileLocation += `:${columnNumber}`; | ||
} | ||
} | ||
let line = ''; | ||
const functionName = this.getFunctionName(); | ||
let addSuffix = true; | ||
const isConstructor = this.isConstructor(); | ||
const isMethodCall = !(this.isToplevel() || isConstructor); | ||
if (isMethodCall) { | ||
let typeName = this.getTypeName(); | ||
// Fixes shim to be backward compatable with Node v0 to v4 | ||
if (typeName === '[object Object]') | ||
typeName = 'null'; | ||
const methodName = this.getMethodName(); | ||
if (functionName) { | ||
if (typeName && functionName.indexOf(typeName) !== 0) | ||
line += `${typeName}.`; | ||
line += functionName; | ||
if (methodName && | ||
functionName.indexOf(`.${methodName}`) !== | ||
functionName.length - methodName.length - 1) | ||
line += ` [as ${methodName}]`; | ||
} | ||
else { | ||
line += `${typeName}.${methodName || '<anonymous>'}`; | ||
} | ||
} | ||
else if (isConstructor) { | ||
line += `new ${functionName || '<anonymous>'}`; | ||
} | ||
else if (functionName) { | ||
line += functionName; | ||
} | ||
else { | ||
line += fileLocation; | ||
addSuffix = false; | ||
} | ||
if (addSuffix) | ||
line += ` (${fileLocation})`; | ||
return line; | ||
} | ||
let line = ""; | ||
const functionName = this.getFunctionName(); | ||
let addSuffix = !0; | ||
const isConstructor = this.isConstructor(); | ||
if (!(this.isToplevel() || isConstructor)) { | ||
let typeName = this.getTypeName(); | ||
typeName === "[object Object]" && (typeName = "null"); | ||
const methodName = this.getMethodName(); | ||
functionName ? (typeName && functionName.indexOf(typeName) !== 0 && (line += `${typeName}.`), line += functionName, methodName && functionName.indexOf(`.${methodName}`) !== functionName.length - methodName.length - 1 && (line += ` [as ${methodName}]`)) : line += `${typeName}.${methodName || "<anonymous>"}`; | ||
} else | ||
isConstructor ? line += `new ${functionName || "<anonymous>"}` : functionName ? line += functionName : (line += fileLocation, addSuffix = !1); | ||
return addSuffix && (line += ` (${fileLocation})`), line; | ||
} | ||
function cloneCallSite(frame) { | ||
const object = {}; | ||
Object.getOwnPropertyNames(Object.getPrototypeOf(frame)).forEach((name) => { | ||
const key = name; | ||
// @ts-expect-error difficult to type | ||
object[key] = /^(?:is|get)/.test(name) | ||
? function () { | ||
return frame[key].call(frame); | ||
} | ||
: frame[key]; | ||
}); | ||
object.toString = CallSiteToString; | ||
return object; | ||
const object = {}; | ||
return Object.getOwnPropertyNames(Object.getPrototypeOf(frame)).forEach((name) => { | ||
const key = name; | ||
object[key] = /^(?:is|get)/.test(name) ? function() { | ||
return frame[key].call(frame); | ||
} : frame[key]; | ||
}), object.toString = CallSiteToString, object; | ||
} | ||
function wrapCallSite(frame, state) { | ||
// provides interface backward compatibility | ||
if (state === undefined) | ||
state = { nextPosition: null, curPosition: null }; | ||
if (frame.isNative()) { | ||
state.curPosition = null; | ||
return frame; | ||
} | ||
// Most call sites will return the source file from getFileName(), but code | ||
// passed to eval() ending in "//# sourceURL=..." will return the source file | ||
// from getScriptNameOrSourceURL() instead | ||
const source = frame.getFileName() || frame.getScriptNameOrSourceURL(); | ||
if (source) { | ||
const line = frame.getLineNumber(); | ||
let column = frame.getColumnNumber() - 1; | ||
// Fix position in Node where some (internal) code is prepended. | ||
// See https://github.com/evanw/node-source-map-support/issues/36 | ||
// Header removed in node at ^10.16 || >=11.11.0 | ||
// v11 is not an LTS candidate, we can just test the one version with it. | ||
// Test node versions for: 10.16-19, 10.20+, 12-19, 20-99, 100+, or 11.11 | ||
const headerLength = 62; | ||
if (line === 1 && column > headerLength && !frame.isEval()) | ||
column -= headerLength; | ||
const position = mapSourcePosition({ | ||
name: null, | ||
source, | ||
line, | ||
column, | ||
}); | ||
state.curPosition = position; | ||
frame = cloneCallSite(frame); | ||
const originalFunctionName = frame.getFunctionName; | ||
frame.getFunctionName = function () { | ||
const name = (() => { | ||
if (state.nextPosition == null) | ||
return originalFunctionName(); | ||
return state.nextPosition.name || originalFunctionName(); | ||
})(); | ||
return name === 'eval' && '_vite' in position ? null : name; | ||
}; | ||
frame.getFileName = function () { | ||
return position.source ?? undefined; | ||
}; | ||
frame.getLineNumber = function () { | ||
return position.line; | ||
}; | ||
frame.getColumnNumber = function () { | ||
return position.column + 1; | ||
}; | ||
frame.getScriptNameOrSourceURL = function () { | ||
return position.source; | ||
}; | ||
return frame; | ||
} | ||
// Code called using eval() needs special handling | ||
let origin = frame.isEval() && frame.getEvalOrigin(); | ||
if (origin) { | ||
origin = mapEvalOrigin(origin); | ||
frame = cloneCallSite(frame); | ||
frame.getEvalOrigin = function () { | ||
return origin || undefined; | ||
}; | ||
return frame; | ||
} | ||
// If we get here then we were unable to change the source position | ||
return frame; | ||
if (state === void 0 && (state = { nextPosition: null, curPosition: null }), frame.isNative()) | ||
return state.curPosition = null, frame; | ||
const source = frame.getFileName() || frame.getScriptNameOrSourceURL(); | ||
if (source) { | ||
const line = frame.getLineNumber(); | ||
let column = frame.getColumnNumber() - 1; | ||
const headerLength = 62; | ||
line === 1 && column > headerLength && !frame.isEval() && (column -= headerLength); | ||
const position = mapSourcePosition({ | ||
name: null, | ||
source, | ||
line, | ||
column | ||
}); | ||
state.curPosition = position, frame = cloneCallSite(frame); | ||
const originalFunctionName = frame.getFunctionName; | ||
return frame.getFunctionName = function() { | ||
const name = (() => state.nextPosition == null ? originalFunctionName() : state.nextPosition.name || originalFunctionName())(); | ||
return name === "eval" && "_vite" in position ? null : name; | ||
}, frame.getFileName = function() { | ||
return position.source ?? void 0; | ||
}, frame.getLineNumber = function() { | ||
return position.line; | ||
}, frame.getColumnNumber = function() { | ||
return position.column + 1; | ||
}, frame.getScriptNameOrSourceURL = function() { | ||
return position.source; | ||
}, frame; | ||
} | ||
let origin = frame.isEval() && frame.getEvalOrigin(); | ||
return origin && (origin = mapEvalOrigin(origin), frame = cloneCallSite(frame), frame.getEvalOrigin = function() { | ||
return origin || void 0; | ||
}), frame; | ||
} | ||
function prepareStackTrace(error, stack) { | ||
const name = error.name || 'Error'; | ||
const message = error.message || ''; | ||
const errorString = `${name}: ${message}`; | ||
const state = { nextPosition: null, curPosition: null }; | ||
const processedStack = []; | ||
for (let i = stack.length - 1; i >= 0; i--) { | ||
processedStack.push(`\n at ${wrapCallSite(stack[i], state)}`); | ||
state.nextPosition = state.curPosition; | ||
} | ||
state.curPosition = state.nextPosition = null; | ||
return errorString + processedStack.reverse().join(''); | ||
const name = error.name || "Error", message = error.message || "", errorString = `${name}: ${message}`, state = { nextPosition: null, curPosition: null }, processedStack = []; | ||
for (let i = stack.length - 1; i >= 0; i--) | ||
processedStack.push(` | ||
at ${wrapCallSite(stack[i], state)}`), state.nextPosition = state.curPosition; | ||
return state.curPosition = state.nextPosition = null, errorString + processedStack.reverse().join(""); | ||
} | ||
function enableSourceMapSupport(runtime) { | ||
if (runtime.options.sourcemapInterceptor === 'node') { | ||
if (typeof process === 'undefined') { | ||
throw new TypeError(`Cannot use "sourcemapInterceptor: 'node'" because global "process" variable is not available.`); | ||
} | ||
if (typeof process.setSourceMapsEnabled !== 'function') { | ||
throw new TypeError(`Cannot use "sourcemapInterceptor: 'node'" because "process.setSourceMapsEnabled" function is not available. Please use Node >= 16.6.0.`); | ||
} | ||
const isEnabledAlready = process.sourceMapsEnabled ?? false; | ||
process.setSourceMapsEnabled(true); | ||
return () => !isEnabledAlready && process.setSourceMapsEnabled(false); | ||
} | ||
return interceptStackTrace(runtime, typeof runtime.options.sourcemapInterceptor === 'object' | ||
? runtime.options.sourcemapInterceptor | ||
: undefined); | ||
if (runtime.options.sourcemapInterceptor === "node") { | ||
if (typeof process > "u") | ||
throw new TypeError(`Cannot use "sourcemapInterceptor: 'node'" because global "process" variable is not available.`); | ||
if (typeof process.setSourceMapsEnabled != "function") | ||
throw new TypeError(`Cannot use "sourcemapInterceptor: 'node'" because "process.setSourceMapsEnabled" function is not available. Please use Node >= 16.6.0.`); | ||
const isEnabledAlready = process.sourceMapsEnabled ?? !1; | ||
return process.setSourceMapsEnabled(!0), () => !isEnabledAlready && process.setSourceMapsEnabled(!1); | ||
} | ||
return interceptStackTrace(runtime, typeof runtime.options.sourcemapInterceptor == "object" ? runtime.options.sourcemapInterceptor : void 0); | ||
} | ||
class ViteRuntime { | ||
options; | ||
runner; | ||
debug; | ||
/** | ||
* Holds the cache of modules | ||
* Keys of the map are ids | ||
*/ | ||
moduleCache; | ||
hmrClient; | ||
entrypoints = new Set(); | ||
idToUrlMap = new Map(); | ||
fileToIdMap = new Map(); | ||
envProxy = new Proxy({}, { | ||
get(_, p) { | ||
throw new Error(`[vite-runtime] Dynamic access of "import.meta.env" is not supported. Please, use "import.meta.env.${String(p)}" instead.`); | ||
}, | ||
options; | ||
runner; | ||
debug; | ||
/** | ||
* Holds the cache of modules | ||
* Keys of the map are ids | ||
*/ | ||
moduleCache; | ||
hmrClient; | ||
entrypoints = /* @__PURE__ */ new Set(); | ||
idToUrlMap = /* @__PURE__ */ new Map(); | ||
fileToIdMap = /* @__PURE__ */ new Map(); | ||
envProxy = new Proxy({}, { | ||
get(_, p) { | ||
throw new Error(`[vite-runtime] Dynamic access of "import.meta.env" is not supported. Please, use "import.meta.env.${String(p)}" instead.`); | ||
} | ||
}); | ||
_destroyed = !1; | ||
_resetSourceMapSupport; | ||
constructor(options, runner, debug) { | ||
this.options = options, this.runner = runner, this.debug = debug, this.moduleCache = options.moduleCache ?? new ModuleCacheMap(options.root), typeof options.hmr == "object" && (this.hmrClient = new HMRClient(options.hmr.logger === !1 ? silentConsole : options.hmr.logger || console, options.hmr.connection, ({ acceptedPath, ssrInvalidates }) => (this.moduleCache.invalidate(acceptedPath), ssrInvalidates && this.invalidateFiles(ssrInvalidates), this.executeUrl(acceptedPath))), options.hmr.connection.onUpdate(createHMRHandler(this))), options.sourcemapInterceptor !== !1 && (this._resetSourceMapSupport = enableSourceMapSupport(this)); | ||
} | ||
/** | ||
* URL to execute. Accepts file path, server path or id relative to the root. | ||
*/ | ||
async executeUrl(url) { | ||
url = this.normalizeEntryUrl(url); | ||
const fetchedModule = await this.cachedModule(url); | ||
return await this.cachedRequest(url, fetchedModule); | ||
} | ||
/** | ||
* Entrypoint URL to execute. Accepts file path, server path or id relative to the root. | ||
* In the case of a full reload triggered by HMR, this is the module that will be reloaded. | ||
* If this method is called multiple times, all entrypoints will be reloaded one at a time. | ||
*/ | ||
async executeEntrypoint(url) { | ||
url = this.normalizeEntryUrl(url); | ||
const fetchedModule = await this.cachedModule(url); | ||
return await this.cachedRequest(url, fetchedModule, [], { | ||
entrypoint: !0 | ||
}); | ||
_destroyed = false; | ||
_resetSourceMapSupport; | ||
constructor(options, runner, debug) { | ||
this.options = options; | ||
this.runner = runner; | ||
this.debug = debug; | ||
this.moduleCache = options.moduleCache ?? new ModuleCacheMap(options.root); | ||
if (typeof options.hmr === 'object') { | ||
this.hmrClient = new HMRClient(options.hmr.logger === false | ||
? silentConsole | ||
: options.hmr.logger || console, options.hmr.connection, ({ acceptedPath, ssrInvalidates }) => { | ||
this.moduleCache.delete(acceptedPath); | ||
if (ssrInvalidates) { | ||
this.invalidateFiles(ssrInvalidates); | ||
} | ||
return this.executeUrl(acceptedPath); | ||
}); | ||
options.hmr.connection.onUpdate(createHMRHandler(this)); | ||
} | ||
if (options.sourcemapInterceptor !== false) { | ||
this._resetSourceMapSupport = enableSourceMapSupport(this); | ||
} | ||
} | ||
/** | ||
* Clear all caches including HMR listeners. | ||
*/ | ||
clearCache() { | ||
this.moduleCache.clear(), this.idToUrlMap.clear(), this.entrypoints.clear(), this.hmrClient?.clear(); | ||
} | ||
/** | ||
* Clears all caches, removes all HMR listeners, and resets source map support. | ||
* This method doesn't stop the HMR connection. | ||
*/ | ||
async destroy() { | ||
this._resetSourceMapSupport?.(), this.clearCache(), this.hmrClient = void 0, this._destroyed = !0; | ||
} | ||
/** | ||
* Returns `true` if the runtime has been destroyed by calling `destroy()` method. | ||
*/ | ||
isDestroyed() { | ||
return this._destroyed; | ||
} | ||
invalidateFiles(files) { | ||
files.forEach((file) => { | ||
const ids = this.fileToIdMap.get(file); | ||
ids && ids.forEach((id) => this.moduleCache.invalidate(id)); | ||
}); | ||
} | ||
// we don't use moduleCache.normalize because this URL doesn't have to follow the same rules | ||
// this URL is something that user passes down manually, and is later resolved by fetchModule | ||
// moduleCache.normalize is used on resolved "file" property | ||
normalizeEntryUrl(url) { | ||
if (url[0] === ".") | ||
return url; | ||
url.startsWith("file://") && (url = url.slice(isWindows ? 8 : 7)), url = url.replace(/\\/g, "/"); | ||
const _root = this.options.root, root = _root[_root.length - 1] === "/" ? _root : `${_root}/`; | ||
return url.startsWith(root) ? url.slice(root.length - 1) : url[0] === "/" ? url : wrapId(url); | ||
} | ||
processImport(exports, fetchResult, metadata) { | ||
if (!("externalize" in fetchResult)) | ||
return exports; | ||
const { id, type } = fetchResult; | ||
return type !== "module" && type !== "commonjs" ? exports : (analyzeImportedModDifference(exports, id, type, metadata), proxyGuardOnlyEsm(exports, id, metadata)); | ||
} | ||
async cachedRequest(id, fetchedModule, callstack = [], metadata) { | ||
const moduleId = fetchedModule.id; | ||
metadata?.entrypoint && this.entrypoints.add(moduleId); | ||
const mod = this.moduleCache.getByModuleId(moduleId), { imports, importers } = mod, importee = callstack[callstack.length - 1]; | ||
if (importee && importers.add(importee), (callstack.includes(moduleId) || Array.from(imports.values()).some((i) => importers.has(i))) && mod.exports) | ||
return this.processImport(mod.exports, fetchedModule, metadata); | ||
let debugTimer; | ||
this.debug && (debugTimer = setTimeout(() => { | ||
const getStack = () => `stack: | ||
${[...callstack, moduleId].reverse().map((p) => ` - ${p}`).join(` | ||
`)}`; | ||
this.debug(`[vite-runtime] module ${moduleId} takes over 2s to load. | ||
${getStack()}`); | ||
}, 2e3)); | ||
try { | ||
if (mod.promise) | ||
return this.processImport(await mod.promise, fetchedModule, metadata); | ||
const promise = this.directRequest(id, fetchedModule, callstack); | ||
return mod.promise = promise, mod.evaluated = !1, this.processImport(await promise, fetchedModule, metadata); | ||
} finally { | ||
mod.evaluated = !0, debugTimer && clearTimeout(debugTimer); | ||
} | ||
/** | ||
* URL to execute. Accepts file path, server path or id relative to the root. | ||
*/ | ||
async executeUrl(url) { | ||
url = this.normalizeEntryUrl(url); | ||
const fetchedModule = await this.cachedModule(url); | ||
return await this.cachedRequest(url, fetchedModule); | ||
} | ||
async cachedModule(id, importer) { | ||
if (this._destroyed) | ||
throw new Error("[vite] Vite runtime has been destroyed."); | ||
const normalized = this.idToUrlMap.get(id); | ||
if (normalized) { | ||
const mod2 = this.moduleCache.getByModuleId(normalized); | ||
if (mod2.meta) | ||
return mod2.meta; | ||
} | ||
/** | ||
* Entrypoint URL to execute. Accepts file path, server path or id relative to the root. | ||
* In the case of a full reload triggered by HMR, this is the module that will be reloaded. | ||
* If this method is called multiple times, all entrypoints will be reloaded one at a time. | ||
*/ | ||
async executeEntrypoint(url) { | ||
url = this.normalizeEntryUrl(url); | ||
const fetchedModule = await this.cachedModule(url); | ||
return await this.cachedRequest(url, fetchedModule, [], { | ||
entrypoint: true, | ||
}); | ||
this.debug?.("[vite-runtime] fetching", id); | ||
const fetchedModule = id.startsWith("data:") ? { externalize: id, type: "builtin" } : await this.options.fetchModule(id, importer), idQuery = id.split("?")[1], query = idQuery ? `?${idQuery}` : "", file = "file" in fetchedModule ? fetchedModule.file : void 0, fullFile = file ? `${file}${query}` : id, moduleId = this.moduleCache.normalize(fullFile), mod = this.moduleCache.getByModuleId(moduleId); | ||
if (fetchedModule.id = moduleId, mod.meta = fetchedModule, file) { | ||
const fileModules = this.fileToIdMap.get(file) || []; | ||
fileModules.push(moduleId), this.fileToIdMap.set(file, fileModules); | ||
} | ||
/** | ||
* Clear all caches including HMR listeners. | ||
*/ | ||
clearCache() { | ||
this.moduleCache.clear(); | ||
this.idToUrlMap.clear(); | ||
this.entrypoints.clear(); | ||
this.hmrClient?.clear(); | ||
return this.idToUrlMap.set(id, moduleId), this.idToUrlMap.set(unwrapId(id), moduleId), fetchedModule; | ||
} | ||
// override is allowed, consider this a public API | ||
async directRequest(id, fetchResult, _callstack) { | ||
const moduleId = fetchResult.id, callstack = [..._callstack, moduleId], mod = this.moduleCache.getByModuleId(moduleId), request = async (dep, metadata) => { | ||
const fetchedModule = await this.cachedModule(dep, moduleId); | ||
return this.moduleCache.getByModuleId(fetchedModule.id).importers.add(moduleId), mod.imports.add(fetchedModule.id), this.cachedRequest(dep, fetchedModule, callstack, metadata); | ||
}, dynamicRequest = async (dep) => (dep = String(dep), dep[0] === "." && (dep = posixResolve(posixDirname(id), dep)), request(dep, { isDynamicImport: !0 })); | ||
if ("externalize" in fetchResult) { | ||
const { externalize } = fetchResult; | ||
this.debug?.("[vite-runtime] externalizing", externalize); | ||
const exports2 = await this.runner.runExternalModule(externalize); | ||
return mod.exports = exports2, exports2; | ||
} | ||
/** | ||
* Clears all caches, removes all HMR listeners, and resets source map support. | ||
* This method doesn't stop the HMR connection. | ||
*/ | ||
async destroy() { | ||
this._resetSourceMapSupport?.(); | ||
this.clearCache(); | ||
this.hmrClient = undefined; | ||
this._destroyed = true; | ||
const { code, file } = fetchResult; | ||
if (code == null) { | ||
const importer = callstack[callstack.length - 2]; | ||
throw new Error(`[vite-runtime] Failed to load "${id}"${importer ? ` imported from ${importer}` : ""}`); | ||
} | ||
/** | ||
* Returns `true` if the runtime has been destroyed by calling `destroy()` method. | ||
*/ | ||
isDestroyed() { | ||
return this._destroyed; | ||
} | ||
invalidateFiles(files) { | ||
files.forEach((file) => { | ||
const ids = this.fileToIdMap.get(file); | ||
if (ids) { | ||
ids.forEach((id) => this.moduleCache.deleteByModuleId(id)); | ||
} | ||
}); | ||
} | ||
// we don't use moduleCache.normalize because this URL doesn't have to follow the same rules | ||
// this URL is something that user passes down manually, and is later resolved by fetchModule | ||
// moduleCache.normalize is used on resolved "file" property | ||
normalizeEntryUrl(url) { | ||
// expect fetchModule to resolve relative module correctly | ||
if (url[0] === '.') { | ||
return url; | ||
} | ||
// file:///C:/root/id.js -> C:/root/id.js | ||
if (url.startsWith('file://')) { | ||
// 8 is the length of "file:///" | ||
url = url.slice(isWindows ? 8 : 7); | ||
} | ||
url = url.replace(/\\/g, '/'); | ||
const _root = this.options.root; | ||
const root = _root[_root.length - 1] === '/' ? _root : `${_root}/`; | ||
// strip root from the URL because fetchModule prefers a public served url path | ||
// packages/vite/src/node/server/moduleGraph.ts:17 | ||
if (url.startsWith(root)) { | ||
// /root/id.js -> /id.js | ||
// C:/root/id.js -> /id.js | ||
// 1 is to keep the leading slash | ||
return url.slice(root.length - 1); | ||
} | ||
// if it's a server url (starts with a slash), keep it, otherwise assume a virtual module | ||
// /id.js -> /id.js | ||
// virtual:custom -> /@id/virtual:custom | ||
return url[0] === '/' ? url : wrapId(url); | ||
} | ||
processImport(exports, fetchResult, metadata) { | ||
if (!('externalize' in fetchResult)) { | ||
return exports; | ||
} | ||
const { id, type } = fetchResult; | ||
if (type !== 'module' && type !== 'commonjs') | ||
return exports; | ||
analyzeImportedModDifference(exports, id, type, metadata); | ||
return proxyGuardOnlyEsm(exports, id, metadata); | ||
} | ||
async cachedRequest(id, fetchedModule, callstack = [], metadata) { | ||
const moduleId = fetchedModule.id; | ||
if (metadata?.entrypoint) { | ||
this.entrypoints.add(moduleId); | ||
} | ||
const mod = this.moduleCache.getByModuleId(moduleId); | ||
const { imports, importers } = mod; | ||
const importee = callstack[callstack.length - 1]; | ||
if (importee) | ||
importers.add(importee); | ||
// check circular dependency | ||
if (callstack.includes(moduleId) || | ||
Array.from(imports.values()).some((i) => importers.has(i))) { | ||
if (mod.exports) | ||
return this.processImport(mod.exports, fetchedModule, metadata); | ||
} | ||
let debugTimer; | ||
if (this.debug) { | ||
debugTimer = setTimeout(() => { | ||
const getStack = () => `stack:\n${[...callstack, moduleId] | ||
.reverse() | ||
.map((p) => ` - ${p}`) | ||
.join('\n')}`; | ||
this.debug(`[vite-runtime] module ${moduleId} takes over 2s to load.\n${getStack()}`); | ||
}, 2000); | ||
} | ||
try { | ||
// cached module | ||
if (mod.promise) | ||
return this.processImport(await mod.promise, fetchedModule, metadata); | ||
const promise = this.directRequest(id, fetchedModule, callstack); | ||
mod.promise = promise; | ||
mod.evaluated = false; | ||
return this.processImport(await promise, fetchedModule, metadata); | ||
} | ||
finally { | ||
mod.evaluated = true; | ||
if (debugTimer) | ||
clearTimeout(debugTimer); | ||
} | ||
} | ||
async cachedModule(id, importer) { | ||
if (this._destroyed) { | ||
throw new Error(`[vite] Vite runtime has been destroyed.`); | ||
} | ||
const normalized = this.idToUrlMap.get(id); | ||
if (normalized) { | ||
const mod = this.moduleCache.getByModuleId(normalized); | ||
if (mod.meta) { | ||
return mod.meta; | ||
} | ||
} | ||
this.debug?.('[vite-runtime] fetching', id); | ||
// fast return for established externalized patterns | ||
const fetchedModule = id.startsWith('data:') | ||
? ({ externalize: id, type: 'builtin' }) | ||
: await this.options.fetchModule(id, importer); | ||
// base moduleId on "file" and not on id | ||
// if `import(variable)` is called it's possible that it doesn't have an extension for example | ||
// if we used id for that, it's possible to have a duplicated module | ||
const idQuery = id.split('?')[1]; | ||
const query = idQuery ? `?${idQuery}` : ''; | ||
const file = 'file' in fetchedModule ? fetchedModule.file : undefined; | ||
const fullFile = file ? `${file}${query}` : id; | ||
const moduleId = this.moduleCache.normalize(fullFile); | ||
const mod = this.moduleCache.getByModuleId(moduleId); | ||
fetchedModule.id = moduleId; | ||
mod.meta = fetchedModule; | ||
if (file) { | ||
const fileModules = this.fileToIdMap.get(file) || []; | ||
fileModules.push(moduleId); | ||
this.fileToIdMap.set(file, fileModules); | ||
} | ||
this.idToUrlMap.set(id, moduleId); | ||
this.idToUrlMap.set(unwrapId(id), moduleId); | ||
return fetchedModule; | ||
} | ||
// override is allowed, consider this a public API | ||
async directRequest(id, fetchResult, _callstack) { | ||
const moduleId = fetchResult.id; | ||
const callstack = [..._callstack, moduleId]; | ||
const mod = this.moduleCache.getByModuleId(moduleId); | ||
const request = async (dep, metadata) => { | ||
const fetchedModule = await this.cachedModule(dep, moduleId); | ||
const depMod = this.moduleCache.getByModuleId(fetchedModule.id); | ||
depMod.importers.add(moduleId); | ||
mod.imports.add(fetchedModule.id); | ||
return this.cachedRequest(dep, fetchedModule, callstack, metadata); | ||
}; | ||
const dynamicRequest = async (dep) => { | ||
// it's possible to provide an object with toString() method inside import() | ||
dep = String(dep); | ||
if (dep[0] === '.') { | ||
dep = posixResolve(posixDirname(id), dep); | ||
} | ||
return request(dep, { isDynamicImport: true }); | ||
}; | ||
if ('externalize' in fetchResult) { | ||
const { externalize } = fetchResult; | ||
this.debug?.('[vite-runtime] externalizing', externalize); | ||
const exports = await this.runner.runExternalModule(externalize); | ||
mod.exports = exports; | ||
return exports; | ||
} | ||
const { code, file } = fetchResult; | ||
if (code == null) { | ||
const importer = callstack[callstack.length - 2]; | ||
throw new Error(`[vite-runtime] Failed to load "${id}"${importer ? ` imported from ${importer}` : ''}`); | ||
} | ||
const modulePath = cleanUrl(file || moduleId); | ||
// disambiguate the `<UNIT>:/` on windows: see nodejs/node#31710 | ||
const href = posixPathToFileHref(modulePath); | ||
const filename = modulePath; | ||
const dirname = posixDirname(modulePath); | ||
const meta = { | ||
filename: isWindows ? toWindowsPath(filename) : filename, | ||
dirname: isWindows ? toWindowsPath(dirname) : dirname, | ||
url: href, | ||
env: this.envProxy, | ||
resolve(id, parent) { | ||
throw new Error('[vite-runtime] "import.meta.resolve" is not supported.'); | ||
}, | ||
// should be replaced during transformation | ||
glob() { | ||
throw new Error('[vite-runtime] "import.meta.glob" is not supported.'); | ||
}, | ||
}; | ||
const exports = Object.create(null); | ||
Object.defineProperty(exports, Symbol.toStringTag, { | ||
value: 'Module', | ||
enumerable: false, | ||
configurable: false, | ||
}); | ||
mod.exports = exports; | ||
let hotContext; | ||
if (this.hmrClient) { | ||
Object.defineProperty(meta, 'hot', { | ||
enumerable: true, | ||
get: () => { | ||
if (!this.hmrClient) { | ||
throw new Error(`[vite-runtime] HMR client was destroyed.`); | ||
} | ||
this.debug?.('[vite-runtime] creating hmr context for', moduleId); | ||
hotContext ||= new HMRContext(this.hmrClient, moduleId); | ||
return hotContext; | ||
}, | ||
set: (value) => { | ||
hotContext = value; | ||
}, | ||
}); | ||
} | ||
const context = { | ||
[ssrImportKey]: request, | ||
[ssrDynamicImportKey]: dynamicRequest, | ||
[ssrModuleExportsKey]: exports, | ||
[ssrExportAllKey]: (obj) => exportAll(exports, obj), | ||
[ssrImportMetaKey]: meta, | ||
}; | ||
this.debug?.('[vite-runtime] executing', href); | ||
await this.runner.runViteModule(context, code, id); | ||
return exports; | ||
} | ||
const modulePath = cleanUrl(file || moduleId), href = posixPathToFileHref(modulePath), filename = modulePath, dirname2 = posixDirname(modulePath), meta = { | ||
filename: isWindows ? toWindowsPath(filename) : filename, | ||
dirname: isWindows ? toWindowsPath(dirname2) : dirname2, | ||
url: href, | ||
env: this.envProxy, | ||
resolve(id2, parent) { | ||
throw new Error('[vite-runtime] "import.meta.resolve" is not supported.'); | ||
}, | ||
// should be replaced during transformation | ||
glob() { | ||
throw new Error('[vite-runtime] "import.meta.glob" is not supported.'); | ||
} | ||
}, exports = /* @__PURE__ */ Object.create(null); | ||
Object.defineProperty(exports, Symbol.toStringTag, { | ||
value: "Module", | ||
enumerable: !1, | ||
configurable: !1 | ||
}), mod.exports = exports; | ||
let hotContext; | ||
this.hmrClient && Object.defineProperty(meta, "hot", { | ||
enumerable: !0, | ||
get: () => { | ||
if (!this.hmrClient) | ||
throw new Error("[vite-runtime] HMR client was destroyed."); | ||
return this.debug?.("[vite-runtime] creating hmr context for", moduleId), hotContext ||= new HMRContext(this.hmrClient, moduleId), hotContext; | ||
}, | ||
set: (value) => { | ||
hotContext = value; | ||
} | ||
}); | ||
const context = { | ||
[ssrImportKey]: request, | ||
[ssrDynamicImportKey]: dynamicRequest, | ||
[ssrModuleExportsKey]: exports, | ||
[ssrExportAllKey]: (obj) => exportAll(exports, obj), | ||
[ssrImportMetaKey]: meta | ||
}; | ||
return this.debug?.("[vite-runtime] executing", href), await this.runner.runViteModule(context, code, id), exports; | ||
} | ||
} | ||
function exportAll(exports, sourceModule) { | ||
// when a module exports itself it causes | ||
// call stack error | ||
if (exports === sourceModule) | ||
return; | ||
if (isPrimitive(sourceModule) || | ||
Array.isArray(sourceModule) || | ||
sourceModule instanceof Promise) | ||
return; | ||
for (const key in sourceModule) { | ||
if (key !== 'default' && key !== '__esModule') { | ||
try { | ||
Object.defineProperty(exports, key, { | ||
enumerable: true, | ||
configurable: true, | ||
get: () => sourceModule[key], | ||
}); | ||
} | ||
catch (_err) { } | ||
if (exports !== sourceModule && !(isPrimitive(sourceModule) || Array.isArray(sourceModule) || sourceModule instanceof Promise)) { | ||
for (const key in sourceModule) | ||
if (key !== "default" && key !== "__esModule") | ||
try { | ||
Object.defineProperty(exports, key, { | ||
enumerable: !0, | ||
configurable: !0, | ||
get: () => sourceModule[key] | ||
}); | ||
} catch { | ||
} | ||
} | ||
} | ||
} | ||
/** | ||
* Vite converts `import { } from 'foo'` to `const _ = __vite_ssr_import__('foo')`. | ||
* Top-level imports and dynamic imports work slightly differently in Node.js. | ||
* This function normalizes the differences so it matches prod behaviour. | ||
*/ | ||
function analyzeImportedModDifference(mod, rawId, moduleType, metadata) { | ||
// No normalization needed if the user already dynamic imports this module | ||
if (metadata?.isDynamicImport) | ||
return; | ||
// If file path is ESM, everything should be fine | ||
if (moduleType === 'module') | ||
return; | ||
// For non-ESM, named imports is done via static analysis with cjs-module-lexer in Node.js. | ||
// If the user named imports a specifier that can't be analyzed, error. | ||
if (metadata?.importedNames?.length) { | ||
const missingBindings = metadata.importedNames.filter((s) => !(s in mod)); | ||
if (missingBindings.length) { | ||
const lastBinding = missingBindings[missingBindings.length - 1]; | ||
// Copied from Node.js | ||
throw new SyntaxError(`\ | ||
[vite] Named export '${lastBinding}' not found. The requested module '${rawId}' is a CommonJS module, which may not support all module.exports as named exports. | ||
if (!metadata?.isDynamicImport && moduleType !== "module" && metadata?.importedNames?.length) { | ||
const missingBindings = metadata.importedNames.filter((s) => !(s in mod)); | ||
if (missingBindings.length) { | ||
const lastBinding = missingBindings[missingBindings.length - 1]; | ||
throw new SyntaxError(`[vite] Named export '${lastBinding}' not found. The requested module '${rawId}' is a CommonJS module, which may not support all module.exports as named exports. | ||
CommonJS modules can always be imported via the default export, for example using: | ||
import pkg from '${rawId}'; | ||
const {${missingBindings.join(', ')}} = pkg; | ||
const {${missingBindings.join(", ")}} = pkg; | ||
`); | ||
} | ||
} | ||
} | ||
} | ||
/** | ||
* Guard invalid named exports only, similar to how Node.js errors for top-level imports. | ||
* But since we transform as dynamic imports, we need to emulate the error manually. | ||
*/ | ||
function proxyGuardOnlyEsm(mod, rawId, metadata) { | ||
// If the module doesn't import anything explicitly, e.g. `import 'foo'` or | ||
// `import * as foo from 'foo'`, we can skip the proxy guard. | ||
if (!metadata?.importedNames?.length) | ||
return mod; | ||
return new Proxy(mod, { | ||
get(mod, prop) { | ||
if (prop !== 'then' && !(prop in mod)) { | ||
throw new SyntaxError(`[vite] The requested module '${rawId}' does not provide an export named '${prop.toString()}'`); | ||
} | ||
return mod[prop]; | ||
}, | ||
}); | ||
return metadata?.importedNames?.length ? new Proxy(mod, { | ||
get(mod2, prop) { | ||
if (prop !== "then" && !(prop in mod2)) | ||
throw new SyntaxError(`[vite] The requested module '${rawId}' does not provide an export named '${prop.toString()}'`); | ||
return mod2[prop]; | ||
} | ||
}) : mod; | ||
} | ||
// eslint-disable-next-line @typescript-eslint/no-empty-function | ||
const AsyncFunction = async function () { }.constructor; | ||
const AsyncFunction = async function() { | ||
}.constructor; | ||
class ESModulesRunner { | ||
async runViteModule(context, code) { | ||
// use AsyncFunction instead of vm module to support broader array of environments out of the box | ||
const initModule = new AsyncFunction(ssrModuleExportsKey, ssrImportMetaKey, ssrImportKey, ssrDynamicImportKey, ssrExportAllKey, | ||
// source map should already be inlined by Vite | ||
'"use strict";' + code); | ||
await initModule(context[ssrModuleExportsKey], context[ssrImportMetaKey], context[ssrImportKey], context[ssrDynamicImportKey], context[ssrExportAllKey]); | ||
Object.seal(context[ssrModuleExportsKey]); | ||
} | ||
runExternalModule(filepath) { | ||
return import(filepath); | ||
} | ||
async runViteModule(context, code) { | ||
await new AsyncFunction( | ||
ssrModuleExportsKey, | ||
ssrImportMetaKey, | ||
ssrImportKey, | ||
ssrDynamicImportKey, | ||
ssrExportAllKey, | ||
// source map should already be inlined by Vite | ||
'"use strict";' + code | ||
)(context[ssrModuleExportsKey], context[ssrImportMetaKey], context[ssrImportKey], context[ssrDynamicImportKey], context[ssrExportAllKey]), Object.seal(context[ssrModuleExportsKey]); | ||
} | ||
runExternalModule(filepath) { | ||
return import(filepath); | ||
} | ||
} | ||
export { ESModulesRunner, ModuleCacheMap, ViteRuntime, ssrDynamicImportKey, ssrExportAllKey, ssrImportKey, ssrImportMetaKey, ssrModuleExportsKey }; | ||
export { | ||
ESModulesRunner, | ||
ModuleCacheMap, | ||
ViteRuntime, | ||
ssrDynamicImportKey, | ||
ssrExportAllKey, | ||
ssrImportKey, | ||
ssrImportMetaKey, | ||
ssrModuleExportsKey | ||
}; |
{ | ||
"name": "vite", | ||
"version": "5.1.4", | ||
"version": "5.1.5", | ||
"type": "module", | ||
@@ -85,3 +85,3 @@ "license": "MIT", | ||
"@babel/parser": "^7.23.9", | ||
"@jridgewell/trace-mapping": "^0.3.22", | ||
"@jridgewell/trace-mapping": "^0.3.23", | ||
"@rollup/plugin-alias": "^5.1.0", | ||
@@ -107,3 +107,3 @@ "@rollup/plugin-commonjs": "^25.0.7", | ||
"dep-types": "link:./src/types", | ||
"dotenv": "^16.4.4", | ||
"dotenv": "^16.4.5", | ||
"dotenv-expand": "^11.0.6", | ||
@@ -117,9 +117,10 @@ "es-module-lexer": "^1.4.1", | ||
"launch-editor-middleware": "^2.6.1", | ||
"lightningcss": "^1.23.0", | ||
"lightningcss": "^1.24.0", | ||
"magic-string": "^0.30.7", | ||
"micromatch": "^4.0.5", | ||
"mlly": "^1.5.0", | ||
"mlly": "^1.6.1", | ||
"mrmime": "^2.0.0", | ||
"open": "^8.4.2", | ||
"parse5": "^7.1.2", | ||
"pathe": "^1.1.2", | ||
"periscopic": "^4.0.2", | ||
@@ -133,2 +134,3 @@ "picocolors": "^1.0.0", | ||
"rollup-plugin-dts": "^6.1.0", | ||
"rollup-plugin-esbuild": "^6.1.1", | ||
"rollup-plugin-license": "^3.2.0", | ||
@@ -135,0 +137,0 @@ "sirv": "^2.0.4", |
@@ -39,2 +39,4 @@ export type HMRPayload = | ||
path?: string | ||
/** @internal */ | ||
triggeredBy?: string | ||
} | ||
@@ -41,0 +43,0 @@ |
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is too big to display
Major refactor
Supply chain riskPackage has recently undergone a major refactor. It may be unstable or indicate significant internal changes. Use caution when updating to versions that include significant changes.
Found 1 instance in 1 package
Major refactor
Supply chain riskPackage has recently undergone a major refactor. It may be unstable or indicate significant internal changes. Use caution when updating to versions that include significant changes.
Found 1 instance in 1 package
12
3538059
59
90998