API: tokens, endpoints and webhooks
From Pro up
The API gives a script the data the app shows: an organization's domains, reports, sources, DNS checks and alerts, as JSON. Every request carries an API token, and each token may make a set number of requests per clock hour. The plan sets that number and how many tokens the organization can have.
What each plan includes
| Plan | Requests per hour, per token | Active tokens |
|---|---|---|
| Starter | 0 | 0 |
| Pro | 60 | 3 |
| Teams | 600 | 25 |
| Enterprise | 3,000 | 100 |
On Pro a token can only read. From Teams up, a token can also be made to write, and writing does one thing: it starts an export. Three more ways to get your data start at these plans:
- Webhooks, which tell your server when something happens: Teams.
- Prometheus metrics: Teams.
- MCP for assistants: Teams.
Your first request
An admin creates a token under Settings → Developer → API tokens, as API tokens explains. The page shows the token once. This request lists your domains:
curl -H "Authorization: Bearer YOUR_TOKEN" https://www.mailmoni.com/api/v1/domains
Every address starts with https://www.mailmoni.com/api/v1/ and has no slash at the end. The endpoint reference lists every request and what it does.
Send the token in the header
Put the token in the Authorization header, after the word Bearer and a space. A token starts with mm_.
The API refuses a token in the address, even when the header is right, because addresses end up in logs. That covers a parameter named token, access_token or api_key, and any value shaped like a token. Such a request gets unauthorized.
The API sends no CORS headers, so JavaScript on a web page cannot read its answers. Keep the token in a script or on a server.
Requests per hour
Each token has its own count for each clock hour, in UTC. The count starts again on the hour. Every answer to a counted request carries three headers:
RateLimit-Limit: how many requests the token may make this hour.RateLimit-Remaining: how many of them are left.RateLimit-Reset: the seconds until the next hour.
A request over the limit gets rate_limited, with status 429 and a Retry-After header in seconds. Two scripts that share a token share its count, so give each script its own token. /metrics keeps a count of its own, and MCP tool calls made with a token use the token's API count.
Lists come in pages
A list answers with an object that holds data, the items, and next_cursor. Send next_cursor back as the cursor parameter to get the next page. When next_cursor is null, there is no next page.
The limit parameter sets how many items a page holds: 100 unless you say otherwise, and at most 500. A larger number is cut to 500. A value that is not a whole number of at least one gets invalid_parameter.
Days and windows
from and to are days, written YYYY-MM-DD, in UTC, and both are included. Without them a request covers the last 7 days, ending yesterday. to can be today at the latest.
A from before the start of your history is moved up to its first day, and the domain summary then says "window_clamped": true. Timestamps in answers are in UTC, written as ISO 8601 with a Z at the end.
Errors
An error answers with a problem document as RFC 9457 defines it, of type application/problem+json. It holds type, title, status, detail and code, and an invalid parameter adds parameter with the parameter's name. Match on code in your script. The type is an address that opens the page for that code, and API problem types lists them all.
English or Finnish
Send Accept-Language: fi to get title, detail and the other sentences the API writes in Finnish. Without it, or with a language we do not offer, they are in English. The answer's Content-Language header says which one you got.
The OpenAPI document
https://www.mailmoni.com/api/v1/openapi.json describes every request, the fields of every answer and every webhook event, as OpenAPI 3.1. It needs no token and follows Accept-Language too. Point a client generator at it, or read the endpoint reference built from it.
- Create and revoke API tokens
An admin creates API tokens for scripts, Prometheus and assistants, chooses their expiry and access, and revokes them. A smaller plan can pause some.
- Which requests does the API answer?
Every request the API answers, built from its OpenAPI document, with what OpenAPI cannot say about subdomains, report records and starting an export.
- Receive events with webhooks
We POST a signed JSON event when a report arrives, an alert opens or clears, or an export is ready. Add an endpoint, check the signature, handle retries.
- Read your numbers into Prometheus
The /metrics endpoint gives Prometheus your mail by source and result, the last report, every DNS check and open alerts. The scrape job and each series.
- Connect an assistant over MCP
Let Claude, ChatGPT, Cursor or another assistant read your domains, sources and reports through our MCP server, by signing in or with an API token.
- API problem types
Every error from the API names a problem type. Each page covers one code: what it means, why you get it and what to do next.
Published 27 October 2026 · Checked 27 October 2026