{"id":29684940,"url":"https://github.com/superwall/expo-superwall","last_synced_at":"2026-02-28T00:23:30.420Z","repository":{"id":297203692,"uuid":"987634301","full_name":"superwall/expo-superwall","owner":"superwall","description":null,"archived":false,"fork":false,"pushed_at":"2025-07-15T17:05:35.000Z","size":17186,"stargazers_count":24,"open_issues_count":4,"forks_count":2,"subscribers_count":1,"default_branch":"main","last_synced_at":"2025-07-18T17:39:27.060Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":null,"language":"TypeScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/superwall.png","metadata":{"files":{"readme":"README.md","changelog":"CHANGELOG.md","contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null}},"created_at":"2025-05-21T11:09:57.000Z","updated_at":"2025-07-17T14:50:30.000Z","dependencies_parsed_at":"2025-06-20T18:39:21.788Z","dependency_job_id":null,"html_url":"https://github.com/superwall/expo-superwall","commit_stats":null,"previous_names":["superwall/superwall-expo","superwall/expo-superwall"],"tags_count":10,"template":false,"template_full_name":null,"purl":"pkg:github/superwall/expo-superwall","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/superwall%2Fexpo-superwall","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/superwall%2Fexpo-superwall/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/superwall%2Fexpo-superwall/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/superwall%2Fexpo-superwall/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/superwall","download_url":"https://codeload.github.com/superwall/expo-superwall/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/superwall%2Fexpo-superwall/sbom","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":265827830,"owners_count":23835062,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":[],"created_at":"2025-07-23T03:09:47.570Z","updated_at":"2026-01-16T20:13:28.858Z","avatar_url":"https://github.com/superwall.png","language":"TypeScript","funding_links":[],"categories":[],"sub_categories":[],"readme":"\u003cp align=\"center\"\u003e\n  \u003cbr /\u003e\n  \u003cimg src=https://user-images.githubusercontent.com/3296904/158817914-144c66d0-572d-43a4-9d47-d7d0b711c6d7.png alt=\"logo\" height=\"100px\" /\u003e\n  \u003ch3 style=\"font-size:25\" align=\"center\"\u003eIn-App Paywalls Made Easy 💸\u003c/h3\u003e\n  \u003cbr /\u003e\n\u003c/p\u003e\n\n\u003e [!WARNING] \n\u003e **Important: Expo SDK 53+ Required**\n\u003e\n\u003e This SDK is exclusively compatible with Expo SDK version 53 and newer.\n\u003e For projects using older Expo versions, please use our [legacy React Native SDK](https://github.com/superwall/react-native-superwall).\n\n## Choosing the Right SDK\n\nThis repository contains two SDKs for integrating Superwall with your Expo app:\n\n*   **For new projects:** We recommend using our new **Hooks-based SDK**. See the guide below.\n*   **For migrating from the Superwall React Native SDK:** Get setup in minutes with the [legacy/compat SDK (`expo-superwall/compat`) guide](./COMPAT_SDK_GETTING_STARTED.md).\n*   **For older Expo SDKs:** Please refer to our [legacy React Native SDK](https://github.com/superwall/react-native-superwall).\n\n---\n\n# Getting Started with Expo Superwall SDK\n\nThis guide will help you integrate the Expo Superwall Hooks SDK into your React Native application, allowing you to easily manage users and display paywalls.\n\n**Warning**: This SDK only supports Expo SDK Version \u003e= 53. If you'd like to use older versions, please use our [legacy react-native sdk](https://github.com/superwall/react-native-superwall).\n\n## Installation\n\nFirst, you need to install the `expo-superwall` package. You can do this using npm or yarn:\n\n```bash\nnpx expo install expo-superwall\n# or\nbunx expo install expo-superwall\n```\n\n## Setup\n\nTo use the Superwall SDK, you need to wrap your application (or the relevant part of it) with the `\u003cSuperwallProvider /\u003e`. This provider initializes the SDK with your API key.\n\n```tsx\nimport { SuperwallProvider } from \"expo-superwall\";\n\n// Replace with your actual Superwall API key\nexport default function App() {\n  return (\n    \u003cSuperwallProvider apiKeys={{ ios: \"YOUR_SUPERWALL_API_KEY\" /* android: API_KEY */ }}\u003e\n      {/* Your app content goes here */}\n    \u003c/SuperwallProvider\u003e\n  );\n}\n```\n\n**Note:** You can find your API key in your Superwall dashboard.\n\n### SuperwallProvider Props\n\nThe `SuperwallProvider` component accepts the following props:\n\n- **`apiKeys`** (required): An object containing your Superwall API keys\n  - `ios?: string` - Your iOS API key\n  - `android?: string` - Your Android API key\n- **`options`** (optional): Configuration options for the SDK (see `SuperwallOptions` type)\n- **`onConfigurationError`** (optional): Callback function invoked when SDK configuration fails\n  - Useful for error tracking and analytics\n  - Example: `(error: Error) =\u003e void`\n- **`children`**: Your app content\n\n## Basic Usage\n\nThe SDK provides hooks to interact with Superwall's features.\n\n### Handling Loading States\n\nWhile the SDK is initializing, you can display a loading indicator. The `\u003cSuperwallLoading /\u003e` and `\u003cSuperwallLoaded /\u003e` components help manage this.\n\n```tsx\nimport {\n  SuperwallProvider,\n  SuperwallLoading,\n  SuperwallLoaded,\n} from \"expo-superwall\";\nimport { ActivityIndicator, View, Text } from \"react-native\";\n\nconst API_KEY = \"YOUR_SUPERWALL_API_KEY\";\n\nexport default function App() {\n  return (\n    \u003cSuperwallProvider apiKeys={{ ios: API_KEY }}\u003e\n      \u003cSuperwallLoading\u003e\n        \u003cActivityIndicator style={{ flex: 1 }} /\u003e\n      \u003c/SuperwallLoading\u003e\n      \u003cSuperwallLoaded\u003e\n        {/* Your main app screen or component */}\n        \u003cMainAppScreen /\u003e\n      \u003c/SuperwallLoaded\u003e\n    \u003c/SuperwallProvider\u003e\n  );\n}\n\nfunction MainAppScreen() {\n  return (\n    \u003cView style={{ flex: 1, alignItems: \"center\", justifyContent: \"center\" }}\u003e\n      \u003cText\u003eSuperwall SDK is ready!\u003c/Text\u003e\n      {/* Rest of your app's UI */}\n    \u003c/View\u003e\n  );\n}\n```\n\n### Handling Configuration Errors\n\nThe SDK provides robust error handling for cases when configuration fails (e.g., during offline scenarios). You can handle errors in three ways:\n\n#### 1. Using the `SuperwallError` Component\n\nDisplay error UI declaratively when SDK initialization fails:\n\n```tsx\nimport {\n  SuperwallProvider,\n  SuperwallLoading,\n  SuperwallLoaded,\n  SuperwallError,\n} from \"expo-superwall\";\nimport { ActivityIndicator, View, Text, Button } from \"react-native\";\n\nconst API_KEY = \"YOUR_SUPERWALL_API_KEY\";\n\nexport default function App() {\n  return (\n    \u003cSuperwallProvider apiKeys={{ ios: API_KEY }}\u003e\n      \u003cSuperwallLoading\u003e\n        \u003cActivityIndicator style={{ flex: 1 }} /\u003e\n      \u003c/SuperwallLoading\u003e\n\n      \u003cSuperwallError\u003e\n        {(error) =\u003e (\n          \u003cView style={{ flex: 1, alignItems: \"center\", justifyContent: \"center\" }}\u003e\n            \u003cText style={{ fontSize: 18, marginBottom: 10 }}\u003e\n              Failed to initialize Superwall\n            \u003c/Text\u003e\n            \u003cText style={{ color: \"gray\", marginBottom: 20 }}\u003e{error}\u003c/Text\u003e\n            \u003cButton title=\"Retry\" onPress={() =\u003e {/* retry logic */}} /\u003e\n          \u003c/View\u003e\n        )}\n      \u003c/SuperwallError\u003e\n\n      \u003cSuperwallLoaded\u003e\n        \u003cMainAppScreen /\u003e\n      \u003c/SuperwallLoaded\u003e\n    \u003c/SuperwallProvider\u003e\n  );\n}\n```\n\n#### 2. Using the `onConfigurationError` Callback\n\nHandle errors with a callback for logging or analytics:\n\n```tsx\nimport { SuperwallProvider } from \"expo-superwall\";\n\nexport default function App() {\n  return (\n    \u003cSuperwallProvider\n      apiKeys={{ ios: API_KEY }}\n      onConfigurationError={(error) =\u003e {\n        // Log to your error tracking service\n        console.error(\"Superwall config failed:\", error);\n        // Sentry.captureException(error);\n      }}\n    \u003e\n      \u003cYourApp /\u003e\n    \u003c/SuperwallProvider\u003e\n  );\n}\n```\n\n#### 3. Accessing Error State Directly\n\nAccess the error state programmatically using `useSuperwall`:\n\n\n```tsx\nimport { useSuperwall } from \"expo-superwall\";\n\nfunction ErrorHandler() {\n  const configError = useSuperwall((state) =\u003e state.configurationError);\n\n  if (configError) {\n    return \u003cText\u003eConfiguration Error: {configError}\u003c/Text\u003e;\n  }\n\n  return null;\n}\n```\n\n**Note:** The SDK will gracefully handle offline scenarios and other configuration failures, ensuring your app doesn't hang indefinitely in a loading state.\n\n### Managing Users with `useUser`\n\nThe `useUser` hook provides functions to identify users, sign them out, update their attributes, and access user and subscription status information.\n\n```tsx\nimport { useUser } from \"expo-superwall\";\nimport { Button, Text, View } from \"react-native\";\n\nfunction UserManagementScreen() {\n  const { identify, user, signOut, update, subscriptionStatus } = useUser();\n\n  const handleLogin = async () =\u003e {\n    // Identify the user with a unique ID\n    await identify(`user_${Date.now()}`);\n  };\n\n  const handleSignOut = async () =\u003e {\n    await signOut();\n  };\n\n  const handleUpdateUserAttributes = async () =\u003e {\n    // Update custom user attributes\n    await update((oldAttributes) =\u003e ({\n      ...oldAttributes,\n      customProperty: \"new_value\",\n      counter: (oldAttributes.counter || 0) + 1,\n    }));\n  };\n\n  return (\n    \u003cView style={{ padding: 20 }}\u003e\n      \u003cText\u003eSubscription Status: {subscriptionStatus?.status ?? \"unknown\"}\u003c/Text\u003e\n      {user \u0026\u0026 \u003cText\u003eUser ID: {user.appUserId}\u003c/Text\u003e}\n      {user \u0026\u0026 \u003cText\u003eUser Attributes: {JSON.stringify(user, null, 2)}\u003c/Text\u003e}\n\n      \u003cButton title=\"Login\" onPress={handleLogin} /\u003e\n      \u003cButton title=\"Sign Out\" onPress={handleSignOut} /\u003e\n      \u003cButton title=\"Update Attributes\" onPress={handleUpdateUserAttributes} /\u003e\n    \u003c/View\u003e\n  );\n}\n```\n\nKey functions from `useUser`:\n- `identify(userId)`: Identifies the current user with Superwall. This is typically called when a user logs in.\n- `signOut()`: Signs the current user out. Call this when a user logs out.\n- `update(attributesUpdater)`: Updates the user's attributes. You can provide a function that receives the old attributes and returns the new ones.\n- `user`: An object containing the user's `appUserId` and other attributes.\n- `subscriptionStatus`: An object indicating the user's subscription status (e.g., `active`, `inactive`).\n\n### Triggering Paywalls with `usePlacement`\n\nThe `usePlacement` hook allows you to register and trigger paywalls (placements) that you've configured in your Superwall dashboard.\n\n```tsx\nimport { usePlacement, useUser } from \"expo-superwall\";\nimport { Alert, Button, Text, View } from \"react-native\";\n\nfunction PaywallScreen() {\n  const { registerPlacement, state: placementState } = usePlacement({\n    onError: (err) =\u003e console.error(\"Placement Error:\", err),\n    onPresent: (info) =\u003e console.log(\"Paywall Presented:\", info),\n    onDismiss: (info, result) =\u003e\n      console.log(\"Paywall Dismissed:\", info, \"Result:\", result),\n  });\n\n  const handleTriggerPlacement = async () =\u003e {\n    await registerPlacement({\n      placement: \"your_placement_id\", // Replace with your actual placement ID\n      feature() {\n        // This function is called if the user is already subscribed\n        // or successfully subscribes through the paywall.\n        console.log(\"Feature unlocked!\");\n        Alert.alert(\"Feature Unlocked!\", \"You can now access this feature.\");\n      },\n    });\n  };\n\n  return (\n    \u003cView style={{ padding: 20 }}\u003e\n      \u003cButton title=\"Show Paywall for 'your_placement_id'\" onPress={handleTriggerPlacement} /\u003e\n      {placementState \u0026\u0026 (\n        \u003cText\u003eLast Paywall Result: {JSON.stringify(placementState)}\u003c/Text\u003e\n      )}\n    \u003c/View\u003e\n  );\n}\n```\n\nKey aspects of `usePlacement`:\n- `registerPlacement(options)`: Registers and potentially presents a paywall.\n    - `options.placement`: The ID of the placement you want to show (e.g., \"fishing\" from the example, or \"onboarding_paywall\").\n    - `options.feature()`: A callback function that is executed if the user has access to the feature (either by already being subscribed or by purchasing through the presented paywall).\n- Callbacks (passed as options to `usePlacement`):\n    - `onError`: Handles errors during paywall presentation.\n    - `onPresent`: Called when a paywall is presented.\n    - `onDismiss`: Called when a paywall is dismissed.\n- `state`: An object returned by the hook, containing information about the last paywall presentation attempt (e.g., `presented`, `purchased`, `cancelled`, `skipped`).\n\nThis covers the basic setup and usage of the `expo-superwall` Hooks SDK. For more advanced scenarios and detailed API information, refer to the official Superwall documentation.\n\n---\n\n## Hooks API Reference\n\nThis section provides a detailed reference for each hook available in the `expo-superwall` SDK.\n\n### `useSuperwall`\n\n**Purpose:**\nThe `useSuperwall` hook is the core hook that provides access to the Superwall store and underlying SDK functionality. It's generally used internally by other more specific hooks like `useUser` and `usePlacement`, but can be used directly for advanced scenarios. It ensures that native event listeners are set up on first use.\n\n**Returned Values (Store State and Actions):**\n\nThe hook returns an object representing the Superwall store. If a `selector` function is provided, it returns the selected slice of the store.\n\n-   **State:**\n    -   `isConfigured: boolean`: True if the Superwall SDK has been configured with an API key.\n    -   `isLoading: boolean`: True when the SDK is performing an asynchronous operation like configuration.\n    -   `listenersInitialized: boolean`: True if native event listeners have been initialized.\n    -   `configurationError: string | null`: Contains error message if SDK configuration failed, `null` otherwise. When set, the SDK is not configured and app should show error UI.\n    -   `user?: UserAttributes | null`: An object containing the current user's attributes.\n        -   `UserAttributes`:\n            -   `aliasId: string`: The alias ID of the user.\n            -   `appUserId: string`: The application-specific user ID.\n            -   `applicationInstalledAt: string`: ISO date string of when the application was installed.\n            -   `seed: number`: A seed value for the user.\n            -   `[key: string]: any`: Other custom user attributes.\n    -   `subscriptionStatus?: SubscriptionStatus`: The current subscription status of the user.\n        -   `SubscriptionStatus` (see `SuperwallExpoModule.types.ts` for full details):\n            -   `status: \"UNKNOWN\" | \"INACTIVE\" | \"ACTIVE\"`\n            -   `entitlements?: Entitlement[]` (if status is \"ACTIVE\")\n                -   `Entitlement`: `{ id: string, type: EntitlementType }`\n\n-   **Actions (Functions):**\n    -   `identify: (userId: string, options?: IdentifyOptions) =\u003e Promise\u003cvoid\u003e`: Identifies the user with the given `userId`.\n        -   `IdentifyOptions`:\n            -   `restorePaywallAssignments?: boolean`: If true, restores paywall assignments from a previous session.\n    -   `registerPlacement: (placement: string, params?: Record\u003cstring, any\u003e, handlerId?: string | null) =\u003e Promise\u003cvoid\u003e`: Registers a placement. This may or may not present a paywall depending on campaign rules. `handlerId` is used internally by `usePlacement` to associate events.\n    -   `getPresentationResult: (placement: string, params?: Record\u003cstring, any\u003e) =\u003e Promise\u003cany\u003e`: Gets the presentation result for a given placement.\n    -   `dismiss: () =\u003e Promise\u003cvoid\u003e`: Dismisses any currently presented paywall.\n    -   `preloadAllPaywalls: () =\u003e Promise\u003cvoid\u003e`: Preloads all paywalls.\n    -   `preloadPaywalls: (placements: string[]) =\u003e Promise\u003cvoid\u003e`: Preloads paywalls for the specified placement IDs.\n    -   `setUserAttributes: (attrs: Record\u003cstring, any\u003e) =\u003e Promise\u003cvoid\u003e`: Sets custom attributes for the current user.\n    -   `getUserAttributes: () =\u003e Promise\u003cRecord\u003cstring, any\u003e\u003e`: Retrieves the attributes of the current user.\n    -   `setLogLevel: (level: string) =\u003e Promise\u003cvoid\u003e`: Sets the log level for the SDK. `level` can be one of: `\"debug\"`, `\"info\"`, `\"warn\"`, `\"error\"`, `\"none\"`.\n\n**Selector (Optional Parameter):**\n\n-   `selector?: (state: SuperwallStore) =\u003e T`: A function that receives the entire `SuperwallStore` state and returns a selected part of it. Useful for performance optimization by only re-rendering components when the selected state changes. Uses `zustand/shallow` for shallow equality checking.\n\n**Example (Direct Usage - Advanced):**\n\n```tsx\nimport { useSuperwall } from 'expo-superwall';\n\nfunction MyAdvancedComponent() {\n  const { isConfigured, setUserAttributes } = useSuperwall();\n\n  if (!isConfigured) {\n    return \u003cText\u003eSDK not configured yet.\u003c/Text\u003e;\n  }\n\n  const handleSetCustomAttribute = () =\u003e {\n    setUserAttributes({ myCustomFlag: true });\n  };\n\n  return \u003cButton title=\"Set Custom Flag\" onPress={handleSetCustomAttribute} /\u003e;\n}\n```\n\n### `useUser`\n\n**Purpose:**\nThe `useUser` hook provides a convenient way to manage user identity and attributes, and access user-specific information like subscription status.\n\n**Returned Values:**\n\nAn object containing:\n\n-   `identify: (userId: string, options?: IdentifyOptions) =\u003e Promise\u003cvoid\u003e`: Identifies the user with Superwall.\n    -   `userId: string`: The unique identifier for the user.\n    -   `options?: IdentifyOptions`: Optional parameters for identification.\n        -   `restorePaywallAssignments?: boolean`: If true, attempts to restore paywall assignments for this user.\n-   `update: (attributes: Record\u003cstring, any\u003e | ((old: Record\u003cstring, any\u003e) =\u003e Record\u003cstring, any\u003e)) =\u003e Promise\u003cvoid\u003e`: Updates the current user's attributes.\n    -   `attributes`: Either an object of attributes to set/update, or a function that takes the old attributes and returns the new attributes.\n-   `signOut: () =\u003e void`: Resets the user's identity, effectively signing them out from Superwall's perspective.\n-   `refresh: () =\u003e Promise\u003cRecord\u003cstring, any\u003e\u003e`: Manually refreshes the user's attributes and subscription status from the Superwall servers. Returns the refreshed user attributes.\n-   `subscriptionStatus?: SubscriptionStatus`: The current subscription status of the user.\n    -   `SubscriptionStatus`: (As defined in `useSuperwall` and `SuperwallExpoModule.types.ts`)\n        -   `status: \"UNKNOWN\" | \"INACTIVE\" | \"ACTIVE\"`\n        -   `entitlements?: Entitlement[]` (if status is \"ACTIVE\")\n-   `user?: UserAttributes | null`: An object containing the current user's attributes (e.g., `appUserId`, `aliasId`, custom attributes).\n    -   `UserAttributes`: (As defined in `useSuperwall`)\n\n**Example:**\n(Covered in the Basic Usage section)\n\n### `usePlacement`\n\n**Purpose:**\nThe `usePlacement` hook is designed to handle the presentation of paywalls based on placements configured in your Superwall dashboard. It manages the state of paywall presentation and provides callbacks for various events.\n\n**Parameters:**\n\n-   `callbacks?: usePlacementCallbacks`: An optional object containing callback functions for different paywall events.\n    -   `usePlacementCallbacks`:\n        -   `onPresent?: (paywallInfo: PaywallInfo) =\u003e void`: Called when a paywall is presented.\n            -   `paywallInfo: PaywallInfo`: Detailed information about the presented paywall (see `SuperwallExpoModule.types.ts`).\n        -   `onDismiss?: (paywallInfo: PaywallInfo, result: PaywallResult) =\u003e void`: Called when a paywall is dismissed.\n            -   `paywallInfo: PaywallInfo`: Information about the dismissed paywall.\n            -   `result: PaywallResult`: The result of the paywall interaction (e.g., `purchased`, `declined`, `restored`). See `SuperwallExpoModule.types.ts`.\n        -   `onSkip?: (reason: PaywallSkippedReason) =\u003e void`: Called when a paywall is skipped (e.g., due to holdout group, no audience match).\n            -   `reason: PaywallSkippedReason`: The reason why the paywall was skipped. See `SuperwallExpoModule.types.ts`.\n        -   `onError?: (error: string) =\u003e void`: Called when an error occurs during paywall presentation or other SDK operations related to this placement.\n            -   `error: string`: The error message.\n\n**Returned Values:**\n\nAn object containing:\n\n-   `registerPlacement: (args: RegisterPlacementArgs) =\u003e Promise\u003cvoid\u003e`: A function to register a placement and potentially trigger a paywall.\n    -   `RegisterPlacementArgs`:\n        -   `placement: string`: The placement name as defined on the Superwall dashboard.\n        -   `params?: Record\u003cstring, any\u003e`: Optional parameters to pass to the placement.\n        -   `feature?: () =\u003e void`: An optional function to execute if the placement does *not* result in a paywall presentation (i.e., the user is allowed through, or is already subscribed).\n-   `state: PaywallState`: An object representing the current state of the paywall associated with this hook instance.\n    -   `PaywallState`:\n        -   `{ status: \"idle\" }`\n        -   `{ status: \"presented\"; paywallInfo: PaywallInfo }`\n        -   `{ status: \"dismissed\"; result: PaywallResult }`\n        -   `{ status: \"skipped\"; reason: PaywallSkippedReason }`\n        -   `{ status: \"error\"; error: string }`\n\n**Example:**\n(Covered in the Basic Usage section)\n\n### `useSuperwallEvents`\n\n**Purpose:**\nThe `useSuperwallEvents` hook provides a low-level way to subscribe to *any* native Superwall event. This is useful for advanced use cases or for events not covered by the more specific hooks. Listeners are automatically cleaned up when the component using this hook unmounts.\n\n**Parameters:**\n\n-   `callbacks?: SuperwallEventCallbacks`: An object where keys are event names and values are the corresponding callback functions.\n    -   `SuperwallEventCallbacks`: (Refer to `src/useSuperwallEvents.ts` and `src/SuperwallExpoModule.types.ts` for a full list of subscribable events and their payload types. Common events include):\n        -   `onPaywallPresent?: (info: PaywallInfo) =\u003e void`\n        -   `onPaywallDismiss?: (info: PaywallInfo, result: PaywallResult) =\u003e void`\n        -   `onPaywallSkip?: (reason: PaywallSkippedReason) =\u003e void`\n        -   `onPaywallError?: (error: string) =\u003e void`\n        -   `onSubscriptionStatusChange?: (status: SubscriptionStatus) =\u003e void`\n        -   `onSuperwallEvent?: (eventInfo: SuperwallEventInfo) =\u003e void`: For generic Superwall events.\n            -   `SuperwallEventInfo`: `{ event: SuperwallEvent, params: Record\u003cstring, any\u003e }`\n        -   `onCustomPaywallAction?: (name: string) =\u003e void`: When a custom action is triggered from a paywall.\n        -   `willDismissPaywall?: (info: PaywallInfo) =\u003e void`\n        -   `willPresentPaywall?: (info: PaywallInfo) =\u003e void`\n        -   `didDismissPaywall?: (info: PaywallInfo) =\u003e void`\n        -   `didPresentPaywall?: (info: PaywallInfo) =\u003e void`\n        -   `onPaywallWillOpenURL?: (url: string) =\u003e void`\n        -   `onPaywallWillOpenDeepLink?: (url: string) =\u003e void`\n        -   `onLog?: (params: { level: LogLevel, scope: LogScope, message: string | null, info: Record\u003cstring, any\u003e | null, error: string | null }) =\u003e void`\n        -   `handlerId?: string`: (Optional) If provided, some events like `onPaywallPresent`, `onPaywallDismiss`, `onPaywallSkip` will only be triggered if the event originated from a `registerPlacement` call associated with the same `handlerId`. This is used internally by `usePlacement`.\n\n**Returned Values:**\n\nThis hook does not return any values (`void`). Its purpose is to set up and tear down event listeners.\n\n**Example:**\n\n```tsx\nimport { useSuperwallEvents } from 'expo-superwall';\n\nfunction EventLogger() {\n  useSuperwallEvents({\n    onSuperwallEvent: (eventInfo) =\u003e {\n      console.log('Superwall Event:', eventInfo.event.event, eventInfo.params);\n    },\n    onSubscriptionStatusChange: (newStatus) =\u003e {\n      console.log('Subscription Status Changed:', newStatus.status);\n    },\n    onPaywallPresent: (info) =\u003e {\n      console.log('Paywall Presented (via useSuperwallEvents):', info.name);\n    }\n  });\n\n}\n```\n\nFor detailed type information on `PaywallInfo`, `PaywallResult`, `PaywallSkippedReason`, `SubscriptionStatus`, `SuperwallEventInfo`, and other types, please refer to the `SuperwallExpoModule.types.ts` file in the `expo-superwall` package.\n\n## Resources\n\n- 📖 [Full Documentation](https://superwall.com/docs/home)\n- 🎮 [Example App](./example)\n- 💬 [Discord Community](https://discord.gg/superwall)\n- 📧 [Support](mailto:jake@superwall.com)\n- 🐛 [Report Issues](https://github.com/superwall/superwall-expo/issues)\n\n\n---\n\n## Contributing\n\nPlease see the [CONTRIBUTING](.github/CONTRIBUTING.md) file for how to help.\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fsuperwall%2Fexpo-superwall","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fsuperwall%2Fexpo-superwall","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fsuperwall%2Fexpo-superwall/lists"}