Skip to content

The public report of a run — no account

GET
/public/report/{token}
curl --request GET \
--url https://beta-api.plune.ai/public/report/example

What anyone who holds the address sees of a run (#1263), with no credential and no cookie, set or read: its title, environment and labels, when it started and finished, the six counters (passed, failed, broken, blocked, skipped, muted), the sub-statuses its results carry, the time it took and what it cost (null for a run nobody timed or priced), and per test its title, status, sub-status and time — and, in a run with configurations, the label of its combination (#1251) — (at most 1000, then testsTruncated). Nothing else: no ids, no people, no CI address, branch or commit, no error text, no files — and the page has no write element. Off, revoked, never made, malformed and a run in the Bin are ONE answer, the same 404 with the same body. A link ends (#1264): after expiresAt it answers 410 with { error, code: "expired" }. A link may have a password, sent in the X-Report-Password header (never in the address, which is logged and shared; no cookie is set or read): none sent is 401 password_required, a wrong one 401 wrong_password. The password is checked before the date. A token nobody holds is 404 whatever is sent, with no derivation spent on it; the difference between 404 (no link), 401 (a password is set) and 200 or 410 (none is) is accepted, because the token is 256 random bits and only someone who already holds a valid one can tell them apart. Wrong passwords are counted per token (10 in 15 minutes, slots taken before the check so parallel requests cannot exceed it); past that every attempt, the right one too, is 429 until the window frees. A client may send 30 requests a minute with a password, and at most 2 derivations run at once in a process: another is 429 with Retry-After: 1. Sent with Cache-Control: no-store, X-Robots-Tag: noindex, nofollow and Referrer-Policy: no-referrer. 120 a minute for a client address.

token
required
string

43 characters of base64url.

X-Report-Password
string

The report’s password, when it has one. Printable ASCII, at most 128 characters.

The report

Media type application/json
object
run
required
object
title
required
string | null
kind
required
string
environment
required
string | null
labels
required
Array<string>
startedAt
required
string format: date-time
finishedAt
required
string | null format: date-time
running
required
boolean
counts
required

Every status is present, zero included.

object
key
additional properties
integer
subStatuses
required
Array<object>
object
status
required
string
name
required
string
count
required
integer
durationMs
required
integer | null
costUsd
required
number | null
tests
required
Array<object>
object
title
required
string
status
required
string
subStatus
required
string | null
durationMs
required
integer | null
configuration

The combination the test ran in (#1251), as its label: «Firefox · macOS». Only in a run launched with configurations.

string
testsTruncated
required
boolean
Example generated
{
"run": {
"title": "example",
"kind": "example",
"environment": "example",
"labels": [
"example"
],
"startedAt": "2026-04-15T12:00:00Z",
"finishedAt": "2026-04-15T12:00:00Z",
"running": true
},
"counts": {
"additionalProperty": 1
},
"subStatuses": [
{
"status": "example",
"name": "example",
"count": 1
}
],
"durationMs": 1,
"costUsd": 1,
"tests": [
{
"title": "example",
"status": "example",
"subStatus": "example",
"durationMs": 1,
"configuration": "example"
}
],
"testsTruncated": true
}

A password is set and none was sent (code: password_required), or the one sent is wrong (code: wrong_password)

Media type application/json
object
error
required
string
Example generated
{
"error": "example"
}

No such report, or it is off or revoked

Media type application/json
object
error
required
string
Example generated
{
"error": "example"
}

The link has expired (code: expired)

Media type application/json
object
error
required
string
Example generated
{
"error": "example"
}

Rate limit exceeded, or too many wrong passwords for this token

Retry-After
integer