From 70b68b98a5b1e584e50c29687ca5e3c4b47d8bde Mon Sep 17 00:00:00 2001 From: Jorijn van der Graaf Date: Sat, 31 Oct 2026 05:10:38 +0100 Subject: [PATCH] test: `--` reaches neither the project args nor the script `run -- record -- a` has to run the record script with the args `--` and `a`: the first `--` ends the options, the second comes after the script's name and is the script's. The project args keep only what stood before `run`. And `run -- -x` has to look for a script called -x, since after `--` an option-like word is an operand. Before the fix the first `--` showed up in the project args, and `-x` joined it there while the bare `run` listed the scripts and succeeded. Co-Authored-By: Claude Opus 5.5 --- tests/Script/main.cpp | 23 +++++++++++++++++++++++ 1 file changed, 23 insertions(+) diff --git a/tests/Script/main.cpp b/tests/Script/main.cpp index 8e200a8..472682d 100644 --- a/tests/Script/main.cpp +++ b/tests/Script/main.cpp @@ -218,6 +218,29 @@ int main() { Check(fs::exists(binSentinel) && fs::exists(buildSentinel), "`clean` as a script argument deleted nothing"); } + // `--` ends this tool's options and goes nowhere itself. In the + // project's args it gave the project a variant of its own, and every + // sibling that inherits the args one too. The word after it is an + // operand even when it looks like an option, here the script's name; + // after the name, a `--` is the script's like any other word. + { + fs::remove(scratch / "record.txt"); + const std::int32_t code = RunWith({"crafter-build", project, "--flavour=x", "run", "--", "record", "--", "a"}); + Check(code == 42, std::format("the script after `--` ran (got {})", code)); + const std::vector expected = { + "arg:--", "arg:a", + "projectArg:--flavour=x", + "debug:false", + "project:script-fixture", + }; + const std::vector record = ReadLines(scratch / "record.txt"); + Check(record == expected, "`--` reached neither the project args nor the script"); + if (record != expected) { + for (const std::string& line : record) std::println(std::cerr, " recorded: {}", line); + } + Check(RunWith({"crafter-build", project, "run", "--", "-x"}) == 1, "after `--` a word that looks like an option names the script"); + } + // The first word after `run` is the name even when it is a verb. { fs::remove(scratch / "record.txt");