/platform/*.
Authentication
Each generated endpoint page lists its supported credential. Server automation endpoints accept apmfa_… team key, a pmfa_pt_… project token when
the endpoint has a project or session boundary, or a verified dashboard bearer.
Endpoints that authorize an action by a specific member accept only a verified
dashboard bearer. This dashboard-only group includes team and member
changes. Team and member changes require an team owner or
admin. Template and flow operations accept machine credentials when their
project boundary and required action scope both match.
Template responses identify drafts with id and createdAt.
Template list responses contain at most 500 drafts.
Each generated operation publishes its required action in x-required-scope
and its authority in x-polymorfa-resource-boundary. Project tokens are
accepted for project and session operations inside their authenticated
project. team operations such as billing, membership, team
settings, project creation, and team API-key administration return 403.
human_only operations require a dashboard bearer. A foreign or conflicting
project selector returns 404 resource not found.
Public domains
The Platform API supports session management and testing numbers, number safety, campaign listing, message-template management, billing and usage reads, team settings, projects, members, and QuickLink settings. Use only the endpoints documented in the generated reference.QuickLink settings
Team-key callers use
quicklink:manage (the historical name
widget:create is still accepted); project-token callers use the same
permission inside their authenticated project; dashboard callers use their
active team membership. Client tokens are rejected. Team-key
and dashboard callers pass projectId to read or update project-specific
settings. A project-token caller may omit it or pass the exact authenticated
project id. See Saved settings for
the supported fields.
Session-management endpoints
Team-key and project-token callers needsessions:manage. A project
token can affect only sessions in its authenticated project. Dashboard callers
need current membership and authorization in the active team.
Create real and simulated sessions through QuickLink.
For a simulated account, send
configuration.testing. When Customers is enabled,
customerId selects a Customer in the same project; omitting it assigns the
protected Default customer.
sessionId accepts a session UUID or a stable session slug up to 64
characters. Batch requests accept 1–100 unique identifiers in sessionIds.
The two deletion endpoints remove testing numbers immediately. A production
number, or a batch containing one, returns 409 without removing any number.
Contact support through the Help Center to delete a production number.
tierOverride is free, standard, pro, or null to
inherit the project plan. Testing-number country accepts one of the 243
WhatsApp-supported ISO alpha-2 country codes in the generated schema and
defaults to US. name is an optional 1–100 character display name.
Start requests connect a stopped testing number immediately or request a real
session start. Stop requests acknowledge an asynchronous stop request. Delete
requests permanently remove the session and end its active connection when
needed. The generated endpoint pages document the exact validation, not-found,
and temporary service-error responses for each endpoint.
Open the method reference inside the matching task guide for every path,
parameter, body, response, and shared schema. If you generated a private client
from an older Platform contract, follow Regenerate Platform API clients.
Customers
Customer reads requirecustomers:read. Enabling Customers, changing records,
and creating or revoking pairing links require customers:manage.
Team credentials supply
projectId for collection requests. A project
token is already bound to one project and cannot select another. Dashboard
mutations also require a live owner or admin membership.
Pairing-link creation accepts optional expectedPhone, methods, and
expiresInSeconds. methods contains qr, phone, or both. Expiry accepts
900 through 604800 seconds and defaults to 86400 seconds. The raw URL appears
only in the create response.
See Customers and Customer pairing
links for Console and recipient workflows.
BanSafe
BanSafe reads usesessions:read. Reporting a ban and withdrawing a report use
sessions:manage. Project tokens can read and report on their own numbers;
a number in another project returns 404. Withdrawing a report requires a team key.
GET /platform/bansafe/health requires projectId. The {session} segment accepts a
session UUID or a stable session slug. List responses are cursor-paginated with
a maximum page size of 100; the health history accepts since and a limit up
to 720. It returns the newest matching points, ordered oldest to newest.
Telemetry history accepts since, until, an opaque cursor, and a limit
from 1 to 50. It defaults to 10 and returns snapshots newest first. Health
actions accept projectId, session, public status, cursor, and a limit up
to 100. Team credentials supply projectId; a project token is bound
to its own project.
health is null without a supported estimate or enough fresh evidence. Read
healthSource, healthEstimatorVersion, healthUnavailableReason,
healthEvaluatedAt, healthFeatureCoverage, healthReliability, and
healthExplanation with it. The rules-v1 source has rules_based reliability
and null model probabilities. Provider-observed account state and retained
findings are separate from the estimate.
Telemetry responses expose only catalogue-backed aggregate signals. They do
not return raw stored records, message or recipient identifiers, runtime
identifiers, device fingerprints, or free-form error text. An unmeasured signal
has null value, sampleSize, and codes; zero remains a measured value. See
Telemetry and collection.
Every recorded finding carries the text to display: title names the retained
check, summary is its evidence sentence, fix is its recorded guidance, and
its timestamps show when the condition was observed. These
rows are historical and do not explain or change current Health. Display
them as returned rather than keeping another copy of their wording.
POST /platform/bansafe/incidents requires an Idempotency-Key header. Reuse it
only to retry the same number’s report. Reusing it for another number returns
409 bansafe_incident_idempotency_scope_conflict.
Retracting withdraws a ban you reported. It applies only to your own reports: a
restriction Polymorfa observed from WhatsApp answers
409 bansafe_incident_not_a_report and stays on the record. Send no request
body. The response includes nullable closedAt, closedBy, and claimId,
alongside the incident’s other fields. An unknown incident returns 404, and
an invalid incident identifier returns 400.
Ban Insurance claims are read-only. A claim is filed for you when a ban is
recorded for a number covered by Pro at the incident time, and a person reviews it before credits are returned;
there is no request that files, approves, or appeals one. Filter the list by
projectId, session, and status.
See BanSafe, Findings,
Restrictions, and
Ban Insurance.
Safe Mode
Safe Mode governs how a number sends: whether it goes online, whether it shows a typing indicator, whether it marks incoming messages read, and how it paces. Set the project ceiling, then tighten any single number against it.
Reading needs
sessions:read and changing needs sessions:manage.
{sessionId} accepts a session UUID or a stable session slug. A signed-in
Console caller must be an team owner, admin, or developer to change
Safe Mode; reading needs team membership.
A PUT body is a partial update: send only the settings you want to change.
Every setting is off by default. Each setting on a number also accepts
inherit to follow the project ceiling, and an override may only be equally or
more conservative than the ceiling.
Both GET responses answer the plan question before you send a change.
entitled is true when a raise is allowed, and entitlementReason carries
the sentence a refused raise would return, or null when the plan includes
Safe Mode. On a project, entitled is true when at least one number in the
project is on a plan that includes BanSafe Lite; on a number, it is that number’s
own plan.
The same four operations are on the Messaging API for server-to-server callers,
with the same settings, codes, and behaviour:
Warm-up plan
A warm-up plan gives every number in a project a daily message allowance that ramps over the number’s first weeks and moves with its health band.
Reading needs
sessions:read and changing needs sessions:manage. A signed-in
Console caller must be an team owner, admin, or developer to change the
plan; reading needs team membership.
A PUT body is a partial update over enabled, warmupDays (1 to 90), and
dailyStart (1 to 2000). The plan is off until a request turns it on, and
turning it off is always allowed.
While the plan is on, a send past a number’s allowance is refused with
429 bansafe_daily_allowance_reached; a campaign recipient is deferred to the
next reset. If durable accounting is unavailable, the send stops before
transport with 503 bansafe_accounting_unavailable and retryAfter: 5. A
conflicting attempt returns 409 bansafe_send_outcome_unknown and must not be
retried automatically.
The same two operations are on the Messaging API for server-to-server callers,
with the same settings, codes, and behaviour:
GET /platform/bansafe/health/{session} includes a warmup block with enabled,
tenureDay, allowance, sentToday, resetsAt, and curve. A disabled plan
has a null allowance and reset, and an empty curve. sentToday comes from the
durable active allowance window and is 0 before its first reservation. Health
history contains accepted Health evaluations only and does not carry allowance
fields.
See Warm-up plan.
Ban insurance evidence
Ban insurance evidence lets Polymorfa measure what the other devices linked to a number do with it. The counts help a reviewer assess a Ban Insurance claim. Collection is off until a request turns it on.
Reading needs
sessions:read and changing needs sessions:manage. A signed-in
Console caller must be an team owner, admin, or developer to change the
setting; reading needs team membership.
A PUT body carries one field, enabled, and it is required. The response
carries projectId, enabled, and banInsuranceIncluded. banInsuranceIncluded is true when at least one number in the project has
insurance included in its plan. The plan does not gate the setting: you can turn evidence on before a number is on Pro, and the
evidence is already there for a ban after the upgrade.
The same two operations are on the Messaging API for server-to-server callers,
with the same settings, codes, and behaviour: