Add more details to ArgumentError if process resolution fails (#59)
diff --git a/CHANGELOG.md b/CHANGELOG.md index d5561b7..ec52840 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md
@@ -1,7 +1,9 @@ -#### 4.0.1 +#### 4.1.0 * Fix the signatures of `ProcessManager.run`, `.runSync`, and `.start` to be consistent with `LocalProcessManager`'s. +* Added more details to the `ArgumentError` thrown when a command cannot be resolved + to an executable. #### 4.0.0
diff --git a/lib/src/interface/common.dart b/lib/src/interface/common.dart index a3aed86..2f6a5c9 100644 --- a/lib/src/interface/common.dart +++ b/lib/src/interface/common.dart
@@ -53,9 +53,9 @@ String? workingDirectory, { Platform platform = const LocalPlatform(), FileSystem fs = const LocalFileSystem(), + bool errorOnNull = false, }) { assert(_osToPathStyle[platform.operatingSystem] == fs.path.style.name); - try { workingDirectory ??= fs.currentDirectory.path; } on FileSystemException { @@ -89,6 +89,11 @@ return path; } } + if (errorOnNull) { + throw ArgumentError('Failed to resolve $command to an executable.\n' + 'workingDirectory: $workingDirectory, ' + 'candidates: ${candidates.length}'); + } return null; }
diff --git a/lib/src/interface/local_process_manager.dart b/lib/src/interface/local_process_manager.dart index a16b753..fe5041c 100644 --- a/lib/src/interface/local_process_manager.dart +++ b/lib/src/interface/local_process_manager.dart
@@ -105,7 +105,8 @@ @override bool canRun(covariant String executable, {String? workingDirectory}) => - getExecutablePath(executable, workingDirectory) != null; + getExecutablePath(executable, workingDirectory, errorOnNull: false) != + null; @override bool killPid(int pid, [ProcessSignal signal = ProcessSignal.sigterm]) { @@ -119,7 +120,8 @@ if (runInShell) { return commandName; } - String? exe = getExecutablePath(commandName, workingDirectory); + String? exe = + getExecutablePath(commandName, workingDirectory, errorOnNull: true); if (exe == null) { throw ArgumentError('Cannot find executable for $commandName.'); }
diff --git a/pubspec.yaml b/pubspec.yaml index 2c6229d..c854b97 100644 --- a/pubspec.yaml +++ b/pubspec.yaml
@@ -1,5 +1,5 @@ name: process -version: 4.0.1 +version: 4.1.0 description: A pluggable, mockable process invocation abstraction for Dart. homepage: https://github.com/google/process.dart
diff --git a/test/src/interface/common_test.dart b/test/src/interface/common_test.dart index 6a3e2df..cbfd180 100644 --- a/test/src/interface/common_test.dart +++ b/test/src/interface/common_test.dart
@@ -192,6 +192,29 @@ expect(executablePath, isNull); }); + test('not found with errorOnNull throws exception with match state', () { + String command = 'foo.exe'; + dynamic error; + try { + getExecutablePath( + command, + workingDir.path, + platform: platform, + fs: fs, + errorOnNull: true, + ); + fail('Expected to throw'); + } catch (err) { + error = err; + } + + expect(error, isA<ArgumentError>()); + expect( + error.toString(), + contains( + 'workingDirectory: C:\\.tmp_rand0\\work_dir_rand0, candidates: 2')); + }); + test('when path has spaces', () { expect( sanitizeExecutablePath('Program Files\\bla.exe', @@ -298,6 +321,29 @@ expect(executablePath, isNull); }); + test('not found with errorOnNull throws exception with match state', () { + String command = 'foo'; + dynamic error; + try { + getExecutablePath( + command, + workingDir.path, + platform: platform, + fs: fs, + errorOnNull: true, + ); + fail('Expected to throw'); + } catch (err) { + error = err; + } + + expect(error, isA<ArgumentError>()); + expect( + error.toString(), + contains( + 'workingDirectory: /.tmp_rand0/work_dir_rand0, candidates: 2')); + }); + test('when path has spaces', () { expect( sanitizeExecutablePath('/usr/local/bin/foo bar',