[deliver]
Deliver article · 2026-07-16 · Charlotte Rodrigues

Klaviyo Events API: send custom events safely

Short answer. Define the event and identity contract before coding. Send server-authoritative events to POST https://a.klaviyo.com/api/events with least-privilege authentication and a supported revision header. Include a stable unique_id for idempotent retries, the actual event time, structured properties, and a profile identifier. Treat 202 Accepted as queued, handle 429 with Retry-After, monitor ingestion, and use backfill: true for historical replays that must not trigger flows.

Custom events let Klaviyo respond to product, subscription, account, marketplace, offline, or operational behavior that a native integration does not provide. The API call is the easy part. Reliable identity, semantics, retries, monitoring, and lifecycle ownership determine whether the event can safely trigger customer communication.

This guide was reviewed July 16, 2026 against Klaviyo's official Events API overview, Create Event reference, rate-limit guide, and versioning policy. Always use the current reference for production code.

Start with an event contract

Create a tracking plan before an endpoint integration.

Field Example Decision
Metric name Report Generated Stable business meaning
Trigger moment Report persisted successfully Not button click or attempt
Profile identity Internal user ID Stable across email changes
Object context workspace_id Account or project relationship
Event time Source occurrence in UTC Not API delivery time
Unique ID Source event UUID Stable across retries
Required properties report_type, project_id Used by flow or analysis
Optional properties source, template Safe fallback if missing
Owner Product data team Monitors schema and delivery
Lifecycle uses Activation flow, segment Downstream dependencies

An event name should describe something that happened. Use Subscription Canceled, not Subscription Status, and define whether it occurs when cancellation is requested or becomes effective.

Avoid changing semantics behind an existing metric. If the event meaning changes materially, version the source contract or create a new metric after a migration plan.

Event versus profile property

Events record occurrences with time and context. Profile properties represent current person-level state.

For a subscription:

Flows often need both. The trigger event provides immutable context, while the current profile state can stop a later message after the situation changes.

Be cautious about update order. If the event reaches Klaviyo before a related profile update, a flow can evaluate stale state. Include essential context on the event or sequence the operations with tested behavior.

Choose a stable profile identity

The current Create Event endpoint requires at least one profile identifier such as Klaviyo profile ID, email, or phone number. Prefer a stable internal identifier or mapped Klaviyo ID where the architecture supports it. Email addresses change and can create identity fragmentation.

Document:

Do not use test domains such as example.com or test.com to validate ingestion. Klaviyo's current Events API documentation says events with those test-style addresses can return 202 and then be silently dropped. Use a controlled domain you own and safe test profiles.

Authenticate with least privilege

For a private integration, use a private API key with only the scopes required by the endpoints. Creating events currently requires events:write.

Security controls:

For a multi-account product integration, evaluate OAuth and its separate rate-limit behavior rather than asking every customer to paste unrestricted keys.

Pin an API revision

Klaviyo versions modern APIs with date-based revision headers. Pass a supported revision such as the exact date selected from the current reference. Do not copy the example date in this article as a permanent value.

Pinning provides predictable request and response behavior. Maintain:

Klaviyo's versioning policy marks beta revisions with a .pre suffix and says they should not be used in production. Use stable revisions for customer-facing systems.

Structure the Create Event request

The endpoint currently follows JSON:API conventions. Conceptually, send:

{
  "data": {
    "type": "event",
    "attributes": {
      "metric": {
        "data": {
          "type": "metric",
          "attributes": { "name": "Project Published" }
        }
      },
      "profile": {
        "data": {
          "type": "profile",
          "attributes": { "email": "qa@your-owned-domain.com" }
        }
      },
      "properties": {
        "project_id": "prj_123",
        "workspace_id": "ws_456",
        "template": "weekly-report"
      },
      "time": "2026-07-16T09:30:00Z",
      "unique_id": "90974d0d-5d62-4d78-98ee-450d74cd7090"
    }
  }
}

Use the exact current API reference and SDK types because shape and supported fields can evolve.

Use unique_id for idempotency

Klaviyo currently deduplicates events using profile, metric, and unique_id. Generate a stable unique identifier for each logical source event and reuse the same value on every retry.

Good source IDs:

Do not generate a new UUID on every retry because that defeats idempotency. Do not reuse an order ID across multiple different order events without including event type or source occurrence.

The current documentation warns that, without unique_id, events for the same profile and metric in the same second can collide because the default is derived from the timestamp. Always provide it for production event sources.

Send the actual occurrence time

Set time to when the source action occurred, not when a retry worker delivered it. This keeps event history and time-based analysis accurate.

Use an ISO 8601 timestamp with an explicit time zone, commonly UTC. Validate impossible future dates and stale source clocks.

