> ## Documentation Index
> Fetch the complete documentation index at: https://docs.oneshotagent.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Events, Questions and Results

> Send an event to a case, have a case ask a named person and wait, and receive its result at your own address

## Overview

<Note>Cases are in limited preview. Everything on this page applies to a goal on an account enabled for cases.</Note>

A case starts with something that happens outside OneShot (a new freight invoice, a failed run), waits on people who are not you (a carrier's billing desk, an attorney, a reviewer), and ends with a result your own system writes down. OneShot holds no access to your system: it sends you the result, and you write it.

## Send an event

`POST /v1/compute/{goalId}/events` with a signed **write proof** (or an access token).

```json theme={null}
{ "event_id": "inv-1001", "case_key": "SHIPMENT-8841", "task": "Freight invoice 1001: 1,240.00 USD for shipment 8841" }
```

* `event_id`: your id for the event. Sending the same id twice is one event.
* `case_key`: the case it is about. It opens that case, or wakes it if it is open; a finished case is reopened. A second invoice for the same shipment reaches the same case. Leave it out to send the event to the goal's root.
* `task`: what happened, with everything the case needs.
* `budget_usdc`, `step_limit`: for a case this event opens.

Answers `202` with `{ "target": "case" | "root", "case_key", "outcome": "created" | "already_open" | "reopened" | "sent_to_root" }`.

## Replies reach the case that asked

An inbound email, text or call result wakes the session that sent the message it answers, and no other goal. Mail that follows nothing a case sent goes to the root of the agent's newest goal on the loop.

## A case asks a named person

The case calls `ask_person` with a person's name and address, a question and a kind:

* `answer`: a reply is the answer. It is written on the case's record with who, when, `via: "reply"` and the message it came from (`inbound_email:<id>`).
* `approval`: anything that releases an action (an amount, a booking, a merge). The person is sent a signed, single-use link that expires, which opens a page showing what is being approved and two buttons. **Only the click counts.** A reply to the same email, even one that says "approved", is told to the case and releases nothing. The click is written on the record with who, when, `via: "link"` and what the person was shown (`shown`, `shown_hash`).

A question can be chased (`chase_after_seconds`, up to three reminders) and has a deadline (`deadline_seconds`, default 7 days) at which the case is told to escalate. A used, expired or altered link is refused.

## Results out

Give the goal an address when you create it:

```json theme={null}
{ "params": { "result_webhook_url": "https://example.com/oneshot/results" } }
```

The URL must be public HTTPS. When a case reaches a result it calls `deliver_result`, and OneShot POSTs it to that address:

```json theme={null}
{ "event": "case.result", "goal_id": "…", "case": "SHIPMENT-8841", "result": { "amount_usd": 1180 }, "approval": { "ask_id": "…", "who": "Rae", "when": "…", "via": "link" }, "delivery_id": "…", "attempt": 1 }
```

The body is signed in `X-OneShot-Signature` (`t=<unix seconds>,v1=<hex HMAC-SHA256 of "<t>.<body>">`). Read the secret at `GET /v1/compute/{goalId}/result-webhook`.

If the case asked for an approval, only a result equal to the approved one is sent; anything else is withheld. A failed delivery is retried with a growing delay and gives up after six attempts. Every attempt shows on the case.

## Read a case

`GET /v1/compute/{goalId}/cases/{key}` returns the case's record, `decisions`, `asks` (each with `status`, `chases`, `deadline_at`, `escalated_at`) and `deliveries` (each with `status`, `attempts`, `last_error`, `next_attempt_at`).


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.