Gérer des Abonnements sur iOSVersion bêta privée
Acceptez les paiements récurrents et gérez les droits d'accès avec BillingSDK pour iOS.
Acceptez les paiements d’abonnement, laissez vos clients gérer leurs Abonnements et gérez les droits d’accès directement dans votre application iOS avec le BillingSDK pour iOS. Le SDK fournit des composants d’interface utilisateur préconfigurés pour afficher les boutons d’achat, présenter le portail client et vérifier les droits d’accès aux fonctionnalités premium.
Avant de commencer
Pour utiliser BillingSDK pour iOS, vous aurez besoin de :
- Un serveur back-end pour créer des sessions client
- Un compte Stripe ayant accès à la version bêta privée
- iOS 15.0 ou version ultérieure et macOS 12.0 ou version ultérieure
- Xcode 15.0 ou version ultérieure
Ce que vous allez créer
Ce guide vous explique comment :
- Configurer un endpoint de serveur pour créer des sessions client
- Installer et configurer le BillingSDK pour iOS
- Afficher les boutons d’achat pour les achats d’abonnement
- Vérifier les droits d’accès aux fonctionnalités premium
- Présenter le portail client pour la gestion des abonnements
- Gérer les erreurs et gérer l’état de la session
Vous trouverez un exemple complet d’application dans le référentiel BillingSDK pour iOS.
Configurer votre back-endServeur
Créez un endpoint de serveur qui génère des sessions client pour les utilisateurs authentifiés. Ces sessions authentifient votre application iOS en toute sécurité avec les API de facturation de Stripe.
Créer un endpoint de session client
L’endpoint doit :
- Vérifier que l’utilisateur est authentifié
- Créer ou récupérer l’ID client Stripe de l’utilisateur
- Créer une session client avec les composants requis activés
- Renvoyez les détails de la session à votre application
Voici un exemple d’implémentation :
import 'dotenv/config'; import express from 'express'; import Stripe from 'stripe'; const stripe = new Stripe(process.env.STRIPE_SECRET_KEY || '', { apiVersion: '2025-07-30.basil', }); const app = express(); app.use(express.json()); app.post('/authenticate', async (req, res) => { try { // Replace with your auth; return 401 if the user is not logged in const user = authUser(req); if (!user) { res.status(401).json({ error: { type: 'no_session_present' } }); return; } const customerSession = await stripe.customerSessions.create({ customer: user.stripeCustomerId, components: { buy_button: { enabled: true }, active_entitlements: { enabled: true }, customer_portal: { enabled: true }, } as any, }); res.json({ clientSecret: customerSession.client_secret, expiresAt: customerSession.expires_at, customer: customerSession.customer as string, }); } catch (err) { res.status(500).json({ error: { message: 'Internal server error' } }); } }); app.listen(3000);
Format de réponse
L’endpoint doit renvoyer ces champs pour une authentification réussie :
| Champ | Type | Description |
|---|---|---|
clientSecret | chaîne | La clé secrète de la session client utilisée pour authentifier le SDK |
expiresAt | nombre | Horodatage d’expiration en secondes depuis l’heure |
customer | chaîne | L’ID client Stripe |
Lorsque l’authentification échoue, renvoyez HTTP 401 pour déclencher l’état non authentifié du SDK.
Installer et configurer le SDKiOS
Le BillingSDK pour iOS fournit une expérience iOS native pour la gestion des abonnements et le contrôle d’accès aux fonctionnalités.
Ajouter le SDK à votre projet
Lors de la prévisualisation privée, installez le paquet BillingSDK :
- Ouvrir votre projet dans Xcode
- Sélectionnez Fichier → Ajouter des dépendances de package
- Saisissez
https://github.dans le champ Rechercher ou saisir l’URL du packagecom/stripe-samples/billing-ios-sdk - Sélectionnez
BillingSDKet cliquez sur Ajouter un package
Configurer le SDK
Initialisez le SDK dans une classe partagée pour gérer la configuration et l’authentification du SDK Billing :
import Foundation import BillingSDK import SwiftUI class BillingManager { static let shared = BillingManager() public let billing: BillingSDK private init() { // Initialize with your publishable key and set how long entitlements can be stale before needing to refresh. let configuration = BillingSDK.Configuration( publishableKey: "pk_test_…", maximumStaleEntitlementsDuration: TimeInterval(60 * 5) ) self.billing = BillingSDK(configuration: configuration) // Set up authentication (see below for implementation) setupCustomerSessionProvider() // Add entitlement change listener (see below for implementation) setupEntitlementListener() } }
Remarque
Le SDK gère la sécurité des threads en interne : vous pouvez appeler ses méthodes en toute sécurité depuis n’importe quel thread.
Configurer le fournisseur de sessions client
Ajoutez la méthode d’authentification à votre gestionnaire de facturation :
import Foundation import BillingSDK extension BillingManager { func setupCustomerSessionProvider() { billing.setCustomerSessionProvider { [weak self] in await self?.fetchCustomerSession() } } private func fetchCustomerSession() async -> UBCustomerSessionDetails? { // Configure request to your backend endpoint guard let url = URL(string: "https://your-backend.example.com/customer-session") else { print("Invalid URL") return nil } var request = URLRequest(url: url) request.httpMethod = "POST" request.setValue("application/json", forHTTPHeaderField: "Content-Type") // Send any additional headers needed to authenticate the user, for example, an auth token. request.setValue("Bearer \(authToken)", forHTTPHeaderField: "Authorization") do { // Make the request let (data, response) = try await URLSession.shared.data(for: request) guard let httpResponse = response as? HTTPURLResponse else { print("Invalid response format") return nil } switch httpResponse.statusCode { case 200: // Parse the successful response let decoder = JSONDecoder() decoder.dateDecodingStrategy = .secondsSince1970 return try decoder.decode(UBCustomerSessionDetails.self, from: data) case 401: // User not authenticated - SDK will enter unauthenticated state print("Authentication required") return nil default: print("Unexpected status code: \(httpResponse.statusCode)") return nil } } catch { print("Session provider error: \(error.localizedDescription)") return nil } } // Call this method when your user signs out func handleSignOut() async { await billing.reset() // Clear session data and caches } }
Remarque
Le SDK Billing appelle automatiquement votre fournisseur de session lorsqu’il doit s’authentifier auprès de Stripe. Lorsque le fournisseur renvoie nil, le SDK passe à l’état non authentifié.
Afficher les boutons d'achat des abonnementsiOS
Les boutons d’achat fournissent un élément d’interface utilisateur préconfiguré pour permettre aux clients d’acheter des Abonnements. Chaque bouton est lié à un produit et à un tarif spécifiques dans votre compte Stripe.
Créer des boutons d’achat dans le Dashboard
Suivez ce guide pour créer des boutons d’achat dans le Dashboard. Si vous prévoyez d’utiliser la fonctionnalité de vérification des droits, assurez-vous que les produits que vous avez créés sont associés à des droits d’accès.
Afficher un bouton d’achat
import SwiftUI import BillingSDK struct SubscriptionView: View { @State private var buyButton: BuyButton? @State private var isLoading = true @State private var errorMessage: String? // Replace with your buy button ID from the Dashboard let buttonId = "buy_btn_1Abcdef123456" var body: some View { VStack { if isLoading { ProgressView("Loading subscription options...") } else if let buyButton = buyButton { // Display the prebuilt buy button UI // Alternatively the BuyButton class also provides all the data to render // a custom UI element. buyButton.view() .frame(height: 56) .padding(.horizontal) } else if let errorMessage = errorMessage { Text("Error: \(errorMessage)") .foregroundColor(.red) Button("Retry") { loadBuyButton() } } } .onAppear { loadBuyButton() } } func loadBuyButton() { isLoading = true errorMessage = nil Task { do { // Fetch the button from Stripe buyButton = try await BillingManager.shared.billing.getBuyButton(id: buttonId) isLoading = false } catch { errorMessage = "Failed to load buy button" isLoading = false } } } }
Remarque
Les boutons d’achat fonctionnent même lorsque les utilisateurs ne sont pas authentifiés. Si nécessaire, le SDK crée un nouveau client Stripe lors de l’achat.
Vérifier et valider les droitsiOS
Les droits vous permettent de contrôler l’accès aux fonctionnalités premium en fonction des Abonnements actifs d’un client.
Vérifier un droit spécifique
Vérifiez si un utilisateur a accès à une fonctionnalité spécifique :
func checkPremiumAccess() async { do { let hasPremiumAccess = try await BillingManager.shared.billing.hasEntitlement(lookupKey: "premium_tier") if hasPremiumAccess { // User has premium access - enable features unlockPremiumFeatures() } else { // User doesn't have access - show upsell showPremiumUpsell() } } catch { showErrorMessage("Couldn't verify entitlements status") } }
Obtenir tous les droits d’accès actifs
Récupérez tous les droits auxquels le client a accès :
func loadUserEntitlements() async { do { // Force refresh ensures we get the latest data from the server let entitlements = try await BillingManager.shared.billing.getActiveEntitlements(forceRefresh: true) // Map entitlements to app features let features = entitlements.map { $0.lookupKey } updateAvailableFeatures(features) } catch { handleError(error) } }
Écouter les changements de droits
Configurez un écouteur pour recevoir une notification en cas de modification des droits :
import Foundation import BillingSDK extension BillingManager { func setupEntitlementListener() { billing.onEntitlementsChanged { updatedEntitlements in // Update UI based on new entitlements DispatchQueue.main.async { self.updateAppFeatures(based: updatedEntitlements) self.refreshUI() } } } }
Remarque
En l’absence de session, getActiveEntitlements() renvoie un tableau vide.
Présenter le portail clientiOS
Le portail client permet aux abonnés de gérer leurs Abonnements, leurs moyens de paiement et leurs informations de facturation.
Afficher le portail client
Présentez le portail lorsque les utilisateurs doivent gérer leur abonnement :
func manageSubscriptionTapped() { Task { do { let portal = try await BillingManager.shared.billing.getCustomerPortal() // Show portal within your app (recommended) portal.presentCustomerPortal(from: self) } catch { if let billingError = error as? BillingSDKError { switch billingError { case .unauthenticated: // User needs to log in first showLoginPrompt() default: // Handle other errors showErrorMessage("Could not load subscription management") } } else { showErrorMessage("Could not load subscription management") } } } }
Avertissement
Le portail client nécessite une session authentifiée active. Si l’utilisateur n’est pas connecté, le SDK renvoie une erreur ..
Redirection externe (facultatif)
Vous pouvez également ouvrir le portail dans un navigateur :
let portal = try await BillingManager.shared.billing.getCustomerPortal() portal.redirectToCustomerPortal() // Opens in default browser
Gestion des sessionsiOS
Gestion des sessions
Réinitialisez le SDK lorsque les utilisateurs se déconnectent pour vider les données et les caches de session :
func signOut() async { // Clear your app's auth state UserDefaults.standard.removeObject(forKey: "auth_token") // Reset the BillingSDK state await BillingManager.shared.billing.reset() // Navigate to login screen showLoginScreen() }
Tester votre intégration
Pendant le développement, utilisez vos clés API d’environnement de test et vos ID de client d’environnement de test pour éviter de créer des paiements réels.
Scénarios de test
Testez ces scénarios courants :
| Scénario | Étapes |
|---|---|
| Achat d’un nouvel abonnement | Présenter un bouton d’achat à un nouvel utilisateur |
| Gestion des abonnements | Utiliser le portail client pour modifier les offres |
| Vérification des droits | Vérifier une fonctionnalité premium avec hasEntitlement |
| Gestion des erreurs | Tester avec des clés non valides ou des sessions expirées |
| Flux de déconnexion | Vérifier que billing. vide les données en cache |