philiprehberger-task_runner 0.5.0 → 0.6.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/CHANGELOG.md +5 -0
- data/README.md +17 -0
- data/lib/philiprehberger/task_runner/version.rb +1 -1
- data/lib/philiprehberger/task_runner.rb +31 -0
- metadata +2 -2
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 81a304bf73bc20e70f8bb340125ed6cbc3add80df788e746909341cdbcac85a4
|
|
4
|
+
data.tar.gz: 46e8d6a93c2f3501142a9a4c330a8686e0d91edfd2c3bcd2674508075d563c34
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: 83345dc31740a6618be9d21078c0b0640ba04bb54b08d457e67fc0df37786e2c8f86b316355ffd558bf1470967e71aa54575a4f98a2b75acaf8731059b8fbf52
|
|
7
|
+
data.tar.gz: 304a3c5de5afd3a41e61dd9e127dc8fabecf546743a22900df0486ad95a768f7112f3713f8f4de9747080a31a0e0563a2c3d67b547a3cd6eefbc9f32b0e9ea83
|
data/CHANGELOG.md
CHANGED
|
@@ -7,6 +7,11 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
|
|
|
7
7
|
|
|
8
8
|
## [Unreleased]
|
|
9
9
|
|
|
10
|
+
## [0.6.0] - 2026-04-28
|
|
11
|
+
|
|
12
|
+
### Added
|
|
13
|
+
- `TaskRunner.which(cmd)` — absolute path of an executable on `PATH`, or `nil` when not found. Honors `ENV['PATHEXT']` on Windows. Raises `ArgumentError` for nil/empty input.
|
|
14
|
+
|
|
10
15
|
## [0.5.0] - 2026-04-21
|
|
11
16
|
|
|
12
17
|
### Added
|
data/README.md
CHANGED
|
@@ -60,6 +60,22 @@ if Philiprehberger::TaskRunner.run?('which', 'git')
|
|
|
60
60
|
end
|
|
61
61
|
```
|
|
62
62
|
|
|
63
|
+
### Which
|
|
64
|
+
|
|
65
|
+
Locate an executable on `PATH` (like the `which` shell builtin). Returns the
|
|
66
|
+
absolute path or `nil` when not found:
|
|
67
|
+
|
|
68
|
+
```ruby
|
|
69
|
+
Philiprehberger::TaskRunner.which("git")
|
|
70
|
+
# => "/usr/bin/git"
|
|
71
|
+
|
|
72
|
+
Philiprehberger::TaskRunner.which("definitely-not-installed")
|
|
73
|
+
# => nil
|
|
74
|
+
```
|
|
75
|
+
|
|
76
|
+
On Windows, candidate suffixes from `ENV["PATHEXT"]` (`.COM`, `.EXE`,
|
|
77
|
+
`.BAT`, `.CMD`) are tried automatically.
|
|
78
|
+
|
|
63
79
|
### Timeout
|
|
64
80
|
|
|
65
81
|
```ruby
|
|
@@ -125,6 +141,7 @@ end
|
|
|
125
141
|
| `.run(cmd, *args, timeout:, env:, chdir:, signal:, kill_after:, stdin:)` | Run a command and return a Result |
|
|
126
142
|
| `.run!(cmd, *args, **opts)` | Same as `run`, raises `CommandError` on non-zero exit |
|
|
127
143
|
| `.run?(cmd, *args, **opts)` | Boolean shortcut — true only when exit code is 0; timeouts return false |
|
|
144
|
+
| `.which(cmd)` | Absolute path of `cmd` on PATH (or `nil`); honors `PATHEXT` on Windows |
|
|
128
145
|
| `CommandError#result` | The failed `Result` object |
|
|
129
146
|
| `.run(cmd) { \|line\| ... }` | Run with line-by-line stdout streaming |
|
|
130
147
|
| `.run(cmd) { \|line, stream\| ... }` | Run with stdout and stderr streaming |
|
|
@@ -81,6 +81,37 @@ module Philiprehberger
|
|
|
81
81
|
false
|
|
82
82
|
end
|
|
83
83
|
|
|
84
|
+
# Find the absolute path of an executable on PATH.
|
|
85
|
+
#
|
|
86
|
+
# Behaves like the `which` shell builtin: walks each entry in
|
|
87
|
+
# `ENV['PATH']` and returns the first directory that contains an
|
|
88
|
+
# executable file matching `cmd`. On Windows, also tries each suffix in
|
|
89
|
+
# `ENV['PATHEXT']`. Returns `nil` when nothing is found.
|
|
90
|
+
#
|
|
91
|
+
# @param cmd [String] the executable name to search for
|
|
92
|
+
# @return [String, nil] the absolute path, or nil when not found
|
|
93
|
+
# @raise [ArgumentError] if `cmd` is nil or empty
|
|
94
|
+
def self.which(cmd)
|
|
95
|
+
raise ArgumentError, 'cmd cannot be nil or empty' if cmd.nil? || cmd.to_s.empty?
|
|
96
|
+
|
|
97
|
+
exts = if Gem.win_platform?
|
|
98
|
+
(ENV['PATHEXT'] || '.COM;.EXE;.BAT;.CMD').split(';')
|
|
99
|
+
else
|
|
100
|
+
['']
|
|
101
|
+
end
|
|
102
|
+
|
|
103
|
+
ENV.fetch('PATH', '').split(File::PATH_SEPARATOR).each do |dir|
|
|
104
|
+
next if dir.empty?
|
|
105
|
+
|
|
106
|
+
exts.each do |ext|
|
|
107
|
+
candidate = File.join(dir, "#{cmd}#{ext}")
|
|
108
|
+
return File.expand_path(candidate) if File.file?(candidate) && File.executable?(candidate)
|
|
109
|
+
end
|
|
110
|
+
end
|
|
111
|
+
|
|
112
|
+
nil
|
|
113
|
+
end
|
|
114
|
+
|
|
84
115
|
# @api private
|
|
85
116
|
def self.run_capture(env_hash, full_cmd, spawn_opts, timeout, start_time, signal, kill_after, stdin_data)
|
|
86
117
|
stdout_buf = +''
|
metadata
CHANGED
|
@@ -1,14 +1,14 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: philiprehberger-task_runner
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 0.
|
|
4
|
+
version: 0.6.0
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- Philip Rehberger
|
|
8
8
|
autorequire:
|
|
9
9
|
bindir: bin
|
|
10
10
|
cert_chain: []
|
|
11
|
-
date: 2026-04-
|
|
11
|
+
date: 2026-04-29 00:00:00.000000000 Z
|
|
12
12
|
dependencies: []
|
|
13
13
|
description: Run shell commands with captured stdout/stderr, exit code, duration measurement,
|
|
14
14
|
configurable timeout, environment variables, line-by-line streaming, graceful signal
|