blob: 0ead18cc2ce1c34b57480e6b035ed170c5302967 [file] [log] [blame]
// Copyright 2013 The Flutter Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
import 'package:engine_build_configs/engine_build_configs.dart';
import '../build_plan.dart';
import '../build_utils.dart';
import '../gn.dart';
import '../label.dart';
import '../proc_utils.dart';
import '../worker_pool.dart';
import 'command.dart';
/// The root 'test' command.
final class TestCommand extends CommandBase {
/// Constructs the 'test' command.
TestCommand({
required super.environment,
required Map<String, BuilderConfig> configs,
super.help = false,
super.usageLineLength,
}) {
builds = BuildPlan.configureArgParser(
argParser,
environment,
configs: configs,
help: help,
);
}
/// List of compatible builds.
late final List<Build> builds;
@override
String get name => 'test';
@override
String get description => '''
Runs a test target
et test //flutter/fml/... # Run all test targets in `//flutter/fml` and its subdirectories.
et test //flutter/fml:all # Run all test targets in `//flutter/fml`.
et test //flutter/fml:fml_benchmarks # Run a single test target in `//flutter/fml`.
''';
@override
Future<int> run() async {
final plan = BuildPlan.fromArgResults(
argResults!,
environment,
builds: builds,
);
if (!await ensureBuildDir(
environment,
plan.build,
enableRbe: plan.useRbe,
extraGnArgs: plan.toGnArgs(),
)) {
return 1;
}
// Builds only accept labels as arguments, so convert patterns to labels.
final gn = Gn.fromEnvironment(environment);
// Figure out what targets the user wants to build.
final buildTargets = <BuildTarget>{};
for (final pattern in argResults!.rest) {
final target = TargetPattern.parse(pattern);
final found = await gn.desc(
'out/${plan.build.ninja.config}',
target,
);
buildTargets.addAll(found);
}
if (buildTargets.isEmpty) {
environment.logger.error('No targets found, nothing to test.');
return 1;
}
// Make sure there is at least one test target.
final testTargets = buildTargets
.whereType<ExecutableBuildTarget>()
.where((ExecutableBuildTarget t) => t.testOnly)
.toList();
if (testTargets.isEmpty) {
environment.logger.error('No test targets found');
return 1;
}
final buildExitCode = await runBuild(
environment,
plan.build,
concurrency: plan.concurrency ?? 0,
targets: testTargets.map((target) => target.label).toList(),
enableRbe: plan.useRbe,
rbeConfig: plan.toRbeConfig(),
extraGnArgs: plan.toGnArgs(),
);
if (buildExitCode != 0) {
return buildExitCode;
}
final workerPool = WorkerPool(
environment,
ProcessTaskProgressReporter(environment),
);
final tasks = <ProcessTask>{};
for (final target in testTargets) {
final commandLine = <String>[target.executable];
tasks.add(ProcessTask(
target.label.toString(),
environment,
environment.engine.srcDir,
commandLine,
));
}
return await workerPool.run(tasks) ? 0 : 1;
}
}