run method

Implementation

Future<List<TargetResult>> run() async {
  Directory(logsDir).createSync(recursive: true);
  final queue = Queue<JobProgress>.of(tracker.jobs);
  final results = <TargetResult>[];

  void tick() {
    _pollWorkers();
    view.update(tracker);
    if (progressFile != null) tracker.writeFile(progressFile!);
  }

  final ticker = Timer.periodic(const Duration(seconds: 1), (_) => tick());
  final signals = <StreamSubscription<ProcessSignal>>[
    ProcessSignal.sigint.watch().listen((_) => _onSignal()),
    if (!Platform.isWindows) ...[
      ProcessSignal.sigterm.watch().listen((_) => _onSignal()),
      // IDE stop buttons and closed terminals send SIGHUP.
      ProcessSignal.sighup.watch().listen((_) => _onSignal()),
    ],
  ];
  tick();

  try {
    await Future.wait([
      for (var i = 0;
          i < math.min(tracker.parallel, tracker.jobs.length);
          i++)
        _worker(queue, results, tick),
    ]);
  } finally {
    ticker.cancel();
    _forceQuit?.cancel();
    for (final s in signals) {
      await s.cancel();
    }
    view.finish(tracker);
    if (progressFile != null) tracker.writeFile(progressFile!);
  }

  // Keep the requested order in the summary.
  final order = [
    for (final j in tracker.jobs)
      for (final t in j.job.targets) '${j.job.client}/${t.label}'
  ];
  results.sort((a, b) => order
      .indexOf('${a.client}/${a.target.label}')
      .compareTo(order.indexOf('${b.client}/${b.target.label}')));
  return results;
}