Can a Gatling run decide pass or fail on its own in a CI pipeline, and at what point in the run is that verdict computed?
answer
- The run judges itself, once, at the end
- Assertions attach to setUp
- Evaluated after the simulation finishes
- Exit 2 for assertions failed
basics
~20 sYes. Assertions declared on setUp are all evaluated after the simulation has finished; if at least one fails the simulation fails and the process exits 2. A run that declares no assertions exits 0, because it judged nothing.
solid answer
~40 sGatling carries its own pass rule. You attach `assertions(...)` to `setUp`, and every assertion is evaluated **after** the simulation finishes, against statistics for the whole run. If at least one fails, the simulation fails and the launcher exits with status **2**; `0` means success and `1` is what the launcher returns for invalid command line arguments — though a crash that escapes `main` also ends the JVM with 1 — so a pipeline that only checks for a non-zero exit still needs to know that 1 is never a load verdict. Two consequences follow from the verdict being computed after the run: a doomed run is not stopped early by its own pass rule, and a simulation that declares no assertions at all always exits 0 no matter how badly it went.
go deeper
Be ready to say that Gatling can pass or fail a run by itself and that the criteria are written in the simulation rather than in the pipeline.
Be ready to explain that assertions are evaluated after the run over whole-run statistics, and to name what each of the three exit statuses means.
Be ready to describe how you would prove a green pipeline stage is actually capable of failing, and how you would keep an argument error from being filed as a regression.
Be ready to weigh a post-run verdict against a continuously evaluated one for your organisation, including who is allowed to change a pass rule and how a rule change is reviewed.
A load generator earns its place in a pipeline by answering one question without help: did this run pass? Gatling answers it natively, and the shape of that answer — when it is computed and what it is computed over — is more important than the fact that it exists. ## How the verdict is declared The pass rule is attached to the same `setUp` call that registers the load profile, so the criteria live in the simulation source next to the load they judge: ```kotlin setUp(browse.injectOpen(atOnceUsers(1))) .assertions( global().responseTime().percentile3().lt(800), global().successfulRequests().percent().gt(99.0) ) ``` Each assertion is a chain that picks a **scope**, a **statistic**, a **metric** and a **condition**. The documentation states the timing without ambiguity: all assertions are evaluated after running the simulation, and if at least one fails, the simulation fails. ## What the process exits with Gatling's launcher defines exactly three status codes: | Code | Meaning | |---|---| | `0` | success — either every assertion passed, or none were declared | | `1` | invalid command line arguments — and, in practice, any crash | | `2` | assertions failed | Only `2` is exhaustive. Gatling logs `Run crashed` and rethrows rather than returning a status code, so a failure in configuration loading, in the simulation's constructor or during the run itself escapes `main` and the JVM terminates on an uncaught exception — which is also exit 1. Read `1` as "the process failed before producing a verdict" rather than as "the simulation never started"; only the log tells you which. That distinction is worth carrying into a pipeline. A job that treats "non-zero" as "performance regression" will report a mistyped flag, or a crashed run, as a failed load test. A job that reads `2` specifically knows the run executed and was judged unsatisfactory. The other half of the contract is the silent case. **A simulation that declares no assertions exits 0.** It did not pass; it simply never judged anything. A pipeline stage that runs a simulation with no `assertions(...)` chain is green by construction and proves nothing, and that is a real failure mode because the run still produces a report full of numbers that look like evidence. ## The consequence of judging after the run Because the whole gate is a post-run computation over consolidated statistics, three things follow: 1. **The pass rule cannot stop a run.** A simulation that is failing its latency target from the first minute still runs to the end of its profile. Bounding the wall-clock cost of a bad run is a separate concern from the pass rule, handled by the run's own duration limits rather than by the assertions. 2. **The verdict is over the whole run.** Statistics are consolidated across everything the run recorded, so a warm-up segment or a deliberate overload tail is inside the numbers being judged unless the simulation was designed to keep them out. Deciding what a pass rule should assert, and over which window, is performance-testing judgement rather than a Gatling feature. 3. **There is exactly one verdict per run.** One process, one exit status. If a profile is executed on several machines, each machine judges only what it saw and produces its own status. ## Where this sits among the alternatives This is one of the differences that actually decides a tool choice, so state it at the right altitude. Load generators differ on **whether** they carry a gate at all and on **when** they evaluate it: * Gatling declares the gate inside the simulation and evaluates it once, after the run, producing a dedicated exit status. No extra tooling is required for a pipeline to fail on it. * Some generators evaluate their criteria continuously as the run proceeds, which lets a breach abort a run early, at the cost of a verdict that depends on when it was checked. * Some generators ship no native gate at all, so a pipeline must score the results file itself with a separate step and own the correctness of that step. Name the contrast; do not borrow the numbers. Another tool's non-zero exit code is its own, and assuming Gatling shares it is a small mistake that produces a pipeline which silently never fails. ## Answering it well The complete answer is three clauses: the gate is declared on `setUp` with `assertions(...)`; it is evaluated after the simulation finishes, over whole-run statistics; and a failure exits `2` while an absent gate exits `0`. Adding the "no assertions means green" caveat unprompted is what separates someone who has wired this into a pipeline from someone who has read the reference page.
- A Gatling stage in CI has been green for months. What would make you suspect it is not actually judging anything?Check whether the simulation declares an assertions chain at all. With no assertions the launcher exits 0 unconditionally, so the stage passes regardless of the results, while still producing a report that looks like evidence. The cheap confirmation is to tighten one assertion deliberately and prove the stage can turn red.
- Your pipeline treats any non-zero exit from a Gatling run as a performance regression. What does that get wrong?It conflates 1 with 2. Only 2 means the run completed and its assertions failed — that is the regression signal. 1 is what the launcher returns for invalid command line arguments, but it is not exclusive to them: Gatling logs the crash and rethrows rather than returning a status code, so an uncaught failure escapes `main` and the JVM exits 1 as well — a configuration or constructor failure, a feeder that threw, a `crashLoadGenerator` block. So 1 means the process failed before producing a verdict, which may or may not mean the simulation ran; read the log rather than filing every 1 as an operator mistake.
- Why can Gatling's gate not abort a run that is clearly going to fail?Because every assertion is evaluated after the simulation finishes, against consolidated statistics for the whole run. Until the run ends there is no value to compare. Limiting how long a bad run costs you is a separate mechanism, expressed as a bound on the run's duration rather than as a pass rule.
saying these in an interview costs you the question
- Assuming a simulation with no assertions still fails on bad results
- Expecting an assertion breach to abort the run mid-flight
- Reading exit 1 as a performance verdict, or as proof the simulation never ran
- Assuming another generator's failure exit code is the same value