runCommand method
Runs a shell command and returns the results. Throws a CliException if the process returns a non-zero exit code.
Implementation
Future<ProcessResult> runCommand(
String executable,
List<String> arguments, {
String? workingDirectory,
bool showOutput = false,
}) async {
try {
if (showOutput) {
Logger.boldInfo('Running: $executable ${arguments.join(' ')}');
final process = await Process.start(
executable,
arguments,
workingDirectory: workingDirectory,
runInShell: true,
);
// Stream stdout and stderr
final stdoutFuture = process.stdout
.transform(utf8.decoder)
.listen((data) => stdout.write(data))
.asFuture();
final stderrFuture = process.stderr
.transform(utf8.decoder)
.listen((data) => stderr.write(data))
.asFuture();
final exitCode = await process.exitCode;
await Future.wait([stdoutFuture, stderrFuture]);
if (exitCode != 0) {
throw CliException(
'Command failed with exit code $exitCode: $executable ${arguments.join(' ')}',
);
}
return ProcessResult(process.pid, exitCode, '', '');
} else {
final result = await Process.run(
executable,
arguments,
workingDirectory: workingDirectory,
runInShell: true,
);
if (result.exitCode != 0) {
throw CliException(
'Command failed: $executable ${arguments.join(' ')}\nError: ${result.stderr}',
);
}
return result;
}
} catch (e) {
if (e is CliException) rethrow;
throw CliException('Failed to execute command: $executable ${arguments.join(' ')}', e);
}
}