For delayed events, decide whether the lifecycle should still trigger. A payment failure delivered six hours late may need different handling. Event timestamp accuracy does not automatically prevent a flow from acting on stale data, so use eligibility filters or freshness properties.

Keep properties useful and bounded

Event properties should support flow content, segmentation, debugging, and analysis. Examples:

Avoid sending full internal objects, large HTML, secrets, payment data, or unused personal information. Klaviyo documents payload, property count, string, array, nesting, and timestamp limits. Treat the current API reference as the authority.

Use controlled property names and types. A property that is sometimes number and sometimes string makes segmentation unreliable.

Place only truly non-segmentable large context into fields designed for that purpose, and still minimize it. Customer messaging systems are not data lakes.

Treat 202 as queued, not fully processed

The Create Event endpoint currently responds 202 Accepted after validation and submission for processing. Klaviyo explicitly says that success does not guarantee processing is complete.

Your producer should record:

For critical integrations, reconcile source events with Klaviyo event retrieval or profile activity samples, taking processing latency into account. Do not perform a read immediately and declare failure when the pipeline is asynchronous.

Handle errors and rate limits

Classify responses:

Klaviyo uses burst and steady windows, with endpoint-specific limits published in the reference. Non-429 responses can include rate-limit headers. A 429 currently replaces those with Retry-After.

Use a queue, concurrency control, exponential backoff, jitter, and a dead-letter path. Keep the same unique_id through retries. Do not hammer the endpoint after an outage.

Alert on sustained error rate, dead-letter depth, delivery latency, and unknown validation errors.

Use bulk endpoints for appropriate volume

When backfilling or sending high event volume, review current bulk endpoint behavior and limits. Batch by operational size, retain individual source IDs, and handle partial or whole-request validation according to the reference.

Do not use live flow-triggering events for a historical replay without a lifecycle plan. A backfill of past orders can send years of post-purchase email.

Use backfill: true for historical replay

Klaviyo's current Events API supports a backfill boolean for historical data. With backfill: true, the event remains available in event data and segmentation but does not trigger flows.

Use it when:

Use time and stable unique_id as well. Test backfill in a safe account or profile before a large import. Confirm downstream reporting and segmentation behavior matches the current documentation.

If some missed events should trigger a customer action, do not remove backfill protection globally. Create an explicit recovery audience and communication plan with freshness, consent, and customer relevance checks.

Design flow safety around events

An API event should not have unrestricted power to send.

Add flow controls:

Use a synthetic or controlled event to test every branch. Then run a small production cohort before broad live status.

Monitoring and reconciliation

Create dashboards for:

Compare by hour and day with expected seasonality. Alert on both drop and spike. A tenfold event increase can be a duplicate bug even if every API response is successful.

Maintain a runbook with key rotation, revision upgrade, replay procedure, flow pause, event source owner, and incident contacts.

Implementation test plan

  1. Valid event for an existing controlled profile.
  2. Valid event that creates or updates a permitted profile attribute, if used.
  3. Duplicate retry with the same unique_id.
  4. Two legitimate events in the same second with different IDs.
  5. Missing required property.
  6. Wrong type and unknown enum value.
  7. Network timeout followed by safe retry.
  8. Simulated or controlled 429 handling.
  9. Historical event with backfill: true.
  10. Profile unsubscribed or suppressed for the target channel.
  11. Conversion or cancellation during a flow delay.
  12. Event volume spike and alert.

Verify the event in Klaviyo, flow behavior, message preview, logs, and downstream reports. Do not use only the HTTP response as QA evidence.

FAQ

What endpoint creates a Klaviyo event?

The current endpoint is POST https://a.klaviyo.com/api/events. Use the official current reference, required authentication, supported revision, and JSON:API payload.

Why did I receive 202 but not see the event?

202 means accepted for asynchronous processing, not guaranteed complete. Allow processing time, verify identity and payload, check test-domain restrictions, deduplication, logs, and the current status page.

How do I prevent duplicate Klaviyo events?

Provide a stable unique_id per logical event and reuse it on retries. Klaviyo currently deduplicates by profile, metric, and unique ID.

How should I import historical events?

Provide the original time, stable IDs, and use backfill: true when the replay must not trigger flows. Test a small batch and reconcile counts.

How should 429 errors be retried?

Honor Retry-After, queue requests, and use bounded backoff with jitter. Respect the endpoint's burst and steady limits and preserve idempotency.

Make custom events dependable enough to trigger customers

Deliver defines event contracts, implements reliable ingestion, and validates lifecycle behavior from source system to message. Request a Klaviyo Events API implementation review.

CR
Charlotte Rodrigues · CRM Lead at Deliver. Questions about this article? charlotte@agence-deliver.com

Want to apply this to your stack?

Spend 30 minutes with Charlotte to review your CRM setup, size the opportunity and leave with a practical action plan.

Book a 30-minute call →