React Native
This guide shows you how to integrate GeelabGuard into a React Native app, initialize the native SDK, and generate a device receipt that can be sent to your business backend.
Overview
geelabguard-rn-plugin supports both the React Native Legacy Architecture and New Architecture through the same Promise-based API. After completing this guide, you will be able to:
- Install the React Native plugin and the separately licensed native SDKs.
- Initialize GeelabGuard with an AppID.
- Generate a local receipt or submit a receipt when a business event occurs.
- Send the token securely to your business backend.
This guide covers only the React Native client integration. Receipt verification, risk decisions, and business actions must be handled by your backend.
Prerequisites
Before you begin, make sure that:
- You have a working React Native development environment.
- Your React Native version is
0.71.0or later. - Your Android app uses
minSdkVersion21 or later. - Your iOS app has a minimum deployment target of iOS 12.4 or later.
- You have obtained an AppID through an authorized GeelabGuard channel.
- You have obtained the native SDK for each target platform through an authorized GeelabGuard channel:
| Platform | Native SDK | Relative installation path in the npm package |
|---|---|---|
| Android | geelabguard_android_vx.y.z_date.aar | android/libs/geelabguard_android_vx.y.z_date.aar |
| iOS | GeelabGuardSDK.xcframework x.y.z | ios/Frameworks/GeelabGuardSDK.xcframework |
The native SDK binaries are not included in the GitHub repository or npm package. React Native Web is not supported.
1. Prepare a React Native project
If you already have a React Native project, continue to the next section. Otherwise, create one with the React Native Community CLI:
npx @react-native-community/cli init GeelabGuardRN
cd GeelabGuardRNRun the app before adding the plugin to confirm that your React Native environment works correctly:
npx react-native startIn another terminal, run the target platform:
# Android
npx react-native run-android
# iOS
npx react-native run-ios2. Install the React Native plugin
Run the following command from the application root:
npm install geelabguard-rn-pluginIf you use Yarn:
yarn add geelabguard-rn-plugin3. Install the native SDKs
Install only the native SDKs for the platforms that your application builds.
Android
Copy the licensed AAR into the plugin's android/libs directory:
mkdir -p node_modules/geelabguard-rn-plugin/android/libs
cp /path/to/geelabguard_android_vx.y.z_date.aar \
node_modules/geelabguard-rn-plugin/android/libs/The plugin checks for this file during Gradle configuration. If the file is missing, the build stops and displays the expected path.
The native SDK manifest declares android.permission.INTERNET. The plugin's consumer ProGuard rules preserve the tech.geelab.core and tech.geelab.geegateway namespaces.
iOS
Copy the licensed XCFramework into the plugin's ios/Frameworks directory, then install the Pods:
mkdir -p node_modules/geelabguard-rn-plugin/ios/Frameworks
cp -R /path/to/GeelabGuardSDK.xcframework \
node_modules/geelabguard-rn-plugin/ios/Frameworks/
cd ios
pod install
cd ..The plugin's podspec checks this directory during CocoaPods resolution and automatically adds the required -ObjC linker flag.
Reinstalling, pruning, or rebuilding
node_modulesmay remove native SDKs that were copied manually. If this happens, copy the SDKs again and rebuild the native app.
4. Initialize the SDK
Before calling any other API, initialize GeelabGuard with the AppID (public_key) obtained from the dashboard:
import { GeelabGuard } from 'geelabguard-rn-plugin';
await GeelabGuard.initialize('your-app-id');When serverUrl is omitted, the native SDK uses the default global service endpoint. If the AppID belongs to a specific Region, pass the reporting endpoint configured for that Region:
await GeelabGuard.initialize(
'your-app-id', // public_key obtained from the dashboard
'https://riskct-eu.geelabapi.com/api/v2/client_report'
);Neither appId nor an explicitly provided serverUrl can be an empty string. The AppID and service endpoint must belong to the same configured Region.
5. Generate and submit a device receipt
Submit online
For most business scenarios that require a server response, call submitReceipt:
const receipt = await GeelabGuard.submitReceipt('business-request-id');
// Send respondedGeeToken to your business backend for verification and risk processing.
const token = receipt.respondedGeeToken;signData binds the receipt to the current business request. You can use a request identifier generated by your business system. Do not pass passwords, private keys, or other sensitive plaintext values.
Generate a local receipt only
When you do not need to submit data to the server immediately, call fetchReceipt:
const receipt = await GeelabGuard.fetchReceipt('business-request-id');
// Send geeToken to your business backend.
const token = receipt.geeToken;signData must be a string. Pass an empty string if your business flow does not need to bind any data.
6. Add a minimal working example
The following App.tsx example initializes the SDK when the page loads and submits a device receipt when the user selects the button. The example displays only the operation status and does not expose the token in the UI or logs.
import { useEffect, useState } from 'react';
import { Button, SafeAreaView, StyleSheet, Text } from 'react-native';
import { GeelabGuard, GeelabGuardError } from 'geelabguard-rn-plugin';
const APP_ID = 'your-app-id'; // public_key obtained from the dashboard
export default function App() {
const [initialized, setInitialized] = useState(false);
const [status, setStatus] = useState('Initializing GeelabGuard…');
useEffect(() => {
let active = true;
GeelabGuard.initialize(APP_ID).then(
() => {
if (!active) return;
setInitialized(true);
setStatus('GeelabGuard initialized');
},
(error: unknown) => {
if (!active) return;
setStatus(
error instanceof GeelabGuardError
? `Initialization failed: ${error.code}`
: 'Initialization failed'
);
}
);
return () => {
active = false;
};
}, []);
const identifyDevice = async () => {
setStatus('Generating device receipt…');
try {
const receipt = await GeelabGuard.submitReceipt('business-request-id');
const token = receipt.respondedGeeToken;
if (!token) throw new Error('The response does not contain respondedGeeToken');
// Call your own HTTPS business API here and send the token to your backend.
// Do not store server private keys on the client or trust client-side risk results directly.
setStatus('Device receipt generated; send it to your business backend');
} catch (error) {
if (error instanceof GeelabGuardError) {
// For network or service errors, error.receipt may contain a local geeToken for fallback use.
setStatus(`Generation failed: ${error.code}`);
return;
}
setStatus('Generation failed: unknown error');
}
};
return (
<SafeAreaView style={styles.container}>
<Text style={styles.status}>{status}</Text>
<Button
title="Generate device receipt"
disabled={!initialized}
onPress={identifyDevice}
/>
</SafeAreaView>
);
}
const styles = StyleSheet.create({
container: {
flex: 1,
justifyContent: 'center',
padding: 24,
},
status: {
marginBottom: 16,
},
});In a real project, replace your-app-id and business-request-id with your own configuration and business request identifier, then connect your HTTPS backend API at the indicated location.
7. Run and verify
After installing or changing native dependencies, rebuild the application. Refreshing JavaScript alone does not load new native modules.
Start Metro:
npx react-native startIn another terminal, run the target platform:
# Android
npx react-native run-android
# iOS
npx react-native run-iosVerify the integration in this order:
- The application completes a native build and starts successfully.
GeelabGuard.initializecompletes successfully.- Selecting Generate device receipt causes
submitReceiptto return a receipt. - The application sends
respondedGeeTokento your business backend over HTTPS according to your API contract. - The business backend verifies the token and makes a risk decision.
To check the installed native SDK version, call:
const version = await GeelabGuard.getVersion();Receipt fields
type GeelabGuardReceipt = {
appId: string | null;
geeToken: string | null;
geeId: string | null;
geeIdTimestamp: string | null;
respondedGeeToken: string | null;
originalResponseBase64: string | null;
};geeToken: A locally generated token that can be used for the local receipt flow or as a fallback after a network failure.respondedGeeToken: The token returned by the server after a successful submission. It is typically sent to your business backend for further processing.- The other fields support correlation and diagnostics. Use them according to your GeelabGuard server integration plan.
originalResponseBase64is a Base64 representation of the raw binary response. Decode it only when required in a controlled diagnostic process.
Do not expose the AppID, signData, tokens, or originalResponseBase64 in production logs, analytics platforms, or the user interface.
Error handling
The plugin normalizes errors as GeelabGuardError:
import { GeelabGuard, GeelabGuardError } from 'geelabguard-rn-plugin';
try {
const receipt = await GeelabGuard.submitReceipt('business-request-id');
// Send receipt.respondedGeeToken securely to your business backend.
} catch (error) {
if (error instanceof GeelabGuardError) {
const fallbackGeeToken = error.receipt?.geeToken;
// Decide whether to use fallbackGeeToken according to error.code and your business policy.
}
}| Error code | Meaning |
|---|---|
INVALID_ARGUMENT | The AppID, service endpoint, or another argument is invalid. |
NOT_INITIALIZED | The SDK has not been initialized, or the native SDK did not return a receipt. |
NETWORK_ERROR | A network error occurred during native submission. |
INVALID_RESPONSE | The service response format is invalid. |
SERVICE_FAILURE | The server reported a processing failure. |
UNKNOWN_NATIVE_ERROR | The native SDK returned an unclassified error. |
For NETWORK_ERROR, INVALID_RESPONSE, or SERVICE_FAILURE, the error may contain a receipt with a local geeToken. Your backend and business policy should determine whether to use that token as a fallback.
Frequently asked questions
The Android build reports a missing SDK
Confirm that the file is located at:
node_modules/geelabguard-rn-plugin/android/libs/geelabguard_android_vx.y.z_date.aarIf you recently reinstalled the dependencies, copy the AAR again and rebuild the app.
pod install reports a missing SDK on iOS
Confirm that the directory is located at:
node_modules/geelabguard-rn-plugin/ios/Frameworks/GeelabGuardSDK.xcframeworkRun pod install again, then rebuild the iOS application.
GeelabGuard is not linked appears
Confirm that the native dependencies are installed, then perform a complete rebuild of the Android or iOS application. Refreshing Metro or reloading JavaScript cannot link a native module.
iOS reports duplicate symbols
Do not declare another Objective-C class named GeelabGuard in the host application. The native SDK already exports this class. The React Native bridge is registered internally as RNGeelabGuard, while the JavaScript module name remains GeelabGuard.
A receipt cannot be obtained
Wait for GeelabGuard.initialize to complete successfully before calling fetchReceipt or submitReceipt. If you provide a regional service endpoint, confirm that it belongs to the same Region as the AppID.
Production checklist
- The native SDKs come from an authorized channel, and their versions match the plugin requirements.
- The AppID matches the regional service endpoint.
- Tokens are sent only to a trusted business backend over HTTPS.
- Server private keys and risk-decision logic are not stored in the React Native client.
- Production logs do not record the AppID,
signData, tokens, or raw responses.
Next steps
- Choose
fetchReceiptorsubmitReceiptaccording to your business scenario. - Receive the token in your business backend, then implement verification, risk decisions, and fallback policies.