Skip to content

Commit 8b012c7

Browse files
dominikgsapphi-red
authored andcommitted
fix: refactor watch code for tsconfig changes to use watchChange hook
1 parent 87949fe commit 8b012c7

File tree

1 file changed

+38
-36
lines changed

1 file changed

+38
-36
lines changed

packages/vite/src/node/plugins/esbuild.ts

Lines changed: 38 additions & 36 deletions
Original file line numberDiff line numberDiff line change
@@ -251,14 +251,48 @@ export function esbuildPlugin(config: ResolvedConfig): Plugin {
251251
},
252252
}
253253

254+
let server: ViteDevServer
255+
254256
return {
255257
name: 'vite:esbuild',
256258
configureServer(_server) {
257259
server = _server
258-
server.watcher
259-
.on('add', reloadOnTsconfigChange)
260-
.on('change', reloadOnTsconfigChange)
261-
.on('unlink', reloadOnTsconfigChange)
260+
},
261+
watchChange(id) {
262+
// any tsconfig.json that's added in the workspace could be closer to a code file than a previously cached one
263+
// any json file in the tsconfig cache could have been used to compile ts
264+
if (
265+
path.basename(id) === 'tsconfig.json' ||
266+
id.endsWith('.json') /*
267+
TODO: the tsconfckCache?.clear() line will make this fail if there are several servers
268+
we may need a cache per server if we don't want all servers to share the reset
269+
leaving it commented for now because it should still work
270+
&& tsconfckCache?.hasParseResult(changedFile)
271+
*/
272+
) {
273+
server.config.logger.info(
274+
`changed tsconfig file detected: ${id} - Clearing cache and forcing full-reload to ensure TypeScript is compiled with updated config values.`,
275+
{ clear: server.config.clearScreen, timestamp: true },
276+
)
277+
278+
// TODO: more finegrained invalidation than the nuclear option below
279+
280+
// clear module graph to remove code compiled with outdated config
281+
for (const environment of Object.values(server.environments)) {
282+
environment.moduleGraph.invalidateAll()
283+
}
284+
285+
// reset tsconfck cache so that recompile works with up2date configs
286+
tsconfckCache?.clear()
287+
288+
// reload environments
289+
for (const environment of Object.values(server.environments)) {
290+
environment.hot.send({
291+
type: 'full-reload',
292+
path: '*',
293+
})
294+
}
295+
}
262296
},
263297
buildEnd() {
264298
// recycle serve to avoid preventing Node self-exit (#6815)
@@ -476,35 +510,3 @@ export async function loadTsconfigJsonForFile(
476510
throw e
477511
}
478512
}
479-
480-
async function reloadOnTsconfigChange(changedFile: string) {
481-
// server could be closed externally after a file change is detected
482-
if (!server) return
483-
// any tsconfig.json that's added in the workspace could be closer to a code file than a previously cached one
484-
// any json file in the tsconfig cache could have been used to compile ts
485-
if (
486-
path.basename(changedFile) === 'tsconfig.json' ||
487-
(changedFile.endsWith('.json') &&
488-
tsconfckCache?.hasParseResult(changedFile))
489-
) {
490-
server.config.logger.info(
491-
`changed tsconfig file detected: ${changedFile} - Clearing cache and forcing full-reload to ensure TypeScript is compiled with updated config values.`,
492-
{ clear: server.config.clearScreen, timestamp: true },
493-
)
494-
495-
// clear module graph to remove code compiled with outdated config
496-
server.moduleGraph.invalidateAll()
497-
498-
// reset tsconfck so that recompile works with up2date configs
499-
tsconfckCache?.clear()
500-
501-
// server may not be available if vite config is updated at the same time
502-
if (server) {
503-
// force full reload
504-
server.hot.send({
505-
type: 'full-reload',
506-
path: '*',
507-
})
508-
}
509-
}
510-
}

0 commit comments

Comments
 (0)