Skip to main content
GUIDE · AMAZON ADS10 min read

Amazon Ads Off-Amazon events API with TrackLayer

A long-form implementation guide for routing TrackLayer server-side events into Amazon Ads Off-Amazon measurement with stable identity, clear event mapping, retry-safe delivery, and practical testing before production rollout.

Context

Why send Off-Amazon events server-side

Amazon Ads only becomes operationally useful when the conversion it sees is the same conversion your business confirmed. Browser tags are useful for collection, but they are fragile at the exact moment the event starts to matter. Users switch devices, consent changes mid-session, checkout crosses domains, and ad blockers suppress scripts that looked fine in staging. A TrackLayer destination changes the source of truth from a page render to a backend-confirmed action.

That matters most for purchases, qualified leads, registrations, and checkout milestones. When TrackLayer receives one of those actions, it already knows the event time, the merchant context, and the normalized identity it is allowed to use. The Amazon payload becomes a destination-specific projection of the same business fact. In practice, that means fewer missing conversions, cleaner debugging, and a rollout path where each event can be tested deterministically before media teams depend on it.

The operating model is simple: collect once, normalize once, then route to Amazon with a small payload that is easy to reason about. TrackLayer capture → normalize → dispatch is a better operating pattern than trying to reconstruct the conversion inside a destination worker after identity or value has already drifted.

Requirements

Prerequisites

01

An Amazon Ads account with access to the advertiser profile that should receive Off-Amazon events, plus the `profile_id` used in the `Amazon-Advertising-API-Scope` header.

02

A server-side OAuth flow that can refresh or rotate the bearer token TrackLayer uses for Amazon Ads requests, with client credentials stored outside browser code.

03

A canonical TrackLayer event plan for `purchase`, `lead`, `sign_up`, `add_to_cart`, `begin_checkout`, `view_item`, and related mid-funnel actions before implementation starts.

04

Consent and retention rules for hashed identifiers, especially email, phone, and mobile advertising IDs, so the match strategy is legally and operationally explicit.

05

A staging or WireMock-backed test path where requests, payload shape, response bodies, latency, and retry outcomes can be inspected before production traffic is enabled.

Build

Step-by-step setup

Step 1

Choose the events Amazon should receive

Do not begin with the whole internal event catalog. Start with the actions Amazon Ads will actually use for optimization and reporting. In most cases that means purchase, lead, sign up, add to cart, begin checkout, page visit, and a carefully chosen custom event if the business needs one. TrackLayer should stay canonical internally, then map only the events Amazon can interpret consistently. That keeps dashboards readable and makes failed delivery analysis much easier.

export const amazonEventMap = {
  page_view: "PageVisit",
  view_item: "ViewContent",
  add_to_cart: "AddToCart",
  begin_checkout: "InitiateCheckout",
  purchase: "Purchase",
  sign_up: "CompleteRegistration",
  lead: "Lead",
};
Step 2

Capture identifiers before the user disappears

The strongest Amazon setup is built before checkout or form submission breaks continuity. Persist the identifiers you actually need while the session is still intact, then let the backend attach them later. In this implementation, Amazon receives `matchKeys`, which can contain hashed email, hashed phone, and MAID. That means the front of the funnel has to preserve enough first-party identity for the backend to build those keys without inventing data after the fact.

const event = {
  user_data: {
    email: "buyer@example.com",
    phone: "+15551234567",
  },
  custom_data: {
    madid: "AEBE52E7-03EE-455A-B3C4-E57283966239",
  },
};
Step 3

Normalize and hash match keys on the server

Amazon match quality gets worse when identity handling is inconsistent. TrackLayer should normalize email and phone, hash them server-side, and only then construct the `matchKeys` array. The rule is straightforward: if the identifier is not present or not allowed, omit it. Do not send empty strings, placeholder values, or browser-derived guesses. A clean payload with fewer trustworthy keys is better than a noisy payload that looks complete but cannot match reliably.

{
  "matchKeys": [
    { "type": "EMAIL", "values": ["973dfe463ec85785f5f95af5ba3906ee..."] },
    { "type": "PHONE", "values": ["f39a67bb4bdfb0b57c3db7689c8e8896..."] },
    { "type": "MAID", "values": ["AEBE52E7-03EE-455A-B3C4-E57283966239"] }
  ]
}
Step 4

Send one event shape for every retry

Your backend should generate the event once, preserve the original event time, and send the same business fact on every retry. In the current TrackLayer adapter, the Amazon payload is intentionally compact: event name, ISO timestamp, conversion value when present, country code, and match keys. That is useful operationally because it reduces places where drift can happen. A transport retry should be the same conversion sent again, not a new conversion assembled from slightly different queue state.

POST https://advertising-api.amazon.com/offAmazonEvents/2023-11-13/events
Authorization: Bearer amzn_access_token
Amazon-Advertising-API-ClientId: amzn_client_id
Amazon-Advertising-API-Scope: 1234567890
Content-Type: application/json

