Command-Line Selection, Tag Expressions, Reruns, and Execution Profiles: Diagnostics, Failure Modes, and Production Practices
Diagnose zero-selection, wrong-selection, cwd-sensitive argument files, rerun identity drift, profile precedence surprises, and false-green rerun workflows while preserving first-failure evidence.
Learning objectives
- Use a fixed diagnostic sequence that begins with first-failure preservation.
- Diagnose zero/wrong selection using command, root, name normalization, and tag predicates.
- Identify cwd-sensitive argument-file paths and RobotCode precedence surprises without PYTHONPATH hacks.
- Recognize rerun identity drift and false-green merge policies.
- Separate selection cost, execution cost, logging cost, and future Pabot/CI costs.
Current compatibility baseline. Verified
2026-08-31: Robot Framework 7.4.2 is the current
stable release and requires Python 3.8+; 7.5b1 is a pre-release and
is not required. Core examples use python -m robot and
python -m robot.rebot so the interpreter is explicit.
RobotCode is not Robot Framework core; where shown as an optional
profile layer, the pinned example is RobotCode
2.7.0, which requires Python 3.10+ and Robot
Framework 5.0+. Mandatory labs do not require RobotCode, Pabot,
browsers, containers, CI accounts, or paid services.
1. Production diagnostic sequence
-
Preserve original
output.xml, log/report, command, and environment/profile evidence. - Confirm Python, Robot Framework, and optional RobotCode versions.
- Confirm execution root, source path, selectors, argument files, variables, and test data revision.
- Validate parse/import graph before changing search paths.
- Inspect suite/test long names, tag membership, and selector combination.
- Inspect library/external state only after confirming the intended tests actually ran.
- If relevant, inspect timing, Pabot workers, CI workspace, and container paths.
- Apply the least destructive correction.
- Rerun the smallest controlled slice and keep both before/after evidence.
2. Failure mode: tag expression selects zero tests
# Intentionally broken assumption: no test has BOTH smoke and slow.
python -m robot --include smokeANDslow tests
Do not “fix” this with --runemptysuite in routine
execution. First inspect tags and your intended predicate. If the
real intent is “smoke OR slow,” use smokeORslow. If the
intent is “smoke, but not slow,” use smokeNOTslow or
include/exclude. The evidence is the selection count and exact
expression, not intuition about what AND means.
3. Failure mode: simple name matches the wrong location
Large repositories often repeat names such as Health Check.
A simple --test "Health Check" can match more than
intended. Repair by using the full long name from the execution root
or by combining a suite selector with the test selector.
python -m robot --suite "Tests.Service" --test "Health Check" tests
# Or when the long name is known:
python -m robot --test "Tests.Service.Health Check" tests
If you change the execution root, the long-name prefix changes. That is an identity change, not merely a path cosmetic.
4. Failure mode: argument file works only from one directory
# config/smoke.args contains a final line: tests
# From rf-cli-lab/ this is valid:
python -m robot -A config/smoke.args
# From the parent, this locates the argument file but the inserted `tests`
# argument now refers to the parent's cwd, not config/'s directory.
python -m robot -A rf-cli-lab/config/smoke.args
Repair the command contract, not Python import behavior.
Options/data sources from argument files are inserted into the
command-line argument stream. Use a documented project-root
launcher, absolute path supplied by the launcher, or a wrapper that
explicitly resolves project root. Arbitrary
PYTHONPATH changes do not repair data-source cwd.
5. Failure mode: option/profile precedence surprise
Core argument-file options take precedence according to position:
the file contents are inserted where -A appears.
RobotCode adds a separate configuration-loading/profile layer. A
local .robot.toml can therefore explain why two
engineers using “smoke” get different output directories or
variables.
# Core: reason about order explicitly.
python -m robot --outputdir results/a -A config/base.args --outputdir results/c tests
# Optional RobotCode diagnostics.
robotcode --version
robotcode profiles list
robotcode profiles show smoke
Do not assume RobotCode is active because a
robot.toml exists; python -m robot does
not load RobotCode profiles. Conversely, if you invoke RobotCode,
inspect its resolved profile instead of debugging Robot Framework
core for a wrapper setting.
6. Failure mode: rerun output replaces the wrong logical identity
Suppose the first run failed
Tests.Service.Controlled Failure, then the file/suite
is renamed to
Tests.Service Checks.Controlled Failure before rerun.
--rerunfailed uses prior failed identity against
current source. The safest production rule is to rerun the same
revision/configuration unless the change under verification is
explicit and the mapping is understood.
Do not rename tests between first run and rerun merely to make selection work. That damages provenance. If source changed to fix a defect, record the revision change and verify that the failed logical test still maps intentionally.
7. Intentionally broken false-green workflow
# BROKEN POLICY — do not copy.
python -m robot --outputdir results/first tests || true
python -m robot --rerunfailed results/first/output.xml --outputdir results/rerun tests || true
python -m robot.rebot --merge --outputdir results/final \
results/first/output.xml results/rerun/output.xml
# Then upload only results/final and delete results/first. <-- evidence loss
This is broken for two reasons. Shell-level
|| true discards Robot's exit status, and deleting the
first run destroys evidence of the original failure. A passing
merged report may be a valid derived state, but it cannot be used to
pretend the initial execution was clean.
Repair: capture each return code, preserve both raw outputs, run the rerun only under an explicit policy, merge into a third directory, and let the release gate distinguish first-pass success from pass-after-rerun.
8. Failure mode: include/exclude/skip semantics are conflated
If a command changes from --exclude quarantined to
--skip quarantined, selected counts and report
semantics change even though the quarantined test bodies still do
not execute. That can be correct, but it is a policy change. Review
the diff as an execution-contract change, not a cosmetic flag
refactor.
9. Security: commands and profiles are evidence surfaces
Shell history, CI logs, argument files, robot.toml, and
Robot log messages are not secret vaults. Never place a real token
in --variable TOKEN:... in a copied command or
committed file. Even Robot Framework 7.4 Secret values mask specific
Robot surfaces; they do not encrypt files or guarantee that an
external library will not log a value. Keep this chapter's values
synthetic.
10. Diagnose the correct performance layer
| Layer | Symptom | Relevant evidence |
|---|---|---|
| Parsing/import | Run is slow before first test | Source count, import timing, parse selection |
| Robot keyword | Specific keyword consumes time | log/output keyword timestamps |
| External system | Waiting on browser/API/database | External/library telemetry |
| Logging/output | Huge result files / slow HTML generation | Artifact sizes, log level, keyword volume |
| Rerun | Repeated execution cost | Original/rerun commands and counts |
| Pabot/CI later | Worker queue/startup/contention | Worker/shard evidence, not tag counts alone |
11. Least-destructive rerun
After repairing selection, rerun the smallest slice that proves the correction. A zero-selection bug needs a selection-focused run, not the full suite. A profile output-dir bug can be diagnosed with RobotCode profile inspection plus one dry/simple test. Preserve the failing artifact before any new run.
Knowledge check
A tag expression unexpectedly selects zero tests. Should you add --runemptysuite immediately?
No. Preserve the command and inspect tag membership/expression semantics first. --runemptysuite can be appropriate for intentional empty slices, but it should not hide a selection defect.
Why does changing PYTHONPATH not fix an argument file whose
tests path resolves from the wrong cwd?
PYTHONPATH controls module/library search. The data-source path is a command-line filesystem argument. Fix the working-directory/path contract instead.
What is the evidence defect in keeping only a passing merged output?
It destroys or obscures the original failure and makes pass-after-rerun indistinguishable from first-pass success.
How do you prove whether RobotCode influenced a run?
Identify the actual launcher, RobotCode version, selected profile(s), loaded configuration files/resolved profile, and compare that with the final Robot options/output paths.
Summary and bridge
Selection failures are usually configuration/identity failures, not assertion failures. Lesson 5 combines the chapter into a checkpoint where you predict three slices, force one controlled failure, rerun/merge it, and produce an evidence packet plus precedence contract.
References and version anchors
- Robot Framework 7.4.2 User Guide — CLI option syntax, name/tag selection, argument files, reruns, skip/exclude semantics, and result post-processing.
- Robot Framework 7.4.2 on PyPI — stable release and Python compatibility anchor.
- RobotCode CLI reference — optional profile inspection and execution commands.
Keep the academy open
Support free, practical DevOps education.
Every lesson is designed to remain readable in a browser, downloadable from GitHub, and usable without a paid learning platform. Contributions help expand and maintain the curriculum.
0x716c4Ab160C4B66F31a28AE2448BfF68fc3a2ef0
Send only Ethereum/ERC-20 compatible assets to this
address.