watchForFileChanges method

Future<void> watchForFileChanges()

Implementation

Future<void> watchForFileChanges() async {
  logger.detail('Watching ${root.path} for changes');

  if (_watcherSubscription != null) {
    return;
  }

  // Watch the root directory
  _watcherSubscription = DirectoryWatcher(root.path).events
      .asyncMap((event) async {
        final WatchEvent(:type, :path) = event;

        if (type == ChangeType.REMOVE) {
          await onFileRemove(path);
        } else {
          await onFilesChange([path]);
        }

        return event;
      })
      .debounce(Duration.zero)
      .listen((event) {
        final WatchEvent(:type, :path) = event;

        _reload(path);
      });

  _watcherSubscription
      ?.asFuture<void>()
      .then((_) async {
        await _cancelWatcherSubscription();
        await stop();
      })
      .catchError((_) async {
        await _cancelWatcherSubscription();
        await stop(1);
      })
      .ignore();

  // Watch dependency directories if available
  if (getDependencyDirectories case final getDependencyDirectories?
      when _dependencyWatchers.isEmpty) {
    final dependencyDirs = await getDependencyDirectories();
    for (final dir in dependencyDirs) {
      logger.detail('Watching dependency directory: $dir');
      final watcher = DirectoryWatcher(dir).events
          .asyncMap((event) async {
            final WatchEvent(:type, :path) = event;

            // Only watch for Dart files in dependency directories
            if (p.extension(path) == '.dart') {
              if (type == ChangeType.REMOVE) {
                await onFileRemove(path);
              } else {
                await onFilesChange([path]);
              }
            }

            return event;
          })
          .debounce(Duration.zero)
          .listen((event) {
            final WatchEvent(:type, :path) = event;

            if (p.extension(path) == '.dart') {
              _reload(path);
            }
          });

      _dependencyWatchers.add(watcher);

      watcher
          .asFuture<void>()
          .then((_) async {
            await _cancelWatcherSubscription();
            await stop();
          })
          .catchError((_) async {
            await _cancelWatcherSubscription();
            await stop(1);
          })
          .ignore();
    }
  }
}