(events: FSEvent[])
| 318 | } |
| 319 | |
| 320 | async handleFilesystemEvents(events: FSEvent[]): Promise<void> { |
| 321 | output.debug(`Filesystem watcher notified of ${events.length} events`); |
| 322 | |
| 323 | const filesChanged: Set<string> = new Set(); |
| 324 | const filesRemoved: Set<string> = new Set(); |
| 325 | |
| 326 | const distPaths: string[] = []; |
| 327 | |
| 328 | for (const buildMatch of this.buildMatches.values()) { |
| 329 | for (const buildResult of buildMatch.buildResults.values()) { |
| 330 | if (buildResult.distPath) { |
| 331 | distPaths.push(buildResult.distPath); |
| 332 | } |
| 333 | } |
| 334 | } |
| 335 | |
| 336 | events = events.filter(event => |
| 337 | distPaths.every(distPath => !event.path.startsWith(distPath)) |
| 338 | ); |
| 339 | |
| 340 | // First, update the `files` mapping of source files |
| 341 | for (const event of events) { |
| 342 | if (event.type === 'add') { |
| 343 | await this.handleFileCreated(event.path, filesChanged, filesRemoved); |
| 344 | } else if (event.type === 'unlink') { |
| 345 | this.handleFileDeleted(event.path, filesChanged, filesRemoved); |
| 346 | } else if (event.type === 'change') { |
| 347 | await this.handleFileModified(event.path, filesChanged, filesRemoved); |
| 348 | } |
| 349 | } |
| 350 | |
| 351 | const vercelConfig = await this.getVercelConfig(); |
| 352 | |
| 353 | // Update the build matches in case an entrypoint was created or deleted |
| 354 | await this.updateBuildMatches(vercelConfig); |
| 355 | |
| 356 | const filesChangedArray = [...filesChanged]; |
| 357 | const filesRemovedArray = [...filesRemoved]; |
| 358 | |
| 359 | // Trigger rebuilds of any existing builds that are dependent |
| 360 | // on one of the files that has changed |
| 361 | const needsRebuild: Map<BuildResult, [string | null, BuildMatch]> = |
| 362 | new Map(); |
| 363 | |
| 364 | for (const match of this.buildMatches.values()) { |
| 365 | for (const [requestPath, result] of match.buildResults) { |
| 366 | // If the `BuildResult` is already queued for a re-build, |
| 367 | // then we can skip subsequent lookups |
| 368 | if (needsRebuild.has(result)) continue; |
| 369 | |
| 370 | if (Array.isArray(result.watch)) { |
| 371 | for (const pattern of result.watch) { |
| 372 | if ( |
| 373 | minimatches(filesChangedArray, pattern) || |
| 374 | minimatches(filesRemovedArray, pattern) |
| 375 | ) { |
| 376 | needsRebuild.set(result, [requestPath, match]); |
| 377 | break; |
no test coverage detected