Every API here is available over the APIs.io API and to AI agents over MCP.
MCP server
One button, every client — Claude, Cursor, VS Code and the rest.
https://apis.io/mcp
Tools for apis
7 MCP tools reach this
find_apisBrowse and filter every API in the catalog.
get_api_artifactsOne API's artifacts, grouped by type.
get_openapiThe primary OpenAPI for this API.
find_similar_apisAPIs that look like this one.
apis_io_searchSTART HERE — APIs, providers and tags for one query, each with its total.
resolveTurn a domain, URL or GitHub org into the provider it belongs to.
find_cohortsEvery scored population of providers in the catalog.
All 92 tools →
Call it yourself
curl for this page
This API
curl "https://apis.io/api/v1/apis/agentisend-com:agentisend-com-audit-api"
All apis
curl "https://apis.io/api/v1/apis?limit=25"
Discovery needs no key. Ratings and market analysis are Pro.
Get an API key
Free tier, no form to fill in. Signing in shares your email address with us — we
store it to create your key and to recognise you if you sign in with another
provider. See our Privacy Policy and
Terms.
A second provider on the same verified email joins the account you already have.
openapi: 3.2.0
info:
contact:
email: hello@agentisend.com
url: https://agentisend.com
description: AgentiSend is a transactional email API for AI agents.
termsOfService: https://agentisend.com/terms
title: AgentiSend Audit API
version: 0.1.0
servers:
- url: https://api.agentisend.com
security:
- bearer: []
tags:
- name: Audit
paths:
/audit-log:
get:
description: Changes made on this account (keys, limits, kill switch, domains, webhooks, suppressions, contacts, segments, topics, templates, broadcasts, automations, approvals, team, billing), with the value before and after. Sending an email is its own record, not here. Newest first.
operationId: getAuditLog
parameters:
- in: query
name: limit
required: false
schema:
default: 50
maximum: 200
minimum: 1
type: integer
- in: query
name: cursor
required: false
schema:
minLength: 1
type: string
- in: query
name: after
required: false
schema:
minLength: 1
type: string
- in: query
name: actor
required: false
schema:
format: uuid
pattern: ^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[1-8][0-9a-fA-F]{3}-[89abAB][0-9a-fA-F]{3}-[0-9a-fA-F]{12}|00000000-0000-0000-0000-000000000000|ffffffff-ffff-ffff-ffff-ffffffffffff)$
type: string
- in: query
name: action
required: false
schema:
maxLength: 100
minLength: 1
type: string
- in: query
name: from
required: false
schema:
format: date-time
pattern: ^(?:(?:\d\d[2468][048]|\d\d[13579][26]|\d\d0[48]|[02468][048]00|[13579][26]00)-02-29|\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\d|30)|(?:02)-(?:0[1-9]|1\d|2[0-8])))T(?:(?:[01]\d|2[0-3]):[0-5]\d(?::[0-5]\d(?:\.\d+)?)?(?:Z))$
type: string
- in: query
name: to
required: false
schema:
format: date-time
pattern: ^(?:(?:\d\d[2468][048]|\d\d[13579][26]|\d\d0[48]|[02468][048]00|[13579][26]00)-02-29|\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\d|30)|(?:02)-(?:0[1-9]|1\d|2[0-8])))T(?:(?:[01]\d|2[0-3]):[0-5]\d(?::[0-5]\d(?:\.\d+)?)?(?:Z))$
type: string
responses:
'200':
content:
application/json:
example:
data: []
has_more: false
next_cursor: example
object: list
schema:
$ref: '#/components/schemas/GetAudit_logReply'
description: Success
headers:
ratelimit-limit:
$ref: '#/components/headers/RateLimitLimit'
ratelimit-remaining:
$ref: '#/components/headers/RateLimitRemaining'
ratelimit-reset:
$ref: '#/components/headers/RateLimitReset'
'400':
$ref: '#/components/responses/BadRequest'
'401':
$ref: '#/components/responses/Unauthorized'
'403':
$ref: '#/components/responses/Forbidden'
'429':
$ref: '#/components/responses/TooManyRequests'
'500':
$ref: '#/components/responses/InternalServerError'
summary: Changes made on this account (keys, limits, kill switch, domains, webhooks…
tags:
- Audit
x-error-codes:
- internal_server_error
- invalid_api_key
- mfa_required
- missing_api_key
- rate_limit_exceeded
- restricted_api_key
- validation_error
components:
headers:
RetryAfter:
description: Seconds to wait before retrying. Present on every refusal the catalog marks retryable — and deliberately absent on one it does not, because a refusal waiting cannot cure must never hand a client a wait hint.
schema:
minimum: 1
type: integer
RateLimitReset:
description: Seconds until the current window resets and the budget refills.
schema:
minimum: 1
type: integer
RateLimitLimit:
description: Messages this API key may spend in one 60-second window.
schema:
minimum: 0
type: integer
RateLimitRemaining:
description: Messages left in the current window.
schema:
minimum: 0
type: integer
responses:
InternalServerError:
content:
application/json:
schema:
properties:
error:
properties:
code:
description: The catalogue code. Resend error names resolve onto these — see x-resend-error-aliases at the root of this document for the table a find-replace migration follows.
type: string
docs_url:
type: string
fix:
type: string
message:
type: string
retry_after_seconds:
description: Seconds to wait before retrying. Present exactly when retryable is true, absent otherwise.
minimum: 1
type: integer
retryable:
description: Whether repeating the identical request could succeed later. A 429 that waiting cannot cure (daily quota, trust throttle) is false.
type: boolean
required:
- code
- message
- fix
- docs_url
- retryable
type: object
message:
description: The same sentence as error.message.
type: string
name:
description: The Resend error name for this code (x-resend-error-names). A validation detail that says the field is required is missing_required_field. error.code stays our catalogue code.
type: string
statusCode:
description: The HTTP status. Present on every error so a Resend SDK can read it beside error.
type: integer
required:
- statusCode
- name
- message
- error
type: object
description: 'Something failed on our side. Codes: internal_server_error.'
headers:
ratelimit-limit:
$ref: '#/components/headers/RateLimitLimit'
ratelimit-remaining:
$ref: '#/components/headers/RateLimitRemaining'
ratelimit-reset:
$ref: '#/components/headers/RateLimitReset'
TooManyRequests:
content:
application/json:
schema:
properties:
error:
properties:
code:
description: The catalogue code. Resend error names resolve onto these — see x-resend-error-aliases at the root of this document for the table a find-replace migration follows.
type: string
docs_url:
type: string
fix:
type: string
message:
type: string
retry_after_seconds:
description: Seconds to wait before retrying. Present exactly when retryable is true, absent otherwise.
minimum: 1
type: integer
retryable:
description: Whether repeating the identical request could succeed later. A 429 that waiting cannot cure (daily quota, trust throttle) is false.
type: boolean
required:
- code
- message
- fix
- docs_url
- retryable
type: object
message:
description: The same sentence as error.message.
type: string
name:
description: The Resend error name for this code (x-resend-error-names). A validation detail that says the field is required is missing_required_field. error.code stays our catalogue code.
type: string
statusCode:
description: The HTTP status. Present on every error so a Resend SDK can read it beside error.
type: integer
required:
- statusCode
- name
- message
- error
type: object
description: 'A rate, quota or ramp ceiling was reached. Codes: onboarding_daily_cap_reached, trust_throttled, invite_limit_reached, rate_ceiling_exceeded, daily_quota_exceeded, monthly_quota_exceeded, rate_limit_exceeded, support_rate_limited, appsumo_lookup_limited.'
headers:
ratelimit-limit:
$ref: '#/components/headers/RateLimitLimit'
ratelimit-remaining:
$ref: '#/components/headers/RateLimitRemaining'
ratelimit-reset:
$ref: '#/components/headers/RateLimitReset'
retry-after:
$ref: '#/components/headers/RetryAfter'
BadRequest:
content:
application/json:
schema:
properties:
error:
properties:
code:
description: The catalogue code. Resend error names resolve onto these — see x-resend-error-aliases at the root of this document for the table a find-replace migration follows.
type: string
docs_url:
type: string
fix:
type: string
message:
type: string
retry_after_seconds:
description: Seconds to wait before retrying. Present exactly when retryable is true, absent otherwise.
minimum: 1
type: integer
retryable:
description: Whether repeating the identical request could succeed later. A 429 that waiting cannot cure (daily quota, trust throttle) is false.
type: boolean
required:
- code
- message
- fix
- docs_url
- retryable
type: object
message:
description: The same sentence as error.message.
type: string
name:
description: The Resend error name for this code (x-resend-error-names). A validation detail that says the field is required is missing_required_field. error.code stays our catalogue code.
type: string
statusCode:
description: The HTTP status. Present on every error so a Resend SDK can read it beside error.
type: integer
required:
- statusCode
- name
- message
- error
type: object
description: 'The request is malformed or a field failed validation. Codes: validation_error, invalid_idempotency_key, invalid_cursor, plan_not_purchasable, stripe_signature_invalid, support_upload_rejected, appsumo_license_not_confirmed, appsumo_ticket_invalid, sign_in_check_required.'
headers:
ratelimit-limit:
$ref: '#/components/headers/RateLimitLimit'
ratelimit-remaining:
$ref: '#/components/headers/RateLimitRemaining'
ratelimit-reset:
$ref: '#/components/headers/RateLimitReset'
Forbidden:
content:
application/json:
schema:
properties:
error:
properties:
code:
description: The catalogue code. Resend error names resolve onto these — see x-resend-error-aliases at the root of this document for the table a find-replace migration follows.
type: string
docs_url:
type: string
fix:
type: string
message:
type: string
retry_after_seconds:
description: Seconds to wait before retrying. Present exactly when retryable is true, absent otherwise.
minimum: 1
type: integer
retryable:
description: Whether repeating the identical request could succeed later. A 429 that waiting cannot cure (daily quota, trust throttle) is false.
type: boolean
required:
- code
- message
- fix
- docs_url
- retryable
type: object
message:
description: The same sentence as error.message.
type: string
name:
description: The Resend error name for this code (x-resend-error-names). A validation detail that says the field is required is missing_required_field. error.code stays our catalogue code.
type: string
statusCode:
description: The HTTP status. Present on every error so a Resend SDK can read it beside error.
type: integer
required:
- statusCode
- name
- message
- error
type: object
description: 'The credential may not do this, or the account or key is stopped. Codes: sending_domain_blocked, young_domain_held, domain_sending_disabled, inbound_sender_refused, domain_not_verified, onboarding_recipient_not_a_member, onboarding_sender_unavailable, account_suspended, account_sandboxed, agent_unconfirmed, recipient_ramp, human_action_required, csrf_origin_rejected, charge_not_this_account, invalid_api_key, restricted_api_key, insufficient_role, invite_email_mismatch, domain_scope_violation, dedicated_ip_assigned_by_us, approval_required, staff_review_required, trust_paused, kill_switch_active.'
headers:
ratelimit-limit:
$ref: '#/components/headers/RateLimitLimit'
ratelimit-remaining:
$ref: '#/components/headers/RateLimitRemaining'
ratelimit-reset:
$ref: '#/components/headers/RateLimitReset'
Unauthorized:
content:
application/json:
schema:
properties:
error:
properties:
code:
description: The catalogue code. Resend error names resolve onto these — see x-resend-error-aliases at the root of this document for the table a find-replace migration follows.
type: string
docs_url:
type: string
fix:
type: string
message:
type: string
retry_after_seconds:
description: Seconds to wait before retrying. Present exactly when retryable is true, absent otherwise.
minimum: 1
type: integer
retryable:
description: Whether repeating the identical request could succeed later. A 429 that waiting cannot cure (daily quota, trust throttle) is false.
type: boolean
required:
- code
- message
- fix
- docs_url
- retryable
type: object
message:
description: The same sentence as error.message.
type: string
name:
description: The Resend error name for this code (x-resend-error-names). A validation detail that says the field is required is missing_required_field. error.code stays our catalogue code.
type: string
statusCode:
description: The HTTP status. Present on every error so a Resend SDK can read it beside error.
type: integer
required:
- statusCode
- name
- message
- error
type: object
description: 'No usable credential was sent. Codes: agent_signup_code_rejected, missing_api_key, session_required, mfa_required, appsumo_signature_invalid.'
headers:
ratelimit-limit:
$ref: '#/components/headers/RateLimitLimit'
ratelimit-remaining:
$ref: '#/components/headers/RateLimitRemaining'
ratelimit-reset:
$ref: '#/components/headers/RateLimitReset'
schemas:
GetAudit_logReply:
properties:
data:
items:
properties:
account_id:
anyOf:
- format: uuid
pattern: ^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[1-8][0-9a-fA-F]{3}-[89abAB][0-9a-fA-F]{3}-[0-9a-fA-F]{12}|00000000-0000-0000-0000-000000000000|ffffffff-ffff-ffff-ffff-ffffffffffff)$
type: string
- type: 'null'
action:
type: string
actor_email:
anyOf:
- type: string
- type: 'null'
actor_id:
anyOf:
- type: string
- type: 'null'
actor_type:
type: string
actor_user_id:
anyOf:
- type: string
- type: 'null'
after:
additionalProperties: {}
propertyNames:
type: string
type: object
before:
additionalProperties: {}
propertyNames:
type: string
type: object
created_at:
format: date-time
pattern: ^(?:(?:\d\d[2468][048]|\d\d[13579][26]|\d\d0[48]|[02468][048]00|[13579][26]00)-02-29|\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\d|30)|(?:02)-(?:0[1-9]|1\d|2[0-8])))T(?:(?:[01]\d|2[0-3]):[0-5]\d(?::[0-5]\d(?:\.\d+)?)?(?:Z))$
type: string
id:
format: uuid
pattern: ^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[1-8][0-9a-fA-F]{3}-[89abAB][0-9a-fA-F]{3}-[0-9a-fA-F]{12}|00000000-0000-0000-0000-000000000000|ffffffff-ffff-ffff-ffff-ffffffffffff)$
type: string
reason:
anyOf:
- type: string
- type: 'null'
target_id:
anyOf:
- type: string
- type: 'null'
target_type:
anyOf:
- type: string
- type: 'null'
required:
- id
- account_id
- actor_type
- actor_id
- actor_user_id
- actor_email
- action
- target_type
- target_id
- before
- after
- reason
- created_at
type: object
type: array
has_more:
type: boolean
next_cursor:
anyOf:
- type: string
- type: 'null'
object:
const: list
type: string
required:
- object
- data
- has_more
- next_cursor
type: object
securitySchemes:
bearer:
description: 'An API key, sent as Authorization: Bearer as_…'
scheme: bearer
type: http
externalDocs:
description: AgentiSend docs
url: https://agentisend.com/docs
x-resend-error-aliases:
concurrent_idempotent_requests: idempotency_in_flight
daily_quota_exceeded: daily_quota_exceeded
internal_server_error: internal_server_error
invalid_api_key: invalid_api_key
invalid_attachment: invalid_attachment
invalid_from_address: invalid_from_address
invalid_idempotent_request: idempotency_payload_mismatch
method_not_allowed: method_not_allowed
missing_api_key: missing_api_key
not_found: not_found
rate_limit_exceeded: rate_limit_exceeded
restricted_api_key: restricted_api_key
validation_error: validation_error
x-resend-error-names:
account_sandboxed: application_error
account_suspended: application_error
agent_budget_exceeded: monthly_quota_exceeded
agent_signup_code_rejected: application_error
agent_signup_refused: application_error
agent_unconfirmed: application_error
already_in_account: application_error
approval_expired: application_error
approval_required: application_error
appsumo_license_inactive: application_error
appsumo_license_linked: application_error
appsumo_license_not_confirmed: application_error
appsumo_lookup_limited: application_error
appsumo_signature_invalid: application_error
appsumo_ticket_invalid: application_error
billing_customer_missing: application_error
billing_not_configured: application_error
charge_not_this_account: application_error
contact_resubscribe_required: application_error
content_refused: application_error
csrf_origin_rejected: application_error
daily_limit_reached: application_error
daily_quota_exceeded: daily_quota_exceeded
dedicated_ip_assigned_by_us: application_error
dkim_key_mismatch: application_error
dns_unreachable: application_error
domain_already_exists: application_error
domain_blocklisted: application_error
domain_check_window_expired: application_error
domain_field_immutable: application_error
domain_limit_reached: application_error
domain_not_claimable: application_error
domain_not_verified: validation_error
domain_scope_violation: application_error
domain_sending_disabled: application_error
domain_verified_elsewhere: application_error
email_still_scheduled: application_error
header_replaced: application_error
html_clipped_by_gmail: application_error
human_action_required: application_error
idempotency_in_flight: concurrent_idempotent_requests
idempotency_payload_mismatch: invalid_idempotent_request
inbound_sender_refused: application_error
insufficient_role: application_error
internal_server_error: internal_server_error
invalid_api_key: invalid_api_key
invalid_attachment: invalid_attachment
invalid_cursor: application_error
invalid_from_address: invalid_from_address
invalid_idempotency_key: application_error
invalid_parameter: validation_error
invalid_region: application_error
invite_email_mismatch: application_error
invite_limit_reached: application_error
invite_not_valid: application_error
key_budget_exceeds_plan: application_error
kill_switch_active: application_error
last_owner_required: application_error
lifetime_sold_on_appsumo: application_error
link_domain_listed: application_error
mailbox_provider_domain: application_error
method_not_allowed: method_not_allowed
mfa_required: application_error
missing_api_key: missing_api_key
missing_required_field: missing_required_field
monthly_quota_exceeded: application_error
not_found: not_found
onboarding_daily_cap_reached: application_error
onboarding_recipient_not_a_member: application_error
onboarding_sender_unavailable: application_error
onboarding_shape_refused: application_error
open_tracking_on_transactional: application_error
overage_cap_reached: application_error
overage_not_on_plan: application_error
payload_too_large: application_error
plan_limit_reached: monthly_quota_exceeded
plan_not_purchasable: application_error
portal_change_unavailable: application_error
rate_ceiling_exceeded: rate_limit_exceeded
rate_limit_exceeded: rate_limit_exceeded
rate_limiter_unavailable: application_error
recipient_blocklisted: application_error
recipient_ramp: application_error
restricted_api_key: restricted_api_key
return_path_subdomain_in_use: application_error
review_sandbox_recipient_only: application_error
seat_limit_reached: application_error
segment_in_use: application_error
sending_domain_blocked: application_error
sending_paused_everywhere: application_error
service_unavailable: application_error
session_expired: application_error
session_required: application_error
sign_in_check_required: application_error
spf_conflict: application_error
spf_lookup_limit: application_error
staff_review_required: application_error
stripe_signature_invalid: application_error
subscription_active: application_error
support_attachment_expired: application_error
support_closed: application_error
support_draft_unavailable: application_error
support_merge_conflict: application_error
support_rate_limited: application_error
support_reopen_expired: application_error
support_reply_too_soon: application_error
support_ticket_not_found: application_error
support_upload_rejected: application_error
support_upload_too_large: application_error
suppressed_recipient: application_error
template_alias_taken: application_error
template_in_use: application_error
template_name_taken: application_error
term_not_on_sale: application_error
tracking_subdomain_cannot_be_removed: application_error
tracking_subdomain_unverified: application_error
trust_paused: application_error
trust_throttled: application_error
unsupported_media_type: application_error
validation_error: validation_error
webhook_endpoint_limit_reached: application_error
young_domain_held: application_error