Segments are reusable audiences. Attach one to a campaign via targetSegmentIds and the campaign only fires for members in that audience — letting you run VIP bonuses, win-back offers, or store-specific rewards without touching the earn rule.
A dynamic segment is a rule tree of AND/OR operators over member-stat fields. Conditions support eq neq gt gte lt lte. Available fields include lifetime totals (lifetime_points, total_spend_cents), rolling windows (spend_cents_30d, txn_count_90d), and RFM quintiles (rfm_recency, rfm_frequency, rfm_monetary).
curl -X POST ".../tenants/$TENANT_ID/segments" \
-H "X-API-Key: sk_test_YOUR_KEY" \
-H "Content-Type: application/json" \
-d '{
"name": "Active High-Spenders (30 days)",
"type": "DYNAMIC",
"rules": {
"operator": "AND",
"conditions": [
{ "field": "spend_cents_30d", "op": "gte", "value": 50000 },
{ "field": "txn_count_30d", "op": "gte", "value": 3 }
]
}
}'Set targetSegmentIds on the campaign. A campaign with one or more target segments only fires for members in at least one of them; leave it empty to target everyone.
curl -X PATCH ".../tenants/$TENANT_ID/campaigns/$CAMPAIGN_ID" \
-H "X-API-Key: sk_test_YOUR_KEY" \
-H "Content-Type: application/json" \
-d '{ "targetSegmentIds": ["segment-uuid-1"] }'Dynamic membership is recomputed from the latest member stats — rolling windows and RFM scores are refreshed on a nightly schedule, and you can force a re-evaluation any time with the refresh endpoint. Use POST /segments/preview to dry-run a rule and see the match count before saving.
*_30d, *_90d) and RFM scores reflect the most recent stats refresh, not live transaction state. A brand-new member reads 0 for these until the next refresh runs. Full field list and endpoints are in the Segments API reference.