Expo + RevenueCat: why your paywall is empty
Your paywall renders but the offerings array is empty. You have checked the code five times. The code is almost certainly fine — this is a configuration and propagation problem, and it has a small number of causes.
The seven causes, in order
1. The Paid Applications Agreement is not active. Until you have signed it and completed banking and tax details in App Store Connect, no product will ever load. This is the most common cause by a wide margin and it produces no error message.
2. Product identifiers do not match exactly between the store and RevenueCat. They are case-sensitive and whitespace-sensitive.
3. Products exist but are not attached to an offering. RevenueCat returns offerings, not products — a product with no offering is invisible to the SDK.
4. You are testing in Expo Go. In-app purchases require native billing APIs that Expo Go does not include. You need a development build.
5. Products are still propagating. App Store Connect can take several hours after creation.
6. Wrong store account signed in on the device. Sign out of the production account and use a Sandbox tester.
7. Bundle identifier mismatch between the build and the store record — common when you use separate dev, preview and production bundle IDs.
How to find out which one it is
Turn on debug logging before you change anything else. RevenueCat's SDK names the exact cause in almost every one of these cases, which saves you from guessing.
import Purchases, { LOG_LEVEL } from "react-native-purchases";
Purchases.setLogLevel(LOG_LEVEL.DEBUG);
await Purchases.configure({ apiKey: PUBLIC_SDK_KEY });
const offerings = await Purchases.getOfferings();
console.log(JSON.stringify(offerings.current, null, 2));Build the paywall before any of this exists
The reason this problem is so painful is that most starter kits require real store configuration before you can see a paywall at all — so you are debugging your UI and your store setup simultaneously.
Nativestarter ships mock entitlements: you toggle them from a developer menu and build both sides of the paywall with no RevenueCat account, no Paid Applications Agreement, and no products. You connect the real thing once the UI is finished, and then there is only one variable left to debug.