Creem
Attribute Creem checkouts and refunds to the visits that led to them.
Use this connector when your products are sold through Creem checkout sessions. Seean verifies each delivery with the webhook secret, records checkout.completed events as orders and matches refund.created events to them. Attribution is derived on Seean’s server from the buyer’s tracked visits when the checkout metadata carries the visitor ID.
Setup
- In Seean open Settings → Integrations → Payment providers on your own website, choose Creem, select Enable and copy the webhook URL (
https://events.seean.io/api/connect/creem/<site ID>; use the exact value shown). - In Creem open Developers → Webhooks and add an endpoint with that URL.
- Make sure
checkout.completedandrefund.createdare delivered to it. - Copy the endpoint’s webhook secret and paste it into Seean, then choose Save secret. Test mode has its own secret.
- Pass the attribution metadata described below when you create checkout sessions.
Only the website owner can connect, replace or disconnect a provider; one connection per provider; demo websites cannot connect providers.
Attribution handoff
Read window.seean.attribution() in the browser, send it to your server and attach it as metadata when creating the checkout session. Creem returns the same metadata on the checkout.completed event:
// Browser
await window.seean?.ready;
const a = window.seean?.attribution?.() ?? {};
const seean = { seean_visitor_id: a.visitorId, seean_landing_path: a.landingPath, seean_converting_path: a.convertingPath, seean_campaign: a.campaign };
// send `seean` to your server with the checkout request
// Server
const res = await fetch("https://api.creem.io/v1/checkouts", {
method: "POST",
headers: { "x-api-key": process.env.CREEM_API_KEY, "Content-Type": "application/json" },
body: JSON.stringify({ product_id: "prod_123", success_url: "https://example.com/thanks", metadata: Object.fromEntries(Object.entries(seean).filter(([, v]) => v)) }),
});
const { checkout_url } = await res.json(); // redirect the visitor there
| Key | Meaning |
|---|---|
seean_visitor_id |
Links the order to the buyer’s tracked visits; touches, first and last source, landing page and time to buy are derived from that history. |
seean_landing_path |
Used only when Seean has no tracked visit for the visitor in the 90 days before the order. |
seean_converting_path |
The page where checkout started. |
seean_campaign |
Overrides the campaign derived from the tracked history. |
Static payment links carry no per-visitor metadata, so orders from them are recorded as Unattributed.
What is recorded
| Event | Result in Seean |
|---|---|
checkout.completed |
Order from object.order: amount (cents) in currency. type: recurring becomes a subscription order; other types are one-time orders. |
refund.created |
Refund of object.order. |
The order ID is the Creem order ID, the product name is object.product.name and the order time is the order’s created_at. Subscription renewals (subscription.paid) and other events are acknowledged and ignored.
Refunds
Creem order amounts exclude tax while refunds include it. A refund whose refund_amount equals the transaction’s amount_paid is recorded as a full refund of the order; a smaller refund reduces the order by the refund amount. Each refund ID is applied once. Refunds lower net revenue in the period of the original order. If the original order has not arrived, Seean returns HTTP 503 and shows Last event failed: Order not found. The provider can retry after the order arrives; the refund ID prevents double counting. A refund whose order is still missing one day after the refund was created is acknowledged and ignored, so refunds of payments Seean never recorded do not keep the endpoint failing; record those with the Order API. See delivery recovery if retries expire.
Currency
Orders are stored in the website’s reporting currency (Settings → Integrations → Revenue integration). Creem amounts are already in minor units. An order in another currency is acknowledged but not stored, and the reason appears under the provider.
Verify
Complete a checkout in Creem’s test mode with a test-mode endpoint connected. The status line under Creem shows the last event time and, if the last event could not be stored, the error. Then open Revenue for a range containing the order and check the amount, product and derived attribution. Duplicate deliveries return duplicate and change nothing.
Limits
- Seean verifies the
creem-signatureheader (hex HMAC-SHA256 of the body). Creem does not sign a timestamp, so a captured delivery could be replayed; replays are deduplicated by order and refund ID and cannot create a second order. - Renewals are not received; report them with the Order API using the Creem transaction ID as
externalId. - Request bodies above 64 KiB are rejected with 413. Events Seean does not handle are acknowledged with 200; rate limits return 429 and temporary ingestion failures return 503 so the provider can retry. See delivery recovery.
- Disable stops accepting events (the URL answers 404); remove the endpoint in Creem so it stops retrying. Existing orders are kept.
Related: Revenue attribution, Order API and refunds.
Something unclear? Contact support.