fix(task): skip shebang line in displayed task command#9844
Conversation
When a task's `run` value starts with a shebang (e.g. `#!/usr/bin/env bash`), mise echoes the command being run as `[task] $ <first line>`, which for shebang scripts ended up showing `[task] $ #!/usr/bin/env bash` instead of something useful. Strip the shebang line for display so the first actual command appears; execution is unchanged. Fixes #9842. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
There was a problem hiding this comment.
Code Review
This pull request modifies the TaskExecutor to improve command display by stripping leading shebangs from scripts, ensuring users see the actual command content. A review comment identifies a redundant .to_string() call on the result of the format! macro, which should be removed to avoid unnecessary allocations.
Greptile SummaryThis PR fixes the task command echo so that scripts starting with shebang or
Confidence Score: 5/5Safe to merge — the change is purely cosmetic, touching only how the echoed command string is built for display; the script written to disk and executed is unchanged. The diff is small and self-contained: a single No files require special attention. Important Files Changed
Reviews (5): Last reviewed commit: "style(task): apply cargo fmt" | Re-trigger Greptile |
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
`set -Eeuo pipefail` and similar shell-options lines aren't useful to echo as the task's "command" either — skip them along with the shebang so the displayed line is the first real command in the script. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
… empty If a script is entirely shebang/blank/`set ...` lines, `display_script` ends up empty, which previously produced "$ arg1 arg2" (double space) when args were present. Join only the non-empty parts. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Hyperfine Performance
|
| Command | Mean [ms] | Min [ms] | Max [ms] | Relative |
|---|---|---|---|---|
mise-2026.5.7 x -- echo |
18.5 ± 0.8 | 16.7 | 22.8 | 1.00 |
mise x -- echo |
18.9 ± 1.2 | 16.8 | 23.8 | 1.03 ± 0.08 |
mise env
| Command | Mean [ms] | Min [ms] | Max [ms] | Relative |
|---|---|---|---|---|
mise-2026.5.7 env |
18.3 ± 0.8 | 16.8 | 22.2 | 1.00 |
mise env |
18.4 ± 0.8 | 16.7 | 23.2 | 1.00 ± 0.06 |
mise hook-env
| Command | Mean [ms] | Min [ms] | Max [ms] | Relative |
|---|---|---|---|---|
mise-2026.5.7 hook-env |
19.4 ± 0.9 | 17.6 | 23.2 | 1.00 |
mise hook-env |
19.4 ± 0.9 | 17.6 | 23.5 | 1.00 ± 0.07 |
mise ls
| Command | Mean [ms] | Min [ms] | Max [ms] | Relative |
|---|---|---|---|---|
mise-2026.5.7 ls |
15.7 ± 0.8 | 14.1 | 19.3 | 1.00 |
mise ls |
15.9 ± 0.8 | 14.3 | 19.5 | 1.02 ± 0.07 |
xtasks/test/perf
| Command | mise-2026.5.7 | mise | Variance |
|---|---|---|---|
| install (cached) | 121ms | 124ms | -2% |
| ls (cached) | 55ms | 55ms | +0% |
| bin-paths (cached) | 62ms | 63ms | -1% |
| task-ls (cached) | 481ms | 480ms | +0% |
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
## Summary When a task's `run` body starts with a shebang (e.g. `#!/usr/bin/env bash`) and/or shell-option lines like `set -Eeuo pipefail`, the command echo ends up showing only that boilerplate: ``` [generate-completions] $ #!/usr/bin/env bash ``` That's the only thing the user sees for the entire task — every following line of the body is hidden because [`trunc`](src/task/task_output.rs:33) keeps just the first line of the displayed command, and for these scripts the first line is boilerplate. This PR skips leading shebang, blank, and `set ...` lines when building the displayed command, so the first real command shows up. Execution is unchanged — the script (shebang and all) is still written to the temp file and run normally. ### Before / after ``` # before [generate-completions] $ #!/usr/bin/env bash # after [generate-completions] $ fzf --fish > ~/.config/fish/completions/fzf.fish ``` Verified locally across several variants: ``` [repro] $ echo "real command" # was: #!/usr/bin/env bash [with-shebang] $ echo "after set -e" # shebang + set skipped [set-without-shebang] $ echo "after set" # bare set skipped [shebang-only] $ echo "after blank line" # blank line skipped [no-skip] $ echo 'simple one-liner' # unchanged ``` Fixes jdx#9842. ## Test plan - [x] `cargo build` — clean - [x] `cargo test --bin mise task::` — 124 task unit tests pass - [x] Manual smoke test across shebang, set, blank-line, and plain variants 🤖 Generated with [Claude Code](https://claude.com/claude-code) <!-- CURSOR_SUMMARY --> --- > [!NOTE] > **Low Risk** > Low risk: changes only affect how inline task scripts are *displayed* (echoed) before execution, not how they run. Main risk is minor formatting edge cases for empty scripts/args. > > **Overview** > Task command echoing for inline `run` scripts now **skips leading boilerplate** (blank lines, shebangs, and `set ...`) so the first *real* command is shown instead of just the header. > > The displayed `$ ...` string construction was adjusted to handle empty script/argument combinations without producing awkward output; execution behavior remains unchanged. > > <sup>Reviewed by [Cursor Bugbot](https://cursor.com/bugbot) for commit eb6e59a. Bugbot is set up for automated code reviews on this repo. Configure [here](https://www.cursor.com/dashboard/bugbot).</sup> <!-- /CURSOR_SUMMARY --> --------- Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
|
@jdx I think it would have been good if it did something else than just printing the first line on multi-line Options:
|
Summary
When a task's
runbody starts with a shebang (e.g.#!/usr/bin/env bash) and/or shell-option lines likeset -Eeuo pipefail, the command echo ends up showing only that boilerplate:That's the only thing the user sees for the entire task — every following line of the body is hidden because
trunckeeps just the first line of the displayed command, and for these scripts the first line is boilerplate.This PR skips leading shebang, blank, and
set ...lines when building the displayed command, so the first real command shows up. Execution is unchanged — the script (shebang and all) is still written to the temp file and run normally.Before / after
Verified locally across several variants:
Fixes #9842.
Test plan
cargo build— cleancargo test --bin mise task::— 124 task unit tests pass🤖 Generated with Claude Code
Note
Low Risk
Low risk: changes only affect how inline task scripts are displayed (echoed) before execution, not how they run. Main risk is minor formatting edge cases for empty scripts/args.
Overview
Task command echoing for inline
runscripts now skips leading boilerplate (blank lines, shebangs, andset ...) so the first real command is shown instead of just the header.The displayed
$ ...string construction was adjusted to handle empty script/argument combinations without producing awkward output; execution behavior remains unchanged.Reviewed by Cursor Bugbot for commit eb6e59a. Bugbot is set up for automated code reviews on this repo. Configure here.