Getting Started
Guides
REST API: Campaigns
Affiliates
Conversions
Affiliate Teams
SCALE
Coupons
Payouts
Other
Webhooks
MCP Server (AI)
Wire Apple App Store Server Notifications v2 to LinkJolt. Offer-code attribution. No SDK.
15 min read
DID_RENEWis_test=trueApp Store Server Notifications v2 (ASSN v2) is Apple's server-to-server event stream for subscription lifecycle events. Each notification arrives at your configured URL as a JSON body containing a single signedPayload field, a JWS signed with Apple's certificate chain rooted at Apple Root CA - G3.
LinkJolt runs a dedicated endpoint per merchant. You never implement the verification yourself, paste the URL into App Store Connect and we handle the JWS chain check, event mapping, and conversion insertion.
Go to Integration Hub → Other Platforms → Apple In-App Purchases and enter:
com.example.app). Required. Used to validate bundleId inside Apple's signed payload.1234567890). Required for Production notification verification. Optional if you're only testing in Sandbox.Both values appear in App Store Connect → My Apps → [your app] → App Information.
From your LinkJolt Apple IAP setup screen, copy the Production and Sandbox URLs. The shape is:
# Production
https://www.linkjolt.io/api/webhooks/apple-iap/<your-merchant-user-id>
# Sandbox
https://www.linkjolt.io/api/webhooks/apple-iap/<your-merchant-user-id>/sandboxIn App Store Connect: General → App Information → scroll to App Store Server Notifications. For each URL field:
Offer codes are Apple's officially-supported attribution mechanism for “influencer partnerships with exclusive codes” and “co-marketing partnerships” (Apple's own words).
In App Store Connect:
Limits: up to 25,000 codes per batch; up to 1,000,000 redemptions per app per quarter.
For each offer code, register it against a campaign and affiliate via the LinkJolt dashboard or the Developer API:
curl https://www.linkjolt.io/api/v1/coupons \
-X POST \
-H "Authorization: Bearer lj_pk_your_key" \
-H "Content-Type: application/json" \
-d '{
"provider": "apple",
"code": "PARTNER_JEN",
"appleOfferType": 3,
"campaignId": "cmp_...",
"affiliateId": "aff_..."
}'Apple offer identifiers are case-sensitive: register them exactly as you configured them in App Store Connect.
LinkJolt automatically handles all subscription lifecycle events:
SUBSCRIBED (INITIAL_BUY / RESUBSCRIBE), inserts a new conversion, attributes to the affiliate matching offerIdentifier.DID_RENEW: inserts a recurring conversion linked to the parent via originalTransactionId. Requires recurring commissions enabled on the campaign.REFUND / REVOKE: marks the matching conversion as rejected.REFUND_REVERSED: reverts rejection back to pending so you can re-approve.EXPIRED, DID_FAIL_TO_RENEW, PRICE_INCREASE, RENEWAL_EXTENDED, DID_CHANGE_RENEWAL_PREF, DID_CHANGE_RENEWAL_STATUS, GRACE_PERIOD_EXPIRED, OFFER_REDEEMED: logged, no commission side-effects.End-to-end sandbox flow:
SUBSCRIBED notification to your Sandbox URLis_test=true, and shows it in your dashboard under “Test data”To exercise the webhook without a real purchase, Apple's POST /inApps/v1/notifications/test endpoint fires a signed TEST notification. Requires a signed JWT with your App Store Connect API key, see Apple's Request a Test Notification docs.
Apple retries failed deliveries 5 times over 72 hours (at 1h, 12h, 24h, 48h, 72h). LinkJolt always returns HTTP 200 for handled or intentionally-ignored events, and 500 only on transient database errors. Apple retries those legitimately. Idempotency is enforced by a unique index on conversions.order_id (= Apple's transactionId), so duplicate deliveries are safe. Sandbox notifications are not retried.
Offer-code attribution is deterministic and 100% accurate on redemption. It does not attempt ambient click-to-install-to-purchase attribution, that requires an MMP and is probabilistic post-ATT on iOS. For indie subscription apps, offer codes are the more honest and higher-quality signal. If a user buys your subscription without redeeming an affiliate code, that conversion is recorded but unattributed.