> ## Documentation Index
> Fetch the complete documentation index at: https://docs.dodopayments.com/llms.txt
> Use this file to discover all available pages before exploring further.

# React Native

> Buka hosted checkout Dodo Payments dari aplikasi React Native di tab browser sistem dan dapatkan hasil bertipe dalam satu panggilan.

<Info>
  Ini adalah checkout SDK React Native resmi dari Dodo Payments, `@dodopayments/react-native-checkout`. SDK ini membuka hosted checkout Dodo di tampilan browser native dan mengembalikan hasil bertipe. Catatan: terdapat package lama yang tidak terkait bernama `dodopayments-react-native-sdk` (unscoped) dengan API yang sepenuhnya berbeda. Halaman ini hanya mendokumentasikan package scoped resmi yang saat ini digunakan.
</Info>

<CardGroup cols={2}>
  <Card title="Checkout Sessions API" icon="cart-shopping" href="/developer-resources/checkout-session">
    Buat checkout\_url yang dibuka SDK ini, dari backend Anda.
  </Card>

  <Card title="Mobile Integration Guide" icon="mobile" href="/developer-resources/mobile-integration">
    Lihat bagaimana hal ini menjadi bagian dari alur pembayaran mobile secara keseluruhan.
  </Card>
</CardGroup>

React Native SDK ini adalah wrapper Turbo Module tipis di atas core Swift dan Kotlin native yang sama. SDK ini membuka `SFSafariViewController` di iOS dan Chrome Custom Tab di Android, tidak menyimpan API key, serta tidak pernah memanggil Dodo API secara langsung. Semua logika checkout berjalan di browser; SDK hanya mengelola siklus hidup tampilan dan menangkap return URL.

<Warning>
  SDK ini hanya memerlukan **New Architecture**, React Native 0.76+, iOS 16+, dan Android `minSdk` 24.
</Warning>

## Instalasi

<Steps>
  <Step title="Install the Package">
    <Tabs>
      <Tab title="Android">
        Package ini ditautkan secara otomatis dan menarik `com.dodopayments.api:checkout-android` dari Maven.

        ```sh theme={null}
        npm i @dodopayments/react-native-checkout
        ```

        Tidak diperlukan konfigurasi tambahan; dependency native diselesaikan secara otomatis.
      </Tab>

      <Tab title="iOS">
        ```sh theme={null}
        npm i @dodopayments/react-native-checkout
        cd ios && pod install
        ```

        Core Swift disertakan dalam package dan diinstal melalui CocoaPods.
      </Tab>

      <Tab title="Expo">
        Hanya untuk development build (bukan Expo Go).

        ```sh theme={null}
        npm i @dodopayments/react-native-checkout
        npx expo install expo-build-properties
        ```

        Selanjutnya, konfigurasikan `app.json` Anda (lihat Daftarkan Callback URL Scheme di bawah).
      </Tab>
    </Tabs>
  </Step>

  <Step title="Register a Callback URL Scheme">
    Aplikasi Anda harus mendaftarkan URL scheme untuk menerima return URL dari checkout.

    <Tabs>
      <Tab title="Android (Gradle)">
        Di `android/app/build.gradle`:

        ```kotlin android/app/build.gradle theme={null}
        android {
            defaultConfig {
                manifestPlaceholders["dodoCallbackScheme"] = "myapp"
            }
        }
        ```

        Ganti `"myapp"` dengan scheme aplikasi Anda.
      </Tab>

      <Tab title="iOS (Info.plist)">
        Di `ios/YourApp/Info.plist`:

        ```xml Info.plist theme={null}
        <key>CFBundleURLTypes</key>
        <array>
          <dict>
            <key>CFBundleURLName</key>
            <string>myapp</string>
            <key>CFBundleURLSchemes</key>
            <array>
              <string>myapp</string>
            </array>
          </dict>
        </array>
        ```

        Anda juga dapat menambahkannya melalui UI **Info → URL Types** di Xcode.
      </Tab>

      <Tab title="Expo (both platforms)">
        Di `app.json`:

        ```json app.json theme={null}
        {
          "expo": {
            "plugins": [
              [
                "expo-build-properties",
                {
                  "android": {
                    "manifestPlaceholders": {
                      "dodoCallbackScheme": "myapp"
                    }
                  }
                }
              ]
            ],
            "ios": {
              "infoPlist": {
                "CFBundleURLTypes": [
                  {
                    "CFBundleURLSchemes": ["myapp"]
                  }
                ]
              }
            }
          }
        }
        ```

        <Warning>
          Package ini juga menyertakan plugin konfigurasi Expo `@dodopayments/react-native-checkout`,
          namun saat ini plugin tersebut tidak menulis URL scheme maupun manifest placeholder.
          Menambahkannya saja **tidak** akan mendaftarkan callback scheme Anda — gunakan
          konfigurasi `expo-build-properties` dan `infoPlist` di atas.
        </Warning>

        <Note>
          Bangun ulang project native setelah mengedit `app.json`:

          ```sh theme={null}
          npx expo prebuild --clean
          ```

          Ini hanya berfungsi dengan development build, bukan Expo Go.
        </Note>
      </Tab>
    </Tabs>
  </Step>
