# Declare run parameters

Agent Mission Control developer docs > Bring your own agent

> Declare the inputs a run accepts so AMC can validate every start, render the Run now form, and route runs to the right person.

**Before you start:** A registration you can edit: Tenant Admin, Department Manager, or Agent Manager (agents only).

The input contract is the list of parameters a run accepts. You declare it on the registration, under **Input contract**, or as `inputContract` in the registration API. AMC uses it in three places: to validate every start, to build the **Run now** form, and to map webhook fields onto inputs.

`inputContract`
```json
{
  "parameters": [
    { "name": "invoiceId", "type": "string", "required": true,
      "format": "INV-####", "description": "Invoice number" },
    { "name": "amountLimit", "type": "number", "required": false },
    { "name": "region", "type": "enum", "required": true,
      "enumValues": ["emea", "amer", "apac"] },
    { "name": "ownerEmail", "type": "string", "required": false, "role": "assignee",
      "description": "Who approves the summary" }
  ],
  "metadata": { "team": "finance-ops" }
}
```

| Field | Meaning |
| --- | --- |
| `name` | Required. The key the value arrives under in `inputs`. |
| `type` | `string`, `number`, `boolean`, `date` or `enum`. Any other label is treated as `string`. |
| `required` | A start without a non-blank value is refused. |
| `format` | A hint. **Run now** shows it as the field's placeholder. |
| `description` | Shown under the field in **Run now**, and as the placeholder when there is no `format`. |
| `default` | Documentation only. AMC does not fill it in, so apply it in your agent when the input is absent. |
| `enumValues` | For `enum`: the allowed values. **Run now** shows a picker. |
| `role` | What the parameter means to AMC. `assignee` is the only role AMC understands; other values are ignored. |
| `metadata` | Optional non-secret key/value pairs stored with the contract. |

## Validation

AMC validates the inputs before it calls your endpoint. Workflow default inputs are all-or-nothing: they apply only when the start supplies no inputs at all, and supplying any input switches every default off. A blank value counts as absent.

| Type | Accepted |
| --- | --- |
| `number` | A decimal number in invariant format, such as `1200` or `1200.50`. |
| `boolean` | `true` or `false`, any case. |
| `date` | An ISO 8601 date or date-time, such as `2026-10-17`. |
| `enum` | One of `enumValues`, compared without case. With no `enumValues`, any value. |
| `string` | Anything. |

`400 when inputs fail validation`
```json
{
  "title": "Invalid request",
  "status": 400,
  "detail": "One or more run inputs are invalid.",
  "error": "run_input_validation_failed",
  "errors": [
    { "parameter": "invoiceId", "code": "required_missing", "message": "Parameter 'invoiceId' is required." },
    { "parameter": "region", "code": "enum_mismatch", "message": "Parameter 'region' must be one of: emea, amer, apac." }
  ]
}
```

The error codes are `required_missing`, `type_mismatch` and `enum_mismatch`. **Run now** marks the failing fields from this list.

## No parameters

Leave the contract empty for a resource that gathers its own inputs, such as one that always works on yesterday's data. It can then be scheduled freely. A resource with any required parameter needs those inputs at every start, so a schedule can't run it unless it supplies them.

## Route runs to a person

Mark the parameter that names the person a run is about with `"role": "assignee"`. Its value must be an email. At run start AMC resolves it to a user in your tenant and makes them the run's assignee, so the run's interventions go to them. A missing value or an unknown email falls back to the workflow's normal routing, and never fails the run.

> **Note:** The registration form doesn't offer `role`. Set it through the registration API (`POST` or `PUT /api/registrations`). Your agent can also declare the assignee itself mid-run. See [Ask a person mid-run](https://www.agentmissioncontrol.ai/developers/byo-human-in-the-loop/).

## Webhook fields

With a contract declared, a webhook body's top-level fields map onto inputs by name, so callers can send named values.

`Webhook body`
```json
{
  "invoiceId": "INV-1042",
  "amountLimit": 5000,
  "region": "emea",
  "runName": "invoice-INV-1042"
}
```

`inputs your agent receives`
```json
{
  "invoiceId": "INV-1042",
  "amountLimit": "5000",
  "region": "emea"
}
```

`runName` and `assigneeId` are reserved: AMC uses them to name the run and set its assignee, and never forwards them.

> **Important:** AMC reads the contract only from the registration. Even if your endpoint publishes one (amc_sdk serves it at `GET /workflows/{id}`), enter the same contract when you register.

## Related

- [Start and cancel a run](https://www.agentmissioncontrol.ai/developers/byo-start-a-run/)
- [Register your agent: the technical reference](https://www.agentmissioncontrol.ai/developers/register-your-agent/)
- [Ask a person mid-run](https://www.agentmissioncontrol.ai/developers/byo-human-in-the-loop/)

---
Source: https://www.agentmissioncontrol.ai/developers/byo-input-contract/ · Last updated 2026-10-21 · Full index: https://www.agentmissioncontrol.ai/llms.txt
