Docs Step Execution Modal

Step Execution Modal

When a TCM test case is opened in step-by-step mode — or a Test Plan reaches a manual approval item that needs a human verdict — Mockarty opens a step execution modal. This page documents what the modal does and the API behind it.

What the modal looks like

The modal has two panes:

  • Left — every step in the run, with a coloured status badge.
  • Right — the active step’s action, expected result, output fields, and a comment editor.

Below the active step there are four outcome buttons (Pass, Fail, Skip, Block) plus Previous / Next for navigation. Choosing an outcome records the verdict, captures any outputs, and auto-advances to the next non-terminal step.

Comments support Markdown. They are sent to the server together with the chosen outcome — there is no separate auto-save round-trip, so a fast click on Pass can never race a pending comment save.

Outcomes

Status Meaning
Pending Not started yet.
Running The step is currently executing.
Awaiting manual The runner has paused — a human verdict is needed.
Passed The step met its expected result.
Failed The step did not meet its expected result.
Skipped The step was deliberately bypassed.
Blocked Mockarty records this as Failed with a [blocked] marker on the comment, so dashboards differentiate “we tried and it didn’t work” from “we couldn’t try because something else got in the way”.

Outputs

Each step can publish named output values that later steps may reference. Outputs are simple key → value pairs, stored as JSON on the step row.

The intended placeholder syntax for downstream steps is:

${steps.<step-uid>.<output-name>}

For example, a “Login” step that publishes a token output:

${steps.login.token}

The storage is in place today (the resolve API accepts an extracted map). Substituting those values into the next step’s text is not supported; read them from the step snapshot and feed them into your own scripts.

API

The modal is driven by the existing TCM case-run endpoints. You can integrate from your own scripts.

Base path: /api/v1/namespaces/{namespace}/tcm/case-runs/{run_id}.

Method Path Purpose
GET / Snapshot the run and all step rows.
GET /stream Server-sent events stream for live updates.
POST /steps/{step_uid}/resolve Atomic terminal transition: resolution + comment + outputs.
POST /pause Pause the case run.
POST /resume Resume a paused run.
POST /cancel Cancel an in-flight run.
POST /rerun Start a fresh run that supersedes this one.

Snapshot

curl https://mockarty.example.com/api/v1/namespaces/{namespace}/tcm/case-runs/{run_id} \
  -H "Authorization: Bearer $MOCKARTY_API_TOKEN"

The response is the run summary plus a steps array. Each step row carries its stepUid, current status, the latest resolutionNote (your comment), and bindingsExtracted (your outputs).

Record an outcome with a comment and outputs

curl -X POST https://mockarty.example.com/api/v1/namespaces/{namespace}/tcm/case-runs/{run_id}/steps/{step_uid}/resolve \
  -H "Authorization: Bearer $MOCKARTY_API_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{
        "resolution": "pass",
        "note": "Logged in as admin@example.com.",
        "noteFmt": "markdown",
        "extracted": {"token": "abc-123"}
      }'

resolution accepts pass, fail, skip (long-form passed, failed, skipped also accepted). noteFmt is markdown (default) or plain. extracted is the per-step output map.

If the run or step is already in a terminal state the call returns 409 Conflict with code: step_or_run_terminal so your client can handle the no-op cleanly.

Permissions and isolation

  • Snapshot + stream require test_case:read on the namespace.
  • Resolve, pause, resume, cancel, rerun require test_case:write.
  • All endpoints are namespace-scoped; a user from one namespace cannot read or mutate another namespace’s case runs.
  • Every state-changing call is recorded in the audit log under one of tcm_case_step_resolve, tcm_case_run_pause, tcm_case_run_resume, tcm_case_run_cancel, tcm_case_run_rerun.

Opening the modal from custom code

The modal is exposed on the global window object so any page in the admin UI can open it:

window.openStepRunModal({
  runId:     '11111111-2222-3333-4444-555555555555',
  namespace: 'acme',
  title:     'Acceptance run',
  steps: [
    {stepUid: 'login',  title: 'Sign in',       description: 'Open /login and submit credentials.', expected: 'Dashboard loads.', outputs: ['token']},
    {stepUid: 'fetch',  title: 'Fetch profile', description: 'GET /profile with ${steps.login.token}.'},
    {stepUid: 'logout', title: 'Sign out'},
  ],
  onComplete: (rows) => console.log('all done', rows),
});

Call window.closeStepRunModal() to close it programmatically.

The steps array is the caller’s view of the case definition; the modal hydrates the per-step status, comment, and outputs from the server snapshot when it opens. Your steps provide the static metadata (title, description, expected, declared outputs) — the runtime state always comes from the server-side run snapshot.