The Workloom API
Read and write the contacts, companies and deals in your workspace, with their notes, tasks and lists. Put contacts into outreach, read the revenue report, and get a signed webhook when something happens. One key, one base URL, JSON in and out.
https://api.useworkloom.com/api/public/v1Your first call
Make a key
In Workloom, open Settings › API and webhooks and choose New key. Start with a test key: it reads your records and changes nothing.
Call GET /
Send the key as a bearer token. The answer names the workspace, the key, its scopes and whether it is live or test.
Make your first write
Add a contact with POST /contacts. A test key answers with what would be saved. A live key saves it, and it is in Workloom straight away.
curl "https://api.useworkloom.com/api/public/v1/" \
-H "Authorization: Bearer $WORKLOOM_KEY"const res = await fetch("https://api.useworkloom.com/api/public/v1/", {
method: "GET",
headers: {
Authorization: `Bearer ${process.env.WORKLOOM_KEY}`
}
});
const data = await res.json();import os, requests
res = requests.get(
"https://api.useworkloom.com/api/public/v1/",
headers={"Authorization": f"Bearer {os.environ['WORKLOOM_KEY']}"},
)
data = res.json()curl -X POST "https://api.useworkloom.com/api/public/v1/contacts" \
-H "Authorization: Bearer $WORKLOOM_KEY" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: $(uuidgen)" \
-d '{
"first_name": "Priya",
"last_name": "Nair",
"email": "priya@brightline.example"
}'const res = await fetch("https://api.useworkloom.com/api/public/v1/contacts", {
method: "POST",
headers: {
Authorization: `Bearer ${process.env.WORKLOOM_KEY}`,
"Content-Type": "application/json",
"Idempotency-Key": crypto.randomUUID()
},
body: JSON.stringify({
"first_name": "Priya",
"last_name": "Nair",
"email": "priya@brightline.example"
})
});
const data = await res.json();import os, uuid, requests
res = requests.post(
"https://api.useworkloom.com/api/public/v1/contacts",
headers={"Authorization": f"Bearer {os.environ['WORKLOOM_KEY']}", "Idempotency-Key": str(uuid.uuid4())},
json={
"first_name": "Priya",
"last_name": "Nair",
"email": "priya@brightline.example"
},
)
data = res.json()Playground
Pick an endpoint, edit the body, and the code changes as you type. Send answers with a sample, including the error the API gives for a bad body. Nothing is sent to Workloom.
What’s in the API
Versions
New fields, endpoints, events and error codes arrive without notice and reach every version, so ignore what you do not know. A change that would break an integration comes as a new dated version, and reaches nobody until they ask for it. The latest is 2026-10-07.
Every key and every webhook endpoint is pinned to the version that was current when it was made. A request without the Workloom-Version header is answered in its key’s version, and a delivery is shaped in its endpoint’s version. To try a newer version, send Workloom-Version: <version> on a request; to move an endpoint, change its workloom_version. Every answer and every delivery says its version in the Workloom-Version header. An old version stops working only after 6 months’ notice in the changelog. The path, /api/public/v1, changes only for a redesign of the whole API.
| Version | What it is |
|---|---|
2026-10-07 | The first dated version: the API as it was on 7 October 2026. Every key and endpoint made before then is on it. |
Headers you send
| Header | Example | What it does |
|---|---|---|
Authorization | Bearer wl_live_… | Your key. Needed on every call except /openapi.json. |
X-API-Key | wl_live_… | The same key, if you cannot send Authorization. |
Idempotency-Key | any unique string | Makes a POST safe to retry. Kept 24 hours. |
Content-Type | application/json | Needed when you send a body. |
Workloom-Version | 2026-10-07 | Answers this request in that version. Leave it out to use your key’s. |
Headers you get back
| Header | What it says |
|---|---|
Workloom-Mode | live or test: which kind of key made the request. |
Workloom-Version | The version this answer is in. |
X-RateLimit-Limit | Requests a minute the key may make. |
X-RateLimit-Remaining | Requests left this minute. |
Retry-After | Only on a 429: seconds to wait. |
Idempotent-Replayed | true when the answer is the stored one for a repeated Idempotency-Key. |
The whole API is also described in an OpenAPI 3.1 file, which needs no key.