Skip to main content

Platform API Management

Platform APIs let you expose structured, role-based REST access to your tenant data — without giving callers full admin credentials.

Each Platform API is a named definition with a set of roles and a permission matrix. You issue keys per role. Callers authenticate with fyso_pkey_* keys and get exactly the permissions defined for their role.

Concepts

TermDescription
API definitionNamed configuration with roles and a permission matrix
RoleA named access level within the API (e.g., viewer, editor)
Permission matrixMap of entity → role → allowed operations
Platform keyfyso_pkey_* credential tied to one API + one role

Key format

Platform API keys use the prefix fyso_pkey_. They are distinct from:

  • Tenant API keys (fyso_ak_*) — full owner-level access
  • Anonymous keys (anon_*) — read-only public access

The full key value is shown only once at issuance time.


Permission Matrix

The permission matrix controls which entities each role can access and which operations are allowed:

{
"contacts": { "viewer": ["read"], "editor": ["read", "create", "update"] },
"deals": { "viewer": ["read"], "editor": ["read", "create", "update", "delete"] }
}

Operations

OperationHTTP methods
readGET
createPOST
updatePUT, PATCH
deleteDELETE

Wildcard entity

Use * to grant a role access to all entities:

{
"permissions": {
"*": { "admin": ["read", "create", "update", "delete"] }
}
}

Management Endpoints

All management endpoints require tenant admin authentication.

List APIs

GET /api/apis
Authorization: Bearer <admin-token>

Returns all API definitions for the tenant.

Create an API

POST /api/apis
Authorization: Bearer <admin-token>
Content-Type: application/json

{
"name": "Public CRM API",
"slug": "public-crm",
"roles": ["viewer", "editor"],
"permissions": {
"contacts": { "viewer": ["read"], "editor": ["read", "create", "update"] },
"deals": { "viewer": ["read"], "editor": ["read", "create", "update", "delete"] }
}
}
FieldTypeRequiredDescription
namestringYesHuman-readable name
slugstringYesURL-safe identifier (unique per tenant)
rolesstring[]YesRole names available in this API
permissionsobjectYesEntity to role to operations matrix

Get API details

GET /api/apis/:id
Authorization: Bearer <admin-token>

Update an API

PUT /api/apis/:id
Authorization: Bearer <admin-token>
Content-Type: application/json

{
"name": "Updated CRM API",
"roles": ["viewer", "editor", "admin"],
"permissions": {}
}

Delete an API

DELETE /api/apis/:id
Authorization: Bearer <admin-token>

Deletes the API definition and cascades to all issued keys. All fyso_pkey_* keys for this API are immediately revoked.


Key Management

List keys

GET /api/apis/:id/keys
Authorization: Bearer <admin-token>

Returns all keys for the API. Key values are never returned — only metadata.

Issue a key

POST /api/apis/:id/keys
Authorization: Bearer <admin-token>
Content-Type: application/json

{
"role": "viewer",
"label": "External analytics system"
}
FieldTypeRequiredDescription
rolestringYesMust be one of the roles defined in the API
labelstringNoHuman-readable description

Response (key shown only once):

{
"success": true,
"data": {
"id": "uuid",
"key": "fyso_pkey_abc123...",
"role": "viewer",
"label": "External analytics system",
"createdAt": "2026-02-24T00:00:00Z"
}
}

Revoke a key

DELETE /api/apis/:id/keys/:keyId
Authorization: Bearer <admin-token>

Immediately revokes the key. Returns 404 if the key does not exist or belongs to a different API.


Using Platform API Keys

Authentication

Include the key in the Authorization header:

curl -H "Authorization: Bearer fyso_pkey_..." \
https://api.fyso.dev/api/entities/contacts/records

Access enforcement

The requirePlatformApiKey middleware enforces permissions on every request:

  1. Validates the key format and looks up the associated API + role
  2. Extracts the target entity from the request path
  3. Maps the HTTP method to an operation (read, create, update, delete)
  4. Checks the permission matrix: entity x role x operation
  5. Returns 403 if the operation is not permitted

Error responses

StatusCause
401Missing or invalid key
403Operation not permitted for this role/entity combination

Full Example

Goal: expose a public CRM API where viewers can read contacts, and editors can also create and update them.

Step 1: Create the API definition

POST /api/apis
{
"name": "CRM Public API",
"slug": "crm-public",
"roles": ["viewer", "editor"],
"permissions": {
"contacts": {
"viewer": ["read"],
"editor": ["read", "create", "update"]
}
}
}

Step 2: Issue keys per role

POST /api/apis/<id>/keys
{ "role": "viewer", "label": "Dashboard read-only" }

POST /api/apis/<id>/keys
{ "role": "editor", "label": "CRM sync integration" }

Step 3: Use the keys

Viewer key reads contacts (200), cannot create (403). Editor key can create (201).


Security Notes

  • Key values are hashed. The plaintext is shown only once at issuance and never stored.
  • Deleting an API cascades to all keys — no orphaned credentials.
  • Existing fyso_ak_* tenant keys are completely unaffected by Platform API management.
  • The wildcard entity (*) grants access to all current and future entities for that role — use carefully.