{
  "events": [
    {
      "name": "Purchase",
      "timestamp": "2026-04-24T08:45:12.000Z",
      "conversionValue": 129.99,
      "countryCode": "US",
      "matchKeys": [
        { "type": "EMAIL", "values": ["973dfe463ec85785f5f95af5ba3906ee..."] }
      ]
    }
  ]
}
Step 5

Log responses with operational context

A destination integration is only production-ready if failures are debuggable under pressure. Log the outbound event name, platform ID, event ID from your internal system, response status, latency, and the count of identifiers attached. Do not log raw email or phone. The useful operational path is capture → normalize → dispatch → inspect, not capture everything and hope the destination dashboard explains the problem later. Your logs should tell you whether the issue is mapping, identity availability, auth, or transport.

{
  "platform": "amazon_ads",
  "event_id": "ord_10492_purchase",
  "amazon_event": "Purchase",
  "status_code": 200,
  "latency_ms": 142,
  "match_key_count": 1
}
Schema

Event mapping

TrackLayer should stay destination-neutral while Amazon receives the event names it expects. The mapping table below is the useful operational layer: it tells paid media, engineering, and QA which canonical event becomes which Amazon event and what data needs to survive the trip.

TrackLayer canonical eventAmazon event nameTypical fields
page_viewPageVisittimestamp, countryCode, matchKeys
view_itemViewContenttimestamp, countryCode, matchKeys
add_to_cartAddToCarttimestamp, countryCode, matchKeys, conversionValue when useful
begin_checkoutInitiateCheckouttimestamp, countryCode, matchKeys, conversionValue when available
purchasePurchasetimestamp, conversionValue, countryCode, matchKeys
sign_upCompleteRegistrationtimestamp, countryCode, matchKeys
leadLeadtimestamp, countryCode, matchKeys
customCustomtimestamp, countryCode, matchKeys, optional conversionValue
Validation

Testing the integration

Load the WireMock stub and prove the transport path

Before debating attribution, prove the request path. Post the Amazon WireMock mapping into the local admin API, then run the smoke script so the adapter can exercise `/offAmazonEvents/2023-11-13/events` with the same transport code used by the platform registry.

Verify mapping and payload shape

Inspect one purchase and one lead. Confirm the canonical TrackLayer event mapped to the expected Amazon event name, that `countryCode` is present, and that `matchKeys` contain only normalized, allowed identifiers.

Test empty-identity fallbacks intentionally

Run at least one case where email and phone are absent. The payload should still be structurally valid and operationally visible, which tells you whether the implementation degrades cleanly instead of crashing or fabricating data.

Operations

Troubleshooting common failure modes

401 or 403 from Amazon Ads

Treat this as credentials or advertiser-scope failure first. Check the bearer token, `Amazon-Advertising-API-ClientId`, and the `profile_id` in `Amazon-Advertising-API-Scope` before touching payload code.

Low match rate despite accepted responses

Audit normalization and identifier availability. Most weak-match incidents come from missing email or phone, inconsistent hashing inputs, or sessions that lost identity before the backend event was created.

Purchase value is missing in reports

Verify TrackLayer actually populated `event.value` upstream. The adapter only sends `conversionValue` when the value exists, so this is usually a source-event issue, not an Amazon transport issue.

Country defaults to the wrong region

The adapter falls back to `US` when `user_data.country` is absent. If your merchant operates elsewhere, populate country explicitly in the source event instead of assuming the destination can infer it.

Duplicate conversions after retries

Keep the retry payload tied to one internal event ID and one business fact. A retry should resend the same conversion, not rehydrate a fresh event from mutable order state.

FAQ

Questions teams ask early

What does Off-Amazon mean here?

It means the conversion happened on your property after Amazon media drove the visit there. TrackLayer is not reporting marketplace orders. It is sending server-side website or app outcomes back into Amazon Ads measurement.

Do I need all match key types for every event?

No. Use the identifiers you actually have and are allowed to send. Email alone is often enough to start. The important part is consistency and normalization, not stuffing the payload with partial guesses.

Should TrackLayer send browsing events as well as purchases?

Only if the business has a reason to use them. Mid-funnel events can help when purchase volume is low, but they also increase operational noise. Start with the few actions Amazon can optimize against meaningfully.

Where should hashing happen?

On the server or in the destination worker, immediately before dispatch. Do not expose hashing logic as a replacement for backend identity handling in the browser.

What is the practical rollout order?

Start with one purchase and one lead in a controlled environment, verify transport and mapping, then widen the event list. Capture → normalize → dispatch is a safer rollout path than enabling every event at once.

We use essential cookies to keep the site secure and functional. Analytics and third-party tags run only with your consent. See our Cookie Policy.

We use essential cookies to keep the site secure and functional. Analytics and third-party tags run only with your consent. See our Cookie Policy.