Both require the
read:experience scope, not the read:creator scope the rest of the creator.* domain uses. Both are delivered in the Standard-Webhooks envelope; the fields below describe the data object.
Access ended, not billing changed
Delivery
These two topics do not use thecreator.* delivery model. Other creator.* events fan out to every app holding the required scope for that creator. These reach only:
- the app that owns the experience, resolved from the subscription’s own
app.uuid, unconditionally, and - the creator’s connector destinations subscribed to the topic.
Experience subscription resource
access_ends_at and expires_at agree only on a period-end cancellation. Every other end_reason revokes mid-period, leaving expires_at the later of the two. Compare them to tell the two cases apart: access_ends_at < expires_at means the fan lost time they had paid for.End reasons
end_reason is a required discriminator on creator.experience_subscription.deactivated.
The payload carries no retry state. A
payment_failed event tells you the charge that was due has been declined and access is gone as of access_ends_at, nothing more, any retry state would already be stale by the time you process it. Revoke on it and wait for creator.experience_subscription.activated.
Activation reasons
activation_reason is a required discriminator on creator.experience_subscription.activated.
Example: creator.experience_subscription.deactivated
A cancellation reaching the end of its paid period, the one case where access_ends_at and expires_at agree.
access_ends_at before expires_at:
Example: creator.experience_subscription.activated
The recovery case, the reason an app that revokes has to handle this topic.
Revoking access on subscription end
Gate the resource on one pair of handlers: revoke ondeactivated, grant on activated. Verify the signature first, return 2xx immediately, and do the revocation out of band, see Delivery, Retries and Idempotency.
- Revoke on the event, not on a cancellation.
cancel_at_period_end: trueon adeactivatedevent is context, it tells you the fan chose to leave rather than failed to pay. It is never itself the trigger. - Always pair revoke with grant. Revoking on
deactivatedwithout handlingactivatedpermanently locks out any fan whose renewal recovered after a declined charge.
Access can also lapse silently at
expires_at. A subscription grants access only while it is not deleted and expires_at is in the future. The hourly expiry sweep defers a row when a renewal is still settling or an upstream lookup fails, so the fan loses access on the clock and no event is sent until a later sweep resolves the row. Treat expires_at as a deadline in its own right: expire your own cached grant at expires_at and let activated extend it, rather than waiting only for deactivated.See also
- Creator webhooks overview, the shared envelope and the full event table
- Creator Subscriptions, the separate profile-subscription lifecycle
- Signature verification
- Delivery, Retries and Idempotency
- Scopes