RevenueCat setup
Two keys from RevenueCat, pasted once, verified in place.
RevenueCat manages subscriptions, entitlements, and in-app purchase infrastructure for native apps. Connecting it to a Contrast project takes two keys and about two minutes.
Create the keys
In the RevenueCat dashboard, create a project for your app (or open the existing one), then collect two keys:
- Secret v2 API key. Under Project settings > API keys, create a secret key with read permission for offerings, packages, products, and entitlements. Scope it to this one project: a key that can see multiple RevenueCat projects verifies, but the catalog feed refuses it because Contrast would not know which catalog is yours.
- Public SDK key. The same API keys page lists the public key the Purchases SDK uses on device. It is safe to expose in the client.
Connect
Open Project Settings → Integrations, pick RevenueCat, and paste the two values:
| Secret | Runtime | Purpose |
|---|---|---|
REVENUECAT_SECRET_KEY | Server only | Catalog reads, revenue metrics, verification |
VITE_REVENUECAT_PUBLIC_KEY | Client | Configures the Purchases SDK in your app |
Press Verify. Contrast probes the RevenueCat API with the secret key and the integration flips to Verified, or tells you exactly what is wrong: an invalid key, missing permissions, or a key that sees zero or multiple projects. Fix-it links point at the RevenueCat page where the key is created.
The secret key is stored as an encrypted project secret and stays server-side. Never paste it into chat: agents read its verification status, not its value.
What connecting teaches your agents
Connecting installs the RevenueCat skill into the project. From then on, agents that add subscriptions follow the production architecture instead of improvising:
- One app-owned
subscriptionrow per user as durable truth, written by the RevenueCat webhook, with the raw provider event kept for support work. - Webhook-first verification. The SDK’s customer info is treated as an optimistic overlay that unlocks the purchasing device immediately; durable access always comes from the webhook-reconciled row.
- A single access-policy helper (like
hasPremiumAccess) so screens never inspect RevenueCat response objects. - Stable identifiers: RevenueCat’s conventional
$rc_monthlyand$rc_annualpackage identifiers and one entitlement key used everywhere. - A paywall built from
getOfferings, which renders in the browser preview and on device alike. The skill steers agents away fromreact-native-purchases-ui’s remote-template paywall, which cannot render in preview and takes the design out of your app’s hands. - A sandbox guard: production builds reject Test Store and sandbox entitlements except for explicit reviewer allowlists, decided by build identity rather than a client toggle.
How the catalog reaches the preview
Once verified, Contrast reads your project’s offerings, packages, products, and entitlements from the RevenueCat API and mirrors them into the native preview’s simulated store. The paywall you test in the browser renders the same catalog your users will see.
Details worth knowing:
- Prices come from RevenueCat’s indicative price on each product, in your project’s default currency. RevenueCat itself does not own store prices (the stores do), so a product with no price set cannot be simulated and is left out of the preview catalog. If a product is missing from your preview paywall, set its price in the RevenueCat dashboard.
- The catalog refreshes about every 15 minutes. Edit an offering in RevenueCat and the change reaches open previews on the next refresh; they reboot into the new catalog automatically.
- A freshly connected project’s first preview may boot before the catalog arrives. It lands seconds later and the preview reboots into it.
- Store preference. When a package carries products from several stores, the preview picks the closest match to what it simulates: Test Store first, then App Store.
Continue to Testing purchases in preview for what the simulated store can do, and Shipping paid apps for the App Store side.