Skip to main content
Glama

declare_run_expectations

Idempotent

Declare a run's pass/fail criteria at its start, before the outcome is known, then validate the closing success ping against them instead of letting the run grade itself.

Instructions

Commit, at the START of a run, to the criteria by which THAT RUN will be judged when it closes — before you can see how it turns out. This is how a run stops grading itself: once declared, a success ping whose body does not satisfy every declared criterion is recorded as a FAILED run with cause 'assertion', regardless of the exit code or what the ping claims. Call this right after your run's /start ping, before doing any work — see the assertions argument for the full, immutable contract, and get_ping_instructions' expectations_how_to for a worked example.

Input Schema

TableJSON Schema
NameRequiredDescriptionDefault
ridYesThe run id exactly as sent on this run's /start ping — the same rid used on every step and the terminal ping.
check_idYesMonitor UUID (from create_monitor or list_monitors).
assertionsYesThe run's complete set of expectations, declared ONCE at the start of the run -- criteria the ping BODY of THIS run's eventual success ping must satisfy when the run closes, checked instead of letting the run grade itself. IMMUTABLE: a second call for the same rid is rejected with a conflict error and the first declaration stands unchanged -- there is no way to edit, add to, or replace it once made, so decide the whole set before you start work. Declaring nothing is allowed and always has been: simply never call this tool for a run, and the monitor's own check-level assertions (if any) stay in force unchanged. INCLUDE AT LEAST ONE POSITIVE CRITERION -- a 'contains', 'matches' or 'json_path' entry -- in every declaration. A declaration made ENTIRELY of 'not_contains' entries is self-satisfying on empty output: a run that produces nothing at all still passes, because there is nothing for the pattern to find. That is precisely the evasion this feature exists to close, so a purely negative declaration defeats its own purpose. A 'matches' entry only counts as positive if its pattern REJECTS an empty body: '.*', '(?s).*' and '^$' all accept one and are validated as perfectly legal patterns, so a declaration resting on one of those is no better than a purely negative declaration. Supply a JSON ARRAY as a string, e.g. '[{"kind":"json_path","path":"result.rows_processed","op":"gt","value":"0"}]'. Fields per entry: kind (required), value, path, op -- no name; a run's declared criteria have none, unlike a monitor's own output assertions. kind is one of 'contains' (body contains value as a substring), 'not_contains' (body does not contain it), 'matches' (body matches value as a Go RE2 regexp, max 1000 bytes), or 'json_path' (parse the body as JSON, read the value at path, compare it against value with op). contains/not_contains/matches require value; json_path requires path and op. path is a DOTTED path only ('a.b.c') -- the query syntax of a real JSONPath library ('[', '*', '$') is rejected. op is one of 'eq', 'ne', 'gt', 'gte', 'lt', 'lte'. At most 20 assertions per run. A malformed entry (uncompilable regexp, a path carrying query syntax, an unknown kind or op) is rejected before anything is written, and nothing is stored if any entry fails.

Schema Changelog

Changes observed during successful MCP inspections. Dates show when Glama detected each change.

  1. First observed

TDQS

A4.6/5.0
Behavior5/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

The annotations carry only coarse hints (idempotentHint=true, readOnlyHint=false), but the description and the assertions contract disclose the full behavioral profile: grading is taken over from the monitor, failures are recorded as cause 'assertion' regardless of exit code, declarations are immutable with a conflict error on second call, malformed entries are rejected before anything is written, and purely negative declarations are flagged as self-defeating. The second-call conflict behavior refines rather than contradicts the idempotentHint — it specifies precisely what idempotency means here, so the agent gets accurate expectations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The main description is three sentences with zero waste: the commitment semantics in the first, the grading effect in the second, and call timing plus pointers to the contract and worked example in the third. It is front-loaded with the most decision-relevant facts before any deferral to the schema or sibling documentation.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a high-complexity commit tool with no output schema, the definition covers when to call, what it does, the failure consequence, immutability, validation-before-write, and the evasion edge cases, while deferring the parameter contract to the schema and the worked example to get_ping_instructions. The only real gap is that a successful call's return value is never described, which is minor for a side-effect commit operation whose behavior is otherwise fully specified.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%: rid and check_id are self-explanatory, and the assertions parameter is exhaustively documented with kinds, ops, dotted-path restrictions, the 20-entry cap, the positive-criterion requirement, and a concrete JSON-array-as-string example. The main description adds only routing context ('see the assertions argument for the full, immutable contract') plus the grading consequence, which is useful framing but not new parameter-level meaning — so the high-coverage baseline of 3 is appropriate.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description states a specific verb ('Commit') and a precise resource (the criteria by which the run will be judged), immediately followed by the observable consequence: the run stops grading itself and unsatisfied criteria produce a FAILED run with cause 'assertion'. It is unmistakably distinct from every sibling tool, none of which declare run expectations, and the '/start ping' timing frames it within a specific lifecycle.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Explicit timing guidance is given ('Call this right after your run's /start ping, before doing any work') and an explicit when-not-to-use is stated: 'simply never call this tool for a run, and the monitor's own check-level assertions (if any) stay in force unchanged' — naming the built-in alternative of doing nothing. It also routes the agent to get_ping_instructions' expectations_how_to for a worked example, leaving no ambiguity about when or how to invoke it.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/tp322d/lastping-app'

If you have feedback or need assistance with the MCP directory API, please join our Discord server