</Steps>

## Penggunaan

```typescript theme={null}
import { Linking } from 'react-native';
import { DodoCheckout } from '@dodopayments/react-native-checkout';

// Required for iOS's return-URL handling.
Linking.addEventListener('url', ({ url }) => DodoCheckout.handleOpenURL(url));

const result = await DodoCheckout.start({
  checkoutUrl,                          // from your backend's checkout session
  returnUrl: 'myapp://checkout/return', // scheme must be registered (see Installation)
  onEvent: (e) => console.log(e.type),  // logging only
});

switch (result.status) {
  case 'succeeded': showSuccess(result.paymentId); break;
  case 'failed':    showFailure(); break;
  case 'cancelled': dismiss(); break;
  case 'pending':   showPending(); break;
  case 'expired':   showExpired(); break;
}
```

## Meneruskan Return URL

Listener `Linking` diperlukan untuk penanganan return URL di iOS. Di Android, `handleOpenURL` tidak melakukan apa pun dan menyelesaikan `false` karena core Android menangani redirect-nya secara native. Listener ini aman untuk didaftarkan tanpa syarat di kedua platform.

```typescript theme={null}
import { Linking } from 'react-native';
import { DodoCheckout } from '@dodopayments/react-native-checkout';

Linking.addEventListener('url', ({ url }) => {
  DodoCheckout.handleOpenURL(url);
});
```

## Arti Hasil

<Warning>
  `result.status` adalah petunjuk UI, bukan bukti pembayaran. Konfirmasikan setiap pembayaran dari backend Anda melalui webhook `payment.succeeded` / `subscription.active`.
</Warning>

<ParamField body="status" type="CheckoutStatus" required>
  Salah satu dari `succeeded`, `failed`, `cancelled`, `pending`, `expired`.
</ParamField>

<ParamField body="paymentId" type="string">
  Diatur ketika return URL menyertakan salah satunya. Tampilkan di UI, tetapi jangan gunakan untuk memberikan akses. Lihat Verifikasi Pembayaran di bawah.
</ParamField>

<ParamField body="subscriptionId" type="string">
  Diatur untuk subscription checkout.
</ParamField>

<ParamField body="licenseKeys" type="string[]">
  Diatur ketika checkout menyertakan produk license key.
</ParamField>

<ParamField body="customerEmail" type="string">
  Diatur ketika checkout mengambil email.
</ParamField>

<ParamField body="raw" type="Record<string, string>">
  Setiap query parameter dari return URL, secara verbatim.
</ParamField>

## Verifikasi Pembayaran

<CardGroup cols={2}>
  <Card title="Webhooks" icon="webhook" href="/developer-resources/webhooks">
    Dodo Payments memanggil backend Anda ketika pembayaran berhasil atau subscription diaktifkan.
  </Card>

  <Card title="Get Payment Detail" icon="magnifying-glass" href="/api-reference/payments/get-payments-1">
    Cari `paymentId` menggunakan secret key Anda untuk memeriksa statusnya secara langsung.
  </Card>
</CardGroup>

Berikan akses setelah salah satu metode ini mengonfirmasi pembayaran, jangan pernah hanya berdasarkan `result.status`.

## Error

`start` menolak dengan `CheckoutError` hanya jika terjadi penyalahgunaan atau kegagalan platform. Pembayaran yang dibatalkan atau ditolak selalu berupa hasil, bukan exception.

* `INVALID_CHECKOUT_URL`: bukan session URL `checkout.dodopayments.com`.
* `INVALID_RETURN_URL`: bukan absolute URL yang valid.
* `ALREADY_IN_PROGRESS`: checkout sedang berjalan.
* `PLATFORM_ERROR`: kegagalan platform yang tidak terduga.

## Session yang Ditinggalkan

Jika aplikasi atau JS bundle dihentikan di tengah checkout, promise akan hilang tetapi layer native tetap mempertahankan session. Pulihkan pada mount berikutnya dan rekonsiliasikan dengan backend Anda.

```typescript theme={null}
import { DodoCheckout } from '@dodopayments/react-native-checkout';

const abandoned = await DodoCheckout.getAbandonedSession();
if (abandoned) {
  // reconcile abandoned.sessionId with your backend, then:
  await DodoCheckout.clearAbandonedSession();
}
```

## Terkait

<CardGroup cols={2}>
  <Card title="Mobile Integration Guide" icon="mobile" href="/developer-resources/mobile-integration">
    Contract yang sama untuk Android, iOS, dan Flutter.
  </Card>

  <Card title="Expo Boilerplate" icon="layer-group" href="/developer-resources/expo-boilerplate">
    Contoh Expo lengkap dengan integrasi checkout.
  </Card>
</CardGroup>
