fix(remote-job): a job name is data, never a shell pattern

`status` built its job list with `for n in $names`, which word-splits AND globs. The
second half is the bug: a job named `x*` was expanded against the caller's working
directory, so the report described unrelated files there as jobs and never mentioned
the one that ran — on a harness whose whole purpose is a report you can trust after
the session that started the job is gone. Splitting stays (several names in one
argument is the documented call shape); expansion goes.

`tail` was honest-by-accident in the wrong direction: with no jobs it handed a
literal `$JOBS/*.out` to tail, which reports a missing *file* — indistinguishable
from a broken tool — and a missing name produced tail's errno rather than "no job
called that". Both now say what is missing and exit 1.

Red first: the name test reads the report from a directory containing an unrelated
file, so the old glob is visible as a phantom job; both new tests fail against the
previous code and pass against this one.

Refs #60
This commit is contained in:
Frank committed 2026-10-21 01:06:11 -07:00
1 parent d0587a5bc5
commit 8393dc1090
3 files changed
+48 -8

No files matched your search

+3 -2
View File
@@ -38,10 +38,10 @@ read afterwards by a short-lived connection. That is what this is.
```bash
remote-job.sh start NAME [--] CMD... # launch detached, return at once
remote-job.sh status [NAME] # one line per job; exit 0 only if all DONE
remote-job.sh status [NAME] # one line per job; names literal, never globs
remote-job.sh wait NAME [SEC] [N] # block until DONE or timeout, then tail N lines
remote-job.sh out NAME [N] # tail a job's output
remote-job.sh tail [NAME] # follow one job, or every job at once
remote-job.sh tail [NAME] # follow one job, or all; exit 1 if nothing to follow
remote-job.sh watch # refreshing status, for a spare pane
```
@@ -77,6 +77,7 @@ can be made from a fresh session on a machine that rebooted underneath it.
| Command name is wrong | `PENDING (no output yet)`, exit 1 — never a false DONE |
| Job exits non-zero | `DONE rc=N`; the code is data, not the report's status |
| Two jobs, same NAME | the second replaces the first's state files |
| `tail` with no job, or a name that is a glob | exit 1 saying there is nothing to follow; names are matched literally, never expanded |
| Job dir missing | created on first use |
Pinned by `tests/remote-job.bats` (black-box: output, exit codes, sentinel