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/hermoso-ai:hermoso-ai-connect-links-api"
All apis
curl "https://apis.io/api/v1/apis?limit=25"
Calls without X-API-Key need no key. Calls with it need a paid plan — get a key.
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:
title: Hermoso Ai Connect Links API
version: '2026-08-26'
description: 'Operations tagged connect-links across 2 of this provider''s published API definitions: app_hermoso_ai.json, app_hermoso_ai_rest.json. Each path carries the servers of the definition it was published in.'
servers:
- url: https://app.hermoso.ai
security:
- bearerAuth: []
tags:
- name: connect-links
paths:
/v1/connect-links:
post:
operationId: createConnectLink
summary: Create a connect link for your customer
description: 'A short-lived hosted link that lets someone with NO Hermoso login connect their own account (Facebook and Instagram, Instagram, TikTok, YouTube, LinkedIn, X, Pinterest, Threads, Google Business Profile and the ad platforms) to the brand named by `X-Hermoso-User`. Hand `url` to your customer. They see a short page from Hermoso, accept Hermoso’s Terms and Privacy Policy, sign in on the platform’s own consent screen, and land on your `redirect_url` with `connect_status` (success | cancelled | error), `provider`, `brand`, `link_id`, `account`, `error_code` and your `state` added to its query string (a same-named parameter of yours is overwritten).
THE PLATFORM’S CONSENT SCREEN SHOWS HERMOSO’S NAME, because the connection is made with Hermoso’s app on that platform.
A link connects ONE provider to ONE brand. It can be retried after a cancel until it expires, and is spent once an account connects. Know when it connects from the `account.connected` webhook event (connect a webhook on the brand and include the `connections` group) or by polling GET /v1/connect-links/{id}. Facebook and LinkedIn then need the Pages chosen: call list_connector_accounts and set_connector_accounts through /v1/tools (the link’s creator owns that choice). Accounts that connect with a pasted key (Bluesky, Telegram) are connected with POST /v1/tools/connect_connector instead.'
tags:
- connect-links
parameters:
- name: Idempotency-Key
in: header
required: false
schema:
type: string
description: 'Send a unique value to make this call safe to retry. A replay returns the original response with `Idempotency-Replayed: true`, for 24 hours — except a call that queued a job, whose replay is that job as it is now (what `GET /v1/jobs/{id}` answers), so a finished render replays as done with its file.'
- name: X-Hermoso-User
in: header
required: false
schema:
type: string
description: 'Which profile to act on, when the account holds more than one: an `id` from `GET /v1/brands`. Defaults to the workspace the key is pinned to. Membership is re-authorised on every request, and an id this key cannot act on is a 404 `brand_not_found`, never an empty result.'
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/ConnectLinkCreate'
responses:
'200':
description: Success
content:
application/json:
schema:
$ref: '#/components/schemas/ConnectLink'
'400':
description: Invalid request.
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'401':
description: Missing, invalid or revoked key — or a channel that is not connected, in which case `error.connector` names it and `error.type` is `connector_error`.
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'404':
description: '`error.code: brand_not_found`: `X-Hermoso-User` (or the profile this key is pinned to) names a profile this key cannot act on. `GET /v1/brands` lists the valid ids.'
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'429':
description: Rate limited. `Retry-After` says how long to wait.
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
security:
- bearerAuth: []
servers:
- url: https://app.hermoso.ai
/v1/connect-links/{id}:
get:
operationId: getConnectLink
summary: Retrieve a connect link
description: '`status` is pending, opened, connected, cancelled, failed, expired or revoked. Once connected, `account` names what was connected. Kept for 7 days after the link expires.'
tags:
- connect-links
parameters:
- name: id
in: path
required: true
schema:
type: string
- name: X-Hermoso-User
in: header
required: false
schema:
type: string
description: 'Which profile to act on, when the account holds more than one: an `id` from `GET /v1/brands`. Defaults to the workspace the key is pinned to. Membership is re-authorised on every request, and an id this key cannot act on is a 404 `brand_not_found`, never an empty result.'
responses:
'200':
description: Success
content:
application/json:
schema:
$ref: '#/components/schemas/ConnectLink'
'400':
description: Invalid request.
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'401':
description: Missing, invalid or revoked key — or a channel that is not connected, in which case `error.connector` names it and `error.type` is `connector_error`.
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'404':
description: '`error.code: brand_not_found`: `X-Hermoso-User` (or the profile this key is pinned to) names a profile this key cannot act on. `GET /v1/brands` lists the valid ids.'
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'429':
description: Rate limited. `Retry-After` says how long to wait.
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
security:
- bearerAuth: []
delete:
operationId: revokeConnectLink
summary: Cancel a connect link
description: The link stops working at once. A link that already connected an account cannot be revoked; remove that connection with DELETE /v1/connections/{provider}.
tags:
- connect-links
parameters:
- name: id
in: path
required: true
schema:
type: string
- name: X-Hermoso-User
in: header
required: false
schema:
type: string
description: 'Which profile to act on, when the account holds more than one: an `id` from `GET /v1/brands`. Defaults to the workspace the key is pinned to. Membership is re-authorised on every request, and an id this key cannot act on is a 404 `brand_not_found`, never an empty result.'
responses:
'200':
description: Success
content:
application/json:
schema:
$ref: '#/components/schemas/ConnectLink'
'400':
description: Invalid request.
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'401':
description: Missing, invalid or revoked key — or a channel that is not connected, in which case `error.connector` names it and `error.type` is `connector_error`.
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'404':
description: '`error.code: brand_not_found`: `X-Hermoso-User` (or the profile this key is pinned to) names a profile this key cannot act on. `GET /v1/brands` lists the valid ids.'
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
'429':
description: Rate limited. `Retry-After` says how long to wait.
content:
application/json:
schema:
$ref: '#/components/schemas/Error'
security:
- bearerAuth: []
servers:
- url: https://app.hermoso.ai
components:
schemas:
ConnectLinkCreate:
type: object
required:
- provider
properties:
provider:
type: string
description: 'Which platform: meta (Facebook and Instagram), instagram (an Instagram account on its own login), tiktok, youtube, linkedin, linkedin_community (comments as a LinkedIn Page), x, pinterest, threads, google_business, and the ad platforms. An unsupported one is refused with the list.'
redirect_url:
type: string
description: Where your customer lands afterwards. Must sit under a registered address (PUT /v1/connect-redirects). Omit to show them a plain “connected, you can close this window” page.
state:
type: string
description: Your own value, up to 500 characters, returned on the redirect and in the webhook so you can match the connection to your customer.
expires_in_minutes:
type: integer
minimum: 5
maximum: 2880
description: Default 60, at most 2880 (48 hours).
ConnectLink:
type: object
properties:
object:
type: string
enum:
- connect_link
id:
type: string
url:
type: string
description: Returned when the link is created. Hand it to your customer; it is a bearer link, so treat it like a password until it is used or expires.
provider:
type: string
brand:
type: string
status:
type: string
enum:
- pending
- opened
- connected
- cancelled
- failed
- expired
- revoked
redirect_url:
type: string
nullable: true
state:
type: string
nullable: true
created_at:
type: string
format: date-time
expires_at:
type: string
format: date-time
connected_at:
type: string
format: date-time
nullable: true
account:
type: object
nullable: true
properties:
label:
type: string
nullable: true
handle:
type: string
nullable: true
id:
type: string
nullable: true
account_selection_required:
type: boolean
nullable: true
description: 'True for Facebook/Instagram (meta) and LinkedIn: choose which Pages the brand may use with list_connector_accounts + set_connector_accounts before posting.'
error:
type: object
nullable: true
properties:
code:
type: string
message:
type: string
Error:
type: object
required:
- error
properties:
error:
type: object
required:
- type
- code
- message
properties:
type:
type: string
enum:
- authentication_error
- permission_error
- invalid_request_error
- connector_error
- rate_limit_error
- insufficient_credits
- api_error
description: The coarse family — branch on this. New CODES land inside an existing type wherever possible so that branch keeps working; the enum is published for code generation, and a client should still fall through gracefully on a member it does not recognise.
code:
type: string
description: The specific reason. Log this. New values may appear at any time.
message:
type: string
param:
type: string
description: The offending field, when there is one.
connector:
type: string
description: Present when the reason is a channel that is not connected. Reconnect in the app — an OAuth consent screen cannot be completed headlessly.
credits_needed:
type: number
description: 'On `insufficient_credits` from a recast or an edit: what the request needs.'
balance:
type: number
description: 'On `insufficient_credits` from a recast or an edit: what this workspace has.'
unknown_arguments:
type: array
items:
type: object
properties:
name:
type: string
description: The key that was sent.
did_you_mean:
type: string
nullable: true
description: An argument THIS tool declares that the key most likely meant, or null.
description: 'On `invalid_arguments` from POST /v1/tools/{name}: each key the tool does not take, with the argument it most likely meant. Nothing was run.'
upgrade_url:
type: string
description: 'On `real_face_needs_paid`: where to choose a paid plan.'
alternative:
type: string
description: 'On `real_face_needs_paid`: the field that works on every plan instead (`person.describe`).'
person_url:
type: string
description: 'On a recast with `person.describe` whose recast step was refused after the person was made: the AI person, in your Library. Send it as `person.image_url` to retry without making a new one.'
request_id:
type: string
nullable: true
securitySchemes:
bearerAuth:
type: http
scheme: bearer
bearerFormat: hmk_...
description: A Hermoso API key, or an access token from the OAuth authorization-code flow (which is the same thing).
x-refined-from:
- app_hermoso_ai.json
- app_hermoso_ai_rest.json