From 9356413650f2fd73874cb0e3d0aa048d80397e3b Mon Sep 17 00:00:00 2001 From: Anthony Fu Date: Wed, 13 Dec 2023 13:36:53 +0100 Subject: [PATCH 1/6] feat: log re-optimization reaons --- packages/vite/src/node/optimizer/index.ts | 90 +++++++++++++++-------- 1 file changed, 59 insertions(+), 31 deletions(-) diff --git a/packages/vite/src/node/optimizer/index.ts b/packages/vite/src/node/optimizer/index.ts index 5b6cf3b729a7df..a3656db243811d 100644 --- a/packages/vite/src/node/optimizer/index.ts +++ b/packages/vite/src/node/optimizer/index.ts @@ -191,6 +191,16 @@ export interface DepOptimizationMetadata { * This is checked on server startup to avoid unnecessary re-bundles. */ hash: string + /** + * This hash is determined by dependency lockfiles. + * This is checked on server startup to avoid unnecessary re-bundles. + */ + lockfileHash: string + /** + * This hash is determined by user config. + * This is checked on server startup to avoid unnecessary re-bundles. + */ + configHash: string /** * The browser hash is determined by the main hash plus additional dependencies * discovered at runtime. This is used to invalidate browser requests to @@ -310,9 +320,13 @@ export function initDepsOptimizerMetadata( ssr: boolean, timestamp?: string, ): DepOptimizationMetadata { - const hash = getDepHash(config, ssr) + const lockfileHash = getLockfileHash(config, ssr) + const configHash = getConfigHash(config, ssr) + const hash = lockfileHash + configHash return { hash, + lockfileHash, + configHash, browserHash: getOptimizedBrowserHash(hash, {}, timestamp), optimized: {}, chunks: {}, @@ -363,11 +377,21 @@ export async function loadCachedDepOptimizationMetadata( ) } catch (e) {} // hash is consistent, no need to re-bundle - if (cachedMetadata && cachedMetadata.hash === getDepHash(config, ssr)) { - log?.('Hash is consistent. Skipping. Use --force to override.') - // Nothing to commit or cancel as we are using the cache, we only - // need to resolve the processing promise so requests can move on - return cachedMetadata + if (cachedMetadata) { + if (cachedMetadata.lockfileHash !== getLockfileHash(config, ssr)) { + config.logger.info( + 'Re-optimizing dependencies because lockfile has changed', + ) + } else if (cachedMetadata.configHash !== getConfigHash(config, ssr)) { + config.logger.info( + 'Re-optimizing dependencies because vite config has changed', + ) + } else { + log?.('Hash is consistent. Skipping. Use --force to override.') + // Nothing to commit or cancel as we are using the cache, we only + // need to resolve the processing promise so requests can move on + return cachedMetadata + } } } else { config.logger.info('Forced re-optimization of dependencies') @@ -417,7 +441,7 @@ export function toDiscoveredDependencies( timestamp?: string, ): Record { const browserHash = getOptimizedBrowserHash( - getDepHash(config, ssr), + getLockfileHash(config, ssr), deps, timestamp, ) @@ -975,17 +999,15 @@ function parseDepsOptimizerMetadata( jsonMetadata: string, depsCacheDir: string, ): DepOptimizationMetadata | undefined { - const { hash, browserHash, optimized, chunks } = JSON.parse( - jsonMetadata, - (key: string, value: string) => { + const { hash, lockfileHash, configHash, browserHash, optimized, chunks } = + JSON.parse(jsonMetadata, (key: string, value: string) => { // Paths can be absolute or relative to the deps cache dir where // the _metadata.json is located if (key === 'file' || key === 'src') { return normalizePath(path.resolve(depsCacheDir, value)) } return value - }, - ) + }) if ( !chunks || Object.values(optimized).some((depInfo: any) => !depInfo.fileHash) @@ -995,6 +1017,8 @@ function parseDepsOptimizerMetadata( } const metadata = { hash, + lockfileHash, + configHash, browserHash, optimized: {}, discovered: {}, @@ -1187,27 +1211,11 @@ const lockfileFormats = [ }) const lockfileNames = lockfileFormats.map((l) => l.name) -export function getDepHash(config: ResolvedConfig, ssr: boolean): string { - const lockfilePath = lookupFile(config.root, lockfileNames) - let content = lockfilePath ? fs.readFileSync(lockfilePath, 'utf-8') : '' - if (lockfilePath) { - const lockfileName = path.basename(lockfilePath) - const { checkPatches } = lockfileFormats.find( - (f) => f.name === lockfileName, - )! - if (checkPatches) { - // Default of https://github.com/ds300/patch-package - const fullPath = path.join(path.dirname(lockfilePath), 'patches') - const stat = tryStatSync(fullPath) - if (stat?.isDirectory()) { - content += stat.mtimeMs.toString() - } - } - } - // also take config into account +export function getConfigHash(config: ResolvedConfig, ssr: boolean): string { + // Take config into account // only a subset of config options that can affect dep optimization const optimizeDeps = getDepOptimizationConfig(config, ssr) - content += JSON.stringify( + const content = JSON.stringify( { mode: process.env.NODE_ENV || config.mode, root: config.root, @@ -1238,6 +1246,26 @@ export function getDepHash(config: ResolvedConfig, ssr: boolean): string { return getHash(content) } +export function getLockfileHash(config: ResolvedConfig, ssr: boolean): string { + const lockfilePath = lookupFile(config.root, lockfileNames) + let content = lockfilePath ? fs.readFileSync(lockfilePath, 'utf-8') : '' + if (lockfilePath) { + const lockfileName = path.basename(lockfilePath) + const { checkPatches } = lockfileFormats.find( + (f) => f.name === lockfileName, + )! + if (checkPatches) { + // Default of https://github.com/ds300/patch-package + const fullPath = path.join(path.dirname(lockfilePath), 'patches') + const stat = tryStatSync(fullPath) + if (stat?.isDirectory()) { + content += stat.mtimeMs.toString() + } + } + } + return getHash(content) +} + function getOptimizedBrowserHash( hash: string, deps: Record, From bf7ca9a068b60f6f52822add806e4ed8645ac68a Mon Sep 17 00:00:00 2001 From: Anthony Fu Date: Wed, 13 Dec 2023 13:43:00 +0100 Subject: [PATCH 2/6] chore: update --- packages/vite/src/node/optimizer/index.ts | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/packages/vite/src/node/optimizer/index.ts b/packages/vite/src/node/optimizer/index.ts index a3656db243811d..f161277dee5136 100644 --- a/packages/vite/src/node/optimizer/index.ts +++ b/packages/vite/src/node/optimizer/index.ts @@ -441,7 +441,7 @@ export function toDiscoveredDependencies( timestamp?: string, ): Record { const browserHash = getOptimizedBrowserHash( - getLockfileHash(config, ssr), + getDepHash(config, ssr), deps, timestamp, ) @@ -1266,6 +1266,10 @@ export function getLockfileHash(config: ResolvedConfig, ssr: boolean): string { return getHash(content) } +export function getDepHash(config: ResolvedConfig, ssr: boolean): string { + return getHash(getLockfileHash(config, ssr) + getConfigHash(config, ssr)) +} + function getOptimizedBrowserHash( hash: string, deps: Record, From 17bd5fd5935a3d32aaef030e91413a0c002ac350 Mon Sep 17 00:00:00 2001 From: Anthony Fu Date: Wed, 13 Dec 2023 14:07:31 +0100 Subject: [PATCH 3/6] chore: fix misalignment --- packages/vite/src/node/optimizer/index.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/vite/src/node/optimizer/index.ts b/packages/vite/src/node/optimizer/index.ts index f161277dee5136..c3689a21f2ec00 100644 --- a/packages/vite/src/node/optimizer/index.ts +++ b/packages/vite/src/node/optimizer/index.ts @@ -1267,7 +1267,7 @@ export function getLockfileHash(config: ResolvedConfig, ssr: boolean): string { } export function getDepHash(config: ResolvedConfig, ssr: boolean): string { - return getHash(getLockfileHash(config, ssr) + getConfigHash(config, ssr)) + return getLockfileHash(config, ssr) + getConfigHash(config, ssr) } function getOptimizedBrowserHash( From ae686eb491115fdc3704f6e230d2922fe808731c Mon Sep 17 00:00:00 2001 From: Anthony Fu Date: Wed, 13 Dec 2023 14:42:42 +0100 Subject: [PATCH 4/6] chore: update --- packages/vite/src/node/optimizer/index.ts | 21 ++++++++++++++------- 1 file changed, 14 insertions(+), 7 deletions(-) diff --git a/packages/vite/src/node/optimizer/index.ts b/packages/vite/src/node/optimizer/index.ts index c3689a21f2ec00..9fb54c2f5e959e 100644 --- a/packages/vite/src/node/optimizer/index.ts +++ b/packages/vite/src/node/optimizer/index.ts @@ -320,9 +320,7 @@ export function initDepsOptimizerMetadata( ssr: boolean, timestamp?: string, ): DepOptimizationMetadata { - const lockfileHash = getLockfileHash(config, ssr) - const configHash = getConfigHash(config, ssr) - const hash = lockfileHash + configHash + const { lockfileHash, configHash, hash } = getDepHash(config, ssr) return { hash, lockfileHash, @@ -441,7 +439,7 @@ export function toDiscoveredDependencies( timestamp?: string, ): Record { const browserHash = getOptimizedBrowserHash( - getDepHash(config, ssr), + getDepHash(config, ssr).hash, deps, timestamp, ) @@ -1266,8 +1264,18 @@ export function getLockfileHash(config: ResolvedConfig, ssr: boolean): string { return getHash(content) } -export function getDepHash(config: ResolvedConfig, ssr: boolean): string { - return getLockfileHash(config, ssr) + getConfigHash(config, ssr) +export function getDepHash( + config: ResolvedConfig, + ssr: boolean, +): { lockfileHash: string; configHash: string; hash: string } { + const lockfileHash = getLockfileHash(config, ssr) + const configHash = getConfigHash(config, ssr) + const hash = getHash(lockfileHash + configHash) + return { + hash, + lockfileHash, + configHash, + } } function getOptimizedBrowserHash( @@ -1325,7 +1333,6 @@ export async function optimizedDepNeedsInterop( return depInfo?.needsInterop } -const MAX_TEMP_DIR_AGE_MS = 24 * 60 * 60 * 1000 export async function cleanupDepsCacheStaleDirs( config: ResolvedConfig, ): Promise { From 897fa24052206eebdf88cff1338e2198de70fe85 Mon Sep 17 00:00:00 2001 From: Anthony Fu Date: Wed, 13 Dec 2023 14:45:59 +0100 Subject: [PATCH 5/6] chore: fix path --- packages/vite/src/node/optimizer/index.ts | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-) diff --git a/packages/vite/src/node/optimizer/index.ts b/packages/vite/src/node/optimizer/index.ts index 9fb54c2f5e959e..e62a8122837041 100644 --- a/packages/vite/src/node/optimizer/index.ts +++ b/packages/vite/src/node/optimizer/index.ts @@ -1051,10 +1051,13 @@ function stringifyDepsOptimizerMetadata( metadata: DepOptimizationMetadata, depsCacheDir: string, ) { - const { hash, browserHash, optimized, chunks } = metadata + const { hash, configHash, lockfileHash, browserHash, optimized, chunks } = + metadata return JSON.stringify( { hash, + configHash, + lockfileHash, browserHash, optimized: Object.fromEntries( Object.values(optimized).map( @@ -1209,7 +1212,7 @@ const lockfileFormats = [ }) const lockfileNames = lockfileFormats.map((l) => l.name) -export function getConfigHash(config: ResolvedConfig, ssr: boolean): string { +function getConfigHash(config: ResolvedConfig, ssr: boolean): string { // Take config into account // only a subset of config options that can affect dep optimization const optimizeDeps = getDepOptimizationConfig(config, ssr) @@ -1244,7 +1247,7 @@ export function getConfigHash(config: ResolvedConfig, ssr: boolean): string { return getHash(content) } -export function getLockfileHash(config: ResolvedConfig, ssr: boolean): string { +function getLockfileHash(config: ResolvedConfig, ssr: boolean): string { const lockfilePath = lookupFile(config.root, lockfileNames) let content = lockfilePath ? fs.readFileSync(lockfilePath, 'utf-8') : '' if (lockfilePath) { @@ -1264,7 +1267,7 @@ export function getLockfileHash(config: ResolvedConfig, ssr: boolean): string { return getHash(content) } -export function getDepHash( +function getDepHash( config: ResolvedConfig, ssr: boolean, ): { lockfileHash: string; configHash: string; hash: string } { From 88d7f3b7fa9ce1594cbbba31bcb4741903dac667 Mon Sep 17 00:00:00 2001 From: Anthony Fu Date: Wed, 13 Dec 2023 14:56:50 +0100 Subject: [PATCH 6/6] chore: fix --- packages/vite/src/node/optimizer/index.ts | 1 + 1 file changed, 1 insertion(+) diff --git a/packages/vite/src/node/optimizer/index.ts b/packages/vite/src/node/optimizer/index.ts index e62a8122837041..5a98810777a314 100644 --- a/packages/vite/src/node/optimizer/index.ts +++ b/packages/vite/src/node/optimizer/index.ts @@ -1336,6 +1336,7 @@ export async function optimizedDepNeedsInterop( return depInfo?.needsInterop } +const MAX_TEMP_DIR_AGE_MS = 24 * 60 * 60 * 1000 export async function cleanupDepsCacheStaleDirs( config: ResolvedConfig, ): Promise {