post_vouchers_by_id_verify

Changes data · you confirm first

Calls POST /api/vouchers/{id}/verify as the signed-in person · REST reference

Claim step 1 — take a scanned voucher for the caller's clinic

Transitions ISSUED → VERIFIED and records claimedByOrgId, which binds the voucher to the clinic that took it: from here on only that clinic may take the remaining claim steps, and approval pays it. ANY clinic may take ANY issued voucher — it is a bearer instrument, and the distributor or platform holding it has no say — so the clinic is the CALLER's own: an org in which the caller holds execute:TransitionVoucherCommand (hospital.vouchers.transition; a clinic's owner holds it, a member once the owner delegates it). A caller who holds it in one clinic sends no body; one who holds it in several names the clinic in orgId, which must be one of them. ONLY a clinic's own staff claim: platform staff are refused (403) — PFF approves and pays claims, it does not make them — and the DAL decides the same (platform authority does not stand in on the claim path). The write runs as the caller (their bearer is forwarded) in a compare-and-set, so the DAL's command gate pins the permission to that clinic and, of two clinics racing for one voucher, exactly one wins.

Arguments

ArgumentTypeDescription
idpathstring (uuid)requiredVoucher id.
bodyJSONobjectThe request body, as a JSON object. Its fields are listed below.

Fields of body

FieldTypeDescription
orgIdstring (uuid)The clinic taking the voucher. Needed only when the caller verifies for more than one clinic; it must be a clinic the caller may verify for.

Example call

A client sends this over the MCP session; Claude and other agents build it for you. The values are placeholders — the shape is real.

json
{
  "jsonrpc": "2.0",
  "id": 1,
  "method": "tools/call",
  "params": {
    "name": "post_vouchers_by_id_verify",
    "arguments": {
      "id": "11111111-1111-4111-8111-111111111111",
      "body": {
        "orgId": "11111111-1111-4111-8111-111111111111"
      }
    }
  }
}
Confirmation
The client shows the person the exact request and waits. Nothing runs until they tick Make this change. See Reading and changing.

Result

On success (HTTP 200) the tool returns one text item holding the API's JSON, pretty-printed.

The voucher after the transition, as the DAL's TransitionVoucher selection returns it — WITHOUT claimedByOrgId, the very field this call just wrote.

json
{
  "code": "string",
  "currency": "string",
  "expiresAt": 1,
  "id": "11111111-1111-4111-8111-111111111111",
  "state": "ACTIVE",
  "value": 1,
  "assignedToOrgId": "11111111-1111-4111-8111-111111111111",
  "batchId": "11111111-1111-4111-8111-111111111111",
  "issuedAt": 1,
  "issuedToEmail": "string",
  "issuedToPhone": "string",
  "maxPayout": 1,
  "procedure": "string",
  "replacedByVoucherId": "11111111-1111-4111-8111-111111111111"
}

Fields

FieldTypeDescription
assignedToOrgIdstring (uuid) | null
batchIdstring (uuid) | null
codestring
currencystring
expiresAtintegerEpoch MILLISECONDS.
idstring (uuid)
issuedAtinteger | nullEpoch MILLISECONDS.
issuedToEmailstring | null
issuedToPhonestring | null
maxPayoutinteger | nullCatalog face-value cap in CENTS.
procedurestring | null
replacedByVoucherIdstring (uuid) | nullThe voucher the DAL minted to replace this one in its batch, if any.
serviceTypestring | null
speciesstring | null
state"ACTIVE" | "APPROVED" | "ASSIGNED" | "AVAILABLE" | "CLAIMED" | "CREATED" | … (17 values)A voucher's lifecycle state, as the DAL's VoucherState enum names it.
valueintegerFace value in CENTS.
voidReasonstring | null

When it fails

A failed call returns isError: true with the API's message as text. A change the person declines, or lets time out, also comes back this way and nothing changes.

400

The caller verifies for more than one clinic and named none in orgId.

403

The caller may verify vouchers for no clinic, or for none named orgId, or belongs to the clinic without the permission to verify vouchers for it, or is platform staff — who approve claims and never make them (the message says which).

404

No such resource — or none this caller may see.

409

Another clinic has already accepted this voucher (including one that won a race for it a moment earlier), or its state cannot move to VERIFIED — it is not ISSUED.

What the model is shown

This is the tool exactly as the server lists it in tools/list. The description starts with the REST call it makes.

json
{
  "name": "post_vouchers_by_id_verify",
  "description": "POST /api/vouchers/{id}/verify — Transitions ISSUED → VERIFIED and records `claimedByOrgId`, which binds the voucher to the clinic that took it: from here on only that clinic may take the remaining claim steps, and approval pays it. ANY clinic may take ANY issued voucher — it is a bearer instrument, and the distributor or platform holding it has no say — so the clinic is the CALLER's own: an org in which the caller holds `execute:TransitionVoucherCommand` (`hospital.vouchers.transition`; a clinic's owner holds it, a member once the owner delegates it). A caller who holds it in one clinic sends no body; one who holds it in several names the clinic in `orgId`, which must be one of them. ONLY a clinic's own staff claim: platform staff are refused (403) — PFF approves and pays claims, it does not make them — and the DAL decides the same (platform authority does not stand in on the claim path). The write runs as the caller (their bearer is forwarded) in a compare-and-set, so the DAL's command gate pins the permission to that clinic and, of two clinics racing for one voucher, exactly one wins.\n\nThis changes data. The person is asked to confirm it before it runs, and nothing happens if they decline.",
  "inputSchema": {
    "type": "object",
    "properties": {
      "id": {
        "type": "string",
        "description": "Voucher id."
      },
      "body": {
        "type": "string",
        "description": "The JSON request body: { orgId: string (The clinic taking the voucher.) }"
      }
    },
    "required": [
      "id"
    ]
  },
  "annotations": {
    "readOnlyHint": false,
    "destructiveHint": true,
    "idempotentHint": false,
    "openWorldHint": false
  }
}