refactor(dream-cli): guard .env grep pipelines against pipefail kill on missing keys#1008
Merged
Lightheartdevs merged 1 commit intoLight-Heart-Labs:mainfrom Apr 27, 2026
Conversation
Seven 'grep "^KEY=" .env | cut | tr' pipelines in dream-cli currently emit exit 1 when the key is absent. Under set -eo pipefail these pipelines would kill the script before the downstream defensive checks ([[ -n ... ]], :-(not set)) can handle the empty-on-miss case the surrounding code was written for. Appended '|| true' to each pipeline at: - line 254 _check_version_compat (DREAM_VERSION) - line 836 cmd_dry_run (DREAM_VERSION) - line 849 cmd_dry_run (DASHBOARD_API_KEY) - line 938 cmd_dry_run loop (model-related keys) - line 953 cmd_dry_run loop (2) (model-related keys) - line 1434 cmd_enable (GPU_BACKEND) - line 1781 cmd_preset (DREAM_MODE) Line 254 additionally swaps '| head -1' for '| sed -n '1p'' (BSD/GNU-portable, SIGPIPE-safe under pipefail). Line 1434 additionally picks up a missing 2>/dev/null for consistency with the other six sites. Preventive hardening — becomes load-bearing once set -o pipefail lands in the CLI.
This was referenced Apr 24, 2026
This was referenced Apr 28, 2026
yasinBursali
added a commit
to yasinBursali/DreamServer
that referenced
this pull request
Apr 29, 2026
Maintainer audit on PR Light-Heart-Labs#998 (Lightheartdevs, 2026-04-28) flagged that under `set -euo pipefail`, `_check_version_compat` must tolerate a `.env` lacking `DREAM_VERSION` and fall back to `.version` / `manifest.json`. The audit-required form is the trailing `|| true` on the DREAM_VERSION grep pipeline: _COMPAT_INSTALLED_VER=$(grep '^DREAM_VERSION=' "$INSTALL_DIR/.env" 2>/dev/null \ | sed -n '1p' | cut -d= -f2 | tr -d '[:space:]' || true) The rebase onto current main (which carries Light-Heart-Labs#1008's tolerance fix) preserved this form via conflict resolution; this test locks it in. `tests/test-dream-cli-version-compat-pipefail.sh` (4 cases, wired into `make test`): 1. dream-cli runs under strict mode (set -e or stricter). 2. The DREAM_VERSION grep pipeline ends with `|| true` (matched against active code; comment lines stripped before grep so the rationale block can't satisfy the assertion on its own). 3. `.version` and `manifest.json` fallback branches still exist (they are the destinations the `|| true` enables reaching). 4. Anti-regression: the bare-close form (no trailing `|| true`) does NOT appear — catches a future "cleanup" PR removing the guard. Behavioural test was attempted but rejected: `_check_version_compat` depends on `warn`/`log`/`_manifest_field`/`_semver_*` and several file-scope color vars, so isolating it requires too much harness setup. The dream-cli BATS suite (Light-Heart-Labs#1018) carries the behavioural coverage at the right layer. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
What
Seven
grep "^KEY=" .env | cut | trpipelines indream-cliwouldexit 1 when the key is absent. Under
set -eo pipefailthosepipelines would kill the script before the downstream defensive
checks (
[[ -n ... ]],${var:-(not set)}) can handle theempty-on-miss case the surrounding code was written for.
Why
The surrounding code treats missing keys as benign (empty string,
"not set" default, fallthrough to defaults). That contract held
pre-pipefail because a grep miss yielded an empty pipeline output
with exit 0. Post-pipefail, a grep miss propagates exit 1, and
because these pipelines are assigned with bare
VAR=$(...)(notlocal VAR=$(...), which would mask the exit status),set -ekills the script mid-flow.
How
Appended
|| trueto each of the seven pipelines:_check_version_compatDREAM_VERSIONcmd_dry_runDREAM_VERSIONcmd_dry_runDASHBOARD_API_KEYcmd_dry_runloopcmd_dry_runloop (2)cmd_enableGPU_BACKENDcmd_presetDREAM_MODELine 254 additionally swaps
| head -1for| sed -n '1p'—SIGPIPE-safe under pipefail, portable across BSD and GNU sed.
Line 1434 additionally picks up a missing
2>/dev/nullforconsistency with the other six sites.
Six other
grep "^KEY="pipelines in the file (around lines 2082,2084–2086, 2163–2164) use the single-line
local VAR=$(...)form,which masks the pipeline exit status (a
localcommand alwaysexits 0 regardless of RHS) — those sites are already safe and are
intentionally out of scope.
Testing
bash -npasses.shellcheckdiff against base: zero new warnings.set -eo pipefail:grep '^NOPE=' file | cut -d= -f2 | tr -d '[:space:]' || true→rc=0, empty value (missing key).grep '^FOO=' file | cut -d= -f2 | tr -d '[:space:]' || true→rc=0, value returned (present key).sed -n '1p'works identically on BSD (macOS) and GNU (Linux)sed; no platform hazard.
Merge order (important)
This refactor is preventive on upstream/main today:
dream-cliis on
set -eonly, so a grep miss in any of these pipelines issilently absorbed. It becomes load-bearing the moment #998
(
fix/dream-cli-pipefail-exit-codes, enablesset -o pipefail)merges — without this fix in place,
dream update,dream rollback,dream enable,dream preset, anddream dry-runcanabort mid-flow on installs that predate (or manually-edited-out) a
given .env key.
Recommended ordering: merge this PR in the same batch as
#998, or land this first. If #998 merges alone, users on upstream
hit the regression immediately.
Platform Impact
grep,cut,tr,sed -n '1p'all behave identically. Zero platform risk.📋 Chain status (operator's reminder — apr-25)
This PR is the head of a
dream-clistrict-mode chain:After this PR merges, the next operator step is:
gh pr ready 998).#998 / #1002 / #1018 are kept in DRAFT as a mechanical safeguard so they cannot merge before this one.