API reference
Webhooks API
Register HTTPS endpoints for signed lifecycle events and inspect their deliveries.
- List webhooks:
GET /v1/webhooks - Create a webhook:
POST /v1/webhooks - Get a webhook:
GET /v1/webhooks/{webhook_id} - Change a webhook:
PATCH /v1/webhooks/{webhook_id} - Delete a webhook:
DELETE /v1/webhooks/{webhook_id} - Rotate a webhook secret:
POST /v1/webhooks/{webhook_id}/rotate-secret - List webhook deliveries:
GET /v1/webhooks/{webhook_id}/deliveries
List webhooks
GET /v1/webhooks
- API key:
Authorization: Bearer vmy_…with presetfull_access. - Browser session: the
vmyard_sessioncookie. - Who: Owner or Admin.
Parameters
| Name | In | Type | Required | Description |
|---|---|---|---|---|
limit | query | integer | No | |
cursor | query | string (uuid) | No | |
X-Organization-ID | header | string (uuid) | No | Organization context. Required with a browser session. Optional with an API key, which fixes the organization; when sent it must match. |
Responses
| Status | Description | Body |
|---|---|---|
200 | — | WebhookPage |
401 | Not signed in, or the API key is malformed, expired, or revoked (unauthenticated, invalid_api_key). | ProblemDetails |
403 | A role other than owner/admin, or an API key without full_access | ProblemDetails |
404 | Not found in this organization (resource_not_found). | ProblemDetails |
curl "$VMYARD_API_URL/v1/webhooks" \
-H "Authorization: Bearer $VMYARD_API_KEY"{
"items": [
{
"created_at": "2026-10-12T05:51:01Z",
"created_by": "6f1c2d3e-4b5a-4c7d-8e9f-0a1b2c3d4e5f",
"enabled": false,
"events": [
"machine.ready"
],
"id": "6f1c2d3e-4b5a-4c7d-8e9f-0a1b2c3d4e5f",
"name": "ci",
"organization_id": "6f1c2d3e-4b5a-4c7d-8e9f-0a1b2c3d4e5f",
"secret_rotated_at": "2026-10-12T05:51:01Z",
"updated_at": "2026-10-12T05:51:01Z",
"url": "https://hooks.example.com/vmyard"
}
],
"next_cursor": "6f1c2d3e-4b5a-4c7d-8e9f-0a1b2c3d4e5f"
}Create a webhook
POST /v1/webhooks
- API key:
Authorization: Bearer vmy_…with presetfull_access. - Browser session: the
vmyard_sessioncookie and thex-csrf-tokenheader. - Who: Owner or Admin.
Parameters
| Name | In | Type | Required | Description |
|---|---|---|---|---|
X-Organization-ID | header | string (uuid) | No | Organization context. Required with a browser session. Optional with an API key, which fixes the organization; when sent it must match. |
Request body (application/json, CreateWebhookRequest)
| Field | Type | Required | Description |
|---|---|---|---|
events | WebhookEventDto[] | Yes | at least 1 items. |
name | string | Yes | 1–64 characters. |
url | string | Yes | https on port 443, without credentials or a fragment, naming a public host. Redirects are never followed. at most 2048 characters. |
enabled | boolean | No | default true. |
Responses
| Status | Description | Body |
|---|---|---|
201 | The signing secret is returned only in this response | WebhookSecretDto |
401 | Not signed in, or the API key is malformed, expired, or revoked (unauthenticated, invalid_api_key). | ProblemDetails |
403 | CSRF failure, a role other than owner/admin, or an API key without full_access | ProblemDetails |
404 | Not found in this organization (resource_not_found). | ProblemDetails |
409 | The organization already has 10 endpoints | ProblemDetails |
422 | Invalid request (invalid_request); field_errors names the fields. | ProblemDetails |
503 | webhooks_unavailable: no secret keys are configured, and secrets are never stored in plaintext | ProblemDetails |
curl -X POST "$VMYARD_API_URL/v1/webhooks" \
-H "Authorization: Bearer $VMYARD_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"name": "ci",
"url": "https://hooks.example.com/vmyard",
"events": [
"machine.ready",
"machine.error"
]
}'{
"secret": "whsec_…",
"webhook": {
"created_at": "2026-10-12T05:51:01Z",
"created_by": "6f1c2d3e-4b5a-4c7d-8e9f-0a1b2c3d4e5f",
"enabled": false,
"events": [
"machine.ready"
],
"id": "6f1c2d3e-4b5a-4c7d-8e9f-0a1b2c3d4e5f",
"name": "ci",
"organization_id": "6f1c2d3e-4b5a-4c7d-8e9f-0a1b2c3d4e5f",
"secret_rotated_at": "2026-10-12T05:51:01Z",
"updated_at": "2026-10-12T05:51:01Z",
"url": "https://hooks.example.com/vmyard"
}
}Get a webhook
GET /v1/webhooks/{webhook_id}
- API key:
Authorization: Bearer vmy_…with presetfull_access. - Browser session: the
vmyard_sessioncookie. - Who: Owner or Admin.
Parameters
| Name | In | Type | Required | Description |
|---|---|---|---|---|
webhook_id | path | string (uuid) | Yes | |
X-Organization-ID | header | string (uuid) | No | Organization context. Required with a browser session. Optional with an API key, which fixes the organization; when sent it must match. |
Responses
| Status | Description | Body |
|---|---|---|
200 | — | WebhookDto |
401 | Not signed in, or the API key is malformed, expired, or revoked (unauthenticated, invalid_api_key). | ProblemDetails |
403 | A role other than owner/admin, or an API key without full_access | ProblemDetails |
404 | Not found in this organization (resource_not_found). | ProblemDetails |
curl "$VMYARD_API_URL/v1/webhooks/$WEBHOOK_ID" \
-H "Authorization: Bearer $VMYARD_API_KEY"{
"created_at": "2026-10-12T05:51:01Z",
"created_by": "6f1c2d3e-4b5a-4c7d-8e9f-0a1b2c3d4e5f",
"enabled": false,
"events": [
"machine.ready"
],
"id": "6f1c2d3e-4b5a-4c7d-8e9f-0a1b2c3d4e5f",
"name": "ci",
"organization_id": "6f1c2d3e-4b5a-4c7d-8e9f-0a1b2c3d4e5f",
"secret_rotated_at": "2026-10-12T05:51:01Z",
"updated_at": "2026-10-12T05:51:01Z",
"url": "https://hooks.example.com/vmyard"
}Change a webhook
PATCH /v1/webhooks/{webhook_id}
- API key:
Authorization: Bearer vmy_…with presetfull_access. - Browser session: the
vmyard_sessioncookie and thex-csrf-tokenheader. - Who: Owner or Admin.
Parameters
| Name | In | Type | Required | Description |
|---|---|---|---|---|
webhook_id | path | string (uuid) | Yes | |
X-Organization-ID | header | string (uuid) | No | Organization context. Required with a browser session. Optional with an API key, which fixes the organization; when sent it must match. |
Request body (application/json, UpdateWebhookRequest)
| Field | Type | Required | Description |
|---|---|---|---|
enabled | boolean | null | No | |
events | WebhookEventDto[] | null | No | at least 1 items. |
name | string | null | No | 1–64 characters. |
url | string | null | No | at most 2048 characters. |
Responses
| Status | Description | Body |
|---|---|---|
200 | Queued deliveries of a disabled endpoint wait until it is enabled again | WebhookDto |
401 | Not signed in, or the API key is malformed, expired, or revoked (unauthenticated, invalid_api_key). | ProblemDetails |
403 | CSRF failure, a role other than owner/admin, or an API key without full_access | ProblemDetails |
404 | Not found in this organization (resource_not_found). | ProblemDetails |
422 | Invalid request (invalid_request); field_errors names the fields. | ProblemDetails |
curl -X PATCH "$VMYARD_API_URL/v1/webhooks/$WEBHOOK_ID" \
-H "Authorization: Bearer $VMYARD_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"enabled": false
}'{
"created_at": "2026-10-12T05:51:01Z",
"created_by": "6f1c2d3e-4b5a-4c7d-8e9f-0a1b2c3d4e5f",
"enabled": false,
"events": [
"machine.ready"
],
"id": "6f1c2d3e-4b5a-4c7d-8e9f-0a1b2c3d4e5f",
"name": "ci",
"organization_id": "6f1c2d3e-4b5a-4c7d-8e9f-0a1b2c3d4e5f",
"secret_rotated_at": "2026-10-12T05:51:01Z",
"updated_at": "2026-10-12T05:51:01Z",
"url": "https://hooks.example.com/vmyard"
}Delete a webhook
DELETE /v1/webhooks/{webhook_id}
- API key:
Authorization: Bearer vmy_…with presetfull_access. - Browser session: the
vmyard_sessioncookie and thex-csrf-tokenheader. - Who: Owner or Admin.
Parameters
| Name | In | Type | Required | Description |
|---|---|---|---|---|
webhook_id | path | string (uuid) | Yes | |
X-Organization-ID | header | string (uuid) | No | Organization context. Required with a browser session. Optional with an API key, which fixes the organization; when sent it must match. |
Responses
| Status | Description | Body |
|---|---|---|
204 | Deleted together with its queued and past deliveries | — |
401 | Not signed in, or the API key is malformed, expired, or revoked (unauthenticated, invalid_api_key). | ProblemDetails |
403 | CSRF failure, a role other than owner/admin, or an API key without full_access | ProblemDetails |
404 | Not found in this organization (resource_not_found). | ProblemDetails |
curl -X DELETE "$VMYARD_API_URL/v1/webhooks/$WEBHOOK_ID" \
-H "Authorization: Bearer $VMYARD_API_KEY"Rotate a webhook secret
POST /v1/webhooks/{webhook_id}/rotate-secret
- API key:
Authorization: Bearer vmy_…with presetfull_access. - Browser session: the
vmyard_sessioncookie and thex-csrf-tokenheader. - Who: Owner or Admin.
Parameters
| Name | In | Type | Required | Description |
|---|---|---|---|---|
webhook_id | path | string (uuid) | Yes | |
X-Organization-ID | header | string (uuid) | No | Organization context. Required with a browser session. Optional with an API key, which fixes the organization; when sent it must match. |
Responses
| Status | Description | Body |
|---|---|---|
200 | The old secret stops signing immediately, including retries of queued deliveries | WebhookSecretDto |
401 | Not signed in, or the API key is malformed, expired, or revoked (unauthenticated, invalid_api_key). | ProblemDetails |
403 | CSRF failure, a role other than owner/admin, or an API key without full_access | ProblemDetails |
404 | Not found in this organization (resource_not_found). | ProblemDetails |
503 | webhooks_unavailable: no secret keys are configured | ProblemDetails |
curl -X POST "$VMYARD_API_URL/v1/webhooks/$WEBHOOK_ID/rotate-secret" \
-H "Authorization: Bearer $VMYARD_API_KEY"{
"secret": "whsec_…",
"webhook": {
"created_at": "2026-10-12T05:51:01Z",
"created_by": "6f1c2d3e-4b5a-4c7d-8e9f-0a1b2c3d4e5f",
"enabled": false,
"events": [
"machine.ready"
],
"id": "6f1c2d3e-4b5a-4c7d-8e9f-0a1b2c3d4e5f",
"name": "ci",
"organization_id": "6f1c2d3e-4b5a-4c7d-8e9f-0a1b2c3d4e5f",
"secret_rotated_at": "2026-10-12T05:51:01Z",
"updated_at": "2026-10-12T05:51:01Z",
"url": "https://hooks.example.com/vmyard"
}
}List webhook deliveries
GET /v1/webhooks/{webhook_id}/deliveries
- API key:
Authorization: Bearer vmy_…with presetfull_access. - Browser session: the
vmyard_sessioncookie. - Who: Owner or Admin.
Parameters
| Name | In | Type | Required | Description |
|---|---|---|---|---|
limit | query | integer | No | 1-100, default 50; newest first. |
webhook_id | path | string (uuid) | Yes | |
X-Organization-ID | header | string (uuid) | No | Organization context. Required with a browser session. Optional with an API key, which fixes the organization; when sent it must match. |
Responses
| Status | Description | Body |
|---|---|---|
200 | Recent deliveries to this endpoint, newest first, with their last attempt | WebhookDeliveryPage |
401 | Not signed in, or the API key is malformed, expired, or revoked (unauthenticated, invalid_api_key). | ProblemDetails |
403 | A role other than owner/admin, or an API key without full_access | ProblemDetails |
404 | Not found in this organization (resource_not_found). | ProblemDetails |
curl "$VMYARD_API_URL/v1/webhooks/$WEBHOOK_ID/deliveries" \
-H "Authorization: Bearer $VMYARD_API_KEY"{
"items": [
{
"attempt_count": 0,
"created_at": "2026-10-12T05:51:01Z",
"delivered_at": "2026-10-12T05:51:01Z",
"event_id": "6f1c2d3e-4b5a-4c7d-8e9f-0a1b2c3d4e5f",
"event_type": "machine.ready",
"id": "6f1c2d3e-4b5a-4c7d-8e9f-0a1b2c3d4e5f",
"last_attempt_at": "2026-10-12T05:51:01Z",
"last_error": "string",
"last_status_code": 0,
"machine_id": "6f1c2d3e-4b5a-4c7d-8e9f-0a1b2c3d4e5f",
"next_attempt_at": "2026-10-12T05:51:01Z",
"operation_id": "6f1c2d3e-4b5a-4c7d-8e9f-0a1b2c3d4e5f",
"status": "pending"
}
]
}