Track API
The Track API records one customer event per request. An event is one action that a person took, such as completing an order or starting a trial. JustAI returns 202 once it has durably accepted the event. Events with a userId can start, advance, or end journeys, and they can count as conversions.
Send customer events walks through naming and planning events. This page is the field-by-field reference.
Endpoint
Section titled “Endpoint”POST https://ingest.justwords.ai/api/track/{org_slug}X-Api-Key: YOUR_API_KEYContent-Type: application/json| Header | Required | Value |
|---|---|---|
X-Api-Key |
Yes, or send the key in Authorization |
Your JustAI API key. Authorization: Bearer and HTTP Basic also work. See Authentication. |
Content-Type |
Recommended | application/json |
X-JustAI-Environment |
Non-production environments only | The environment key, for example staging. Leave it out for Production. See Environments. |
Request body
Section titled “Request body”Send one JSON object with these fields:
| Field | Type | Required | Rules |
|---|---|---|---|
type |
string | Yes | Must be exactly "track". |
messageId |
string | Yes | The event’s unique ID. Must not be empty. |
event |
string | Yes | The event name. Must not be empty. JustAI matches names exactly: case-sensitive and not trimmed. |
timestamp |
string | Yes | When the action happened, in ISO 8601 with Z or a numeric offset. See Timestamps. |
userId |
string or null |
userId, anonymousId, or both |
Your ID for the person, the same one you send to Identify. An empty or whitespace-only string counts as absent. |
anonymousId |
string or null |
userId, anonymousId, or both |
An ID for a person you have not identified. Same rules as userId. |
properties |
object | No | Details of the event. Defaults to {}. null or an array returns 400. |
context |
object | No | Defaults to {}. JustAI saves it with the event. null returns 400. |
integrations |
object | No | Defaults to {}. JustAI saves it with the event. null returns 400. |
JustAI ignores every other top-level field, including sentAt, originalTimestamp, receivedAt, channel, version, writeKey, and projectId. A full Segment or RudderStack track payload works as it is.
Three more rules apply to the fields:
- JustAI does not trim
messageIdorevent. A value made of spaces passes validation and is stored as sent, so always send a meaningful ID and name. - Do not name an event
profile_fields_changedorsubscription_changed. JustAI uses those names for its own events. - Send every ID as a string. A number returns
400.
Timestamps
Section titled “Timestamps”timestamp uses the same format as Identify: an ISO 8601 date-time string with Z or a numeric offset, such as 2026-10-01T12:05:00Z. A value with no time zone, a space in place of T, a date alone, or an epoch number returns 400. Identify timestamps lists every accepted and rejected form.
Track has no time bounds. It accepts dates before 1970 and dates in the future. Send the time that the action happened, not the time that you send the request.
Identity
Section titled “Identity”- Send the same
userIdthat you send to Identify. Identify removes leading and trailing spaces fromuserId, but Track stores it exactly as sent, so send user IDs without spaces. - Track does not create or update customer profiles. Send profile data with the Identify API.
- A journey looks up the person by
userId. Before you send an event that starts an email journey, send Identify withtraits.emailfor that person. - Events with only an
anonymousIdappear in Events > Custom events. They never start or advance journeys, and they never count as conversions. JustAI does not link them to a profile later, even after an Identify call for the same person.
Journeys and conversions
Section titled “Journeys and conversions”When a published journey uses an event name, a Track event with that exact name and a non-empty userId can:
- start the journey, when its entry is Event triggered
- end a Wait until step
- trigger an exit
Names match exactly, including case. A journey reacts only to events that JustAI receives after the journey is published. After you publish a journey, wait about a minute before you send a test event. Events that arrive in the first moments after publishing can miss the journey. To check that an event reached a journey, see Confirm that an event reaches a journey.
Journey event pickers read the Events > Custom events list, which shows the event names JustAI received in the last 30 days. Send one test event with the exact name, and build the journey after the name appears in Custom events.
A Track event can also be a journey’s conversion goal, set in the journey’s analytics under Measurement > Key metric. A conversion counts when a person sends the event after entering the journey, within the attribution window. JustAI matches the person by userId.
Size limits
Section titled “Size limits”- Each event must be under about 1 MB. The size JustAI counts is larger than your request body, especially when values contain many quotes, so keep each event well under 1 MB. A larger event returns
413with{"error":"Track event is too large"}. - An event that starts or advances a journey must keep its properties and IDs under 128 KB, with
propertiesnested no more than 100 levels deep. Its properties must not contain the null character,\u0000. An event that breaks these limits still returns202and counts for analytics, but it does not trigger a journey.
Example
Section titled “Example”curl -X POST "https://ingest.justwords.ai/api/track/$JUSTAI_ORG_SLUG" \ -H "X-Api-Key: $JUSTAI_API_KEY" \ -H "Content-Type: application/json" \ -d '{ "type": "track", "messageId": "order-5678-completed", "userId": "user-1234", "event": "Order Completed", "timestamp": "2026-10-01T12:05:00Z", "properties": { "order_id": "order-5678", "total": 49.5, "currency": "USD" } }'{"message_id":"order-5678-completed","status":"accepted"}Responses
Section titled “Responses”| Status | Body | Meaning |
|---|---|---|
202 |
{"message_id":"...","status":"accepted"} |
JustAI durably accepted the event. message_id echoes your messageId. |
400 |
{"error":"..."} |
The body failed validation. See Errors. |
413 |
{"error":"Track event is too large"} |
The event is over the size limit of about 1 MB. Remove large values from properties and context. |
503 |
{"error":"Event storage is unavailable"} |
JustAI could not accept the event at that moment. Retry with the same body and messageId. |
Authentication, path, and server errors are the same for all three APIs. See Errors and retries.
A 202 means that JustAI accepted the event. To check that the event reached your journeys and find the run it started, see Confirm that an event reaches a journey.
Duplicates
Section titled “Duplicates”messageId is the event’s identity. JustAI treats Track events that share a messageId as one event, so a retry does not count twice and does not start a journey twice.
- The API returns
202again for a repeatedmessageId. It does not report duplicates. - Reuse a
messageIdonly to retry the same event with the same body. - Do not reuse a
messageIdto correct an event. JustAI can’t edit or delete an accepted event. If you send a corrected event with a newmessageId, JustAI records it in addition to the original, and it can start a matching journey again. To remove events, contact your JustAI team.
Errors
Section titled “Errors”A 400 from Track contains only the first problem’s message, and the message does not name the field. JustAI checks the fields in this order: type, messageId, userId, anonymousId, event, timestamp, context, integrations, properties, and then the rule that at least one ID is present.
| Cause | Body |
|---|---|
| The body is not valid JSON | {"error":"Invalid JSON"} |
type is missing or is not "track", including a {"batch": [...]} envelope |
{"error":"Invalid literal value, expected \"track\""} |
messageId, event, or timestamp is missing |
{"error":"Required"} |
messageId or event is an empty string |
{"error":"String must contain at least 1 character(s)"} |
timestamp has the wrong format |
{"error":"Invalid datetime"} |
timestamp, messageId, userId, or anonymousId is a number |
{"error":"Expected string, received number"} |
properties, context, or integrations is null |
{"error":"Expected object, received null"} |
properties, context, or integrations is an array, or the body is an array |
{"error":"Expected object, received array"} |
Neither userId nor anonymousId has a value |
{"error":"At least one of userId or anonymousId is required"} |
Verify an event
Section titled “Verify an event”New event names can take time to appear in Events > Custom events. Journey triggers, waits, and exits do not wait for this list. To see an event in JustAI:
-
At the bottom of the left sidebar, check the environment shown under your name.
If it is not the environment that you sent the event to, open the account menu, select Environment, and select Switch next to that environment.
-
Open Events > Custom events and select Refresh.
The event name appears in the list.
-
Select the event name.
The event page shows Last seen and Recent events, including the user each event came from.
If an accepted event still doesn’t appear after you refresh, contact your JustAI team with its messageId.
Confirm that an event reaches a journey
Section titled “Confirm that an event reaches a journey”Events > Activity lists a Track event only when a published journey uses its name. Use it to confirm that your events reach the journeys your marketing team builds. This list does not have the Custom events delay.
-
Publish the journey that uses the event, and wait about a minute. Events that arrive in the first moments after publishing can miss the journey.
-
Send one Track event with the exact event name for a test
userIdthat already has a profile withtraits.email.The response is
202. -
In JustAI, check that the environment you sent the event to is selected, then open Events > Activity.
-
Enter the test user ID in Search events. To narrow the list, select Filter events and select
track-apiunder Source.The event appears with its name under Type and
track-apiunder Source. Status showsprocessedonce your journeys have handled the event. If it showspending, select Refresh after a moment. -
Open Users, search for the test user ID, and open the person. Under Activity, select Events.
The same event appears in the person’s activity.
If the event does not appear, check that the journey is published, that the event name matches the journey’s event exactly, including case, that the event has a userId, and that it is within the journey size limits. Then send a new test event with a new messageId. If Status shows failed, contact your JustAI team with the event’s messageId.
To see what the journey did for your test person, open the journey from Journeys. A published journey opens on its Live view, with Recent runs beside it. Enter the test user ID in Email or user ID, press Enter, and select the run to see each step it reached.
