diff --git a/tests/test_tools/test_command_scan.py b/tests/test_tools/test_command_scan.py index ea8b8e6..2e73d30 100644 --- a/tests/test_tools/test_command_scan.py +++ b/tests/test_tools/test_command_scan.py @@ -183,6 +183,33 @@ def test_unwrap_remote_client_alone() -> None: assert unwrap_command(argv).remote is None, argv +def test_unwrap_reads_options_with_getopt() -> None: + """Each wrapper's spec is a ``getopt`` pattern: flags and values are exact. + + ``--`` ends the wrapper's options, jammed values work (``-p2222``), and a + launcher's common flags stay flags (``uv run --no-project pytest``). + """ + assert unwrap_command(["sudo", "-u", "root", "--", "rm", "-rf", "/"]).base == "rm" + assert unwrap_command(["ssh", "-p2222", "prod", "uptime"]).base == "uptime" + assert unwrap_command(["uv", "run", "--no-project", "pytest", "-x"]).base == "pytest" + assert unwrap_command(["time", "-f", "%e", "python", "x.py"]).base == "python" + assert unwrap_command(["xargs", "-0", "--", "rm"]).base == "rm" + + +def test_an_unknown_option_stops_the_unwrap_and_is_reported() -> None: + """The program behind an option we cannot read is a guess, so it is reported. + + The wrapper itself stays the command: ``sudo rm -rf /`` is still + judged as ``sudo`` by the denylist, so nothing hides behind the guess. + """ + scan = unwrap_command(["sudo", "--new-sudo-flag", "rm", "-rf", "/"]) + assert scan.base == "sudo", scan + assert scan.wrappers == () + assert "new-sudo-flag" in scan.unparsed + # A known option is read, not reported. + assert unwrap_command(["sudo", "-E", "rm", "-rf", "/"]).unparsed == "" + + def test_unwrap_remote_command_still_reviews_what_runs() -> None: """The remote slice is parsed like a local command (code, escalation).""" scan = unwrap_command(["ssh", "prod", "bash", "-c", "rm -rf /"]) diff --git a/tests/test_tools/test_danger.py b/tests/test_tools/test_danger.py index dfe6f47..f06619f 100644 --- a/tests/test_tools/test_danger.py +++ b/tests/test_tools/test_danger.py @@ -174,6 +174,16 @@ def test_a_remote_command_is_judged_by_what_runs_there() -> None: assert pty is not None and "python3" in pty +def test_an_unreadable_option_asks_instead_of_guessing() -> None: + """An option the spec does not know makes the wrapped program a guess.""" + reason = _reason("run_argv", {"argv": ["sudo", "--new-sudo-flag", "uptime"]}) + assert reason is not None + assert "options not understood" in reason + assert "new-sudo-flag" in reason + # A known option is read: no review for a harmless wrapped program. + assert _reason("run_argv", {"argv": ["sudo", "-E", "uptime"]}) is None + + def test_a_remote_shell_is_announced() -> None: """``ssh host`` runs nothing this scan can see, so the human is told first.""" reason = _reason("open_pty", {"command": ["ssh", "prod"]})