Skip to content

How to isolate tests in a test set with precondition and recovery hooks

A test set runs its tests in order, and — this surprises people — each test runs in its own fresh browser. Cookies and local storage from one test don’t carry into the next; that’s true in both modes. (A journey that should share a session — log in, then create, then delete — belongs in a single test, where steps share one browser.)

So what does independent mode add over the default sequential mode? Two things: per-test hooks — a setup test that runs before each test (a “precondition”) and a teardown test that runs after (a “recovery”) — and retries. The hooks mirror BeforeEach / AfterEach from xUnit-style frameworks: use a precondition to put every test into a known state (freshly logged in, freshly seeded), and a recovery to clean up after, even when the test failed.

  • Every test needs the same starting state — a freshly logged-in user, a freshly seeded database. A precondition guarantees it before each one, instead of hoping the test ahead of it left things right.
  • You want automatic cleanup after each test, even on failure — a recovery test undoes whatever the test created.
  • A flaky test should retry instead of failing the run on the first miss.

If your tests need none of that, sequential mode is simpler. The cost of independent mode isn’t a fresh browser — you get one either way — it’s the extra executions: each precondition and recovery is a real run that counts against your quota.

  1. Open the test set’s settings

    On the Runner page, find the test set in the picker. Click the menu next to its name and choose Settings….

  2. Switch the execution mode

    Pick Independent instead of Sequential. The dialog grows two new fields and a checkbox.

  3. Pick a precondition test (optional)

    Choose a test from the same project that should run before each test in the set. A typical pick is a Login test — every test starts with a fresh logged-in session.

    Leave it as None if your tests don’t need shared setup.

  4. Pick a recovery test (optional)

    Choose a test that should run after each test, regardless of whether the main test passed or failed. Common picks are Logout, or a test that deletes any data created during the run.

    Recovery runs even when the main test fails — that’s the point. The next iteration starts from a known-clean state instead of inheriting the dirty state the failure left behind.

  5. Save

    The next time you run this set, Marriska will:

    • Run the precondition test (if set)
    • Run the main test
    • Run the recovery test (if set)
    • Repeat for the next test in the set

Each test’s step list includes the steps from the precondition and recovery (when configured). Hook steps are tagged in the event stream (with a hook_phase marker), but dedicated Setup and Teardown sections in the report UI aren’t implemented yet. The main test’s pass/fail status is unaffected by hook failures — a recovery that fails is logged but doesn’t fail the iteration.

The settings dialog also has a Run iterations in parallel option for parameterized tests in independent mode.

When it does activate, parallel iterations will be capped by your org’s plan limit — see parallel executions on the plan tiers page.

Underneath the parallel checkbox is a Retry failed tests counter with + / buttons. Set it from No retries (default, capped at 5 retries max).

When set, the runner watches each test’s outcome. If the main test fails AND retries remain, it:

  1. Runs the recovery hook (always, even on failure — see above).
  2. Runs the precondition hook again (fresh state).
  3. Re-runs the main test.
  4. Decrements the retry budget. Repeats until the test passes or the budget is exhausted.

The final status reported on the run is whichever attempt the test ended on — pass on attempt 3 of 3 still counts as pass.

The retry counter is only available in independent mode. A clean retry leans on the hooks: the recovery test undoes the failed attempt’s side effects and the precondition re-establishes a known state before the next try. Sequential mode has no hooks, so there’s nothing to make a retry clean — we don’t expose the control there.