Skip to content

REST API Reference

AgentsForms has two tiers of endpoints with different auth requirements:

These endpoints are designed for browser and agent integration without an API key:

EndpointMethodDescription
/api/forms/createPOSTCreate a draft form
/api/forms/:id/activatePOSTActivate form (email verification)
/api/forms/:id/submissionsPOSTSubmit answers to a form
/api/demoPOSTDemo endpoint (stores + emails)
/healthGETHealth check

The public /api/forms/... endpoints above are the recommended paths for new self-serve and static-site integrations. They do not require an API key.

Older /v1/forms/... endpoints remain available for backwards compatibility and dashboard/management use. Some deployments accept these calls without auth today, but if you have an API key you can include it as:

Authorization: Bearer <YOUR_API_KEY>

All endpoints return errors in a consistent format:

{
"error": {
"code": "validation_failed | not_found | unauthorized | internal_error",
"message": "Human-readable error description",
"details": [
{
"path": "fields.0.id",
"code": "invalid_string",
"message": "Detailed error message"
}
]
}
}

HTTP status codes: 400 (bad request), 401 (unauthorized), 404 (not found), 422 (validation failed), 500 (internal error).


Validate a form definition without creating it.

Request body: a form definition JSON object (see Form Schema Reference).

bash
Terminal window
curl -X POST https://api.agentsforms.com/v1/forms/validate \
-H "Authorization: Bearer $AGENTSFORMS_API_KEY" \
-H "Content-Type: application/json" \
-d @forms/example-form.json

Example response (200):

{
"ok": true,
"form": {
"name": "Support Intake",
"slug": "support-intake",
"fields": [{ "id": "email", "type": "email", "required": true }]
}
}

Example error (422):

{
"error": {
"code": "validation_failed",
"message": "Invalid form definition",
"details": [
{ "path": "fields.0.id", "code": "invalid_string", "message": "Field id must start with a letter" }
]
}
}

Create a new form from a JSON schema. The form is created in draft status. No authentication required.

Request body:

FieldTypeDescription
namestringHuman-readable name
slugstringURL-safe slug
descriptionstringOptional description
fieldsField[]Array of field definitions
deliveryDeliveryEmail or webhook delivery config
settingsSettingsOptional form-level settings
bash
Terminal window
curl -X POST https://agentsforms.com/api/forms/create \
-H "Content-Type: application/json" \
-d @forms/support-intake.json

Example response (201):

{
"form": {
"id": "form_abc123",
"name": "Support Intake",
"slug": "support-intake",
"status": "draft",
"activate_url": "/api/forms/form_abc123/activate?token=..."
}
}

Activate a draft form. The token is returned in the activate_url from the create step. Sends a confirmation email to the provided address. No authentication required.

Request body:

{ "email": "[email protected]" }

Example response (200):

{
"form": { "status": "published", "current_version_id": "..." },
"message": "Form activated. Submissions will be delivered by email."
}

Submit answers to a published form. No authentication required.

Request body:

{
"source": "site",
"answers": { "email": "[email protected]", "message": "Hello!" }
}

Example response (201):

{ "ok": true, "submission_id": "sub_xyz789" }

List submissions for a form with pagination and filtering. Requires an API key with the submissions:read scope.

The public /api/forms/:id/submissions endpoint is write-only and accepts POST submissions. It does not expose stored submissions to unauthenticated callers.

Query parameters:

ParameterTypeDescription
limitnumberMax results (default 20, max 100)
offsetnumberPagination offset

Example response (200):

{
"submissions": [
{
"id": "sub_xyz789",
"form_id": "form_abc123",
"answers": { "email": "[email protected]", "message": "Hello!" },
"status": "accepted",
"created_at": "2026-06-23T10:00:00Z"
}
]
}

Health check. No authentication required.

Example response (200):

{ "ok": true }

Session endpoints are stable and ready for production use.

Create a new form-filling session.

Request body:

FieldTypeDescription
expires_innumberSession lifetime in seconds (default 3600)
prefillobjectKey-value prefill map by field id
metadataobjectArbitrary key-value metadata attached to the session

Response (201):

{
"session": {
"id": "sess_xyz789",
"form_id": "form_abc123",
"status": "open",
"url": "https://agentsforms.com/f/sess_xyz789",
"expires_at": "2026-06-23T11:00:00Z"
}
}

Get a session by ID. Returns the session status and any partial answers if allowPartial is enabled.

Update a session (e.g., extend expiry, add prefill data).

Force-submit a session. Normally the human user submits via the form UI; this endpoint allows an agent to auto-submit on the user’s behalf.


Submission endpoints are stable and ready for production use.

Legacy / management-tier equivalent of POST /api/forms/:id/submissions. For new browser and static-site integrations, use the public /api/forms/:id/submissions endpoint.

List submissions for a form with pagination and filtering.

Get a single submission by ID with full answer data.


Webhook endpoints are stable and ready for production use.

Register a webhook endpoint.

Request body:

FieldTypeDescription
urlstringHTTPS URL to receive webhook events
eventsstring[]Event types: submission.created, session.expired
secretstringOptional HMAC signing secret

List registered webhooks.

Get a webhook by ID.

Delete a webhook.

List delivery attempts for a webhook, with status and timestamps.

Replay a failed webhook delivery.


Renders the hosted form page for a human user to fill out. This endpoint returns HTML, not JSON.