> For the complete documentation index, see [llms.txt](https://docs.talsec.app/freerasp/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.talsec.app/freerasp/freerasp/integration/react-native.md).

# React Native

{% hint style="success" %}
**Example**: <https://github.com/talsec/Free-RASP-ReactNative>
{% endhint %}

## 📝 Prerequisites

The freeRASP has the following prerequisites that must be met before starting.

### Android

freeRASP requires a minimum **SDK** level of **23**. React Native projects, by default, support even lower levels of minimum SDK. This creates an inconsistency we must solve by updating the minimum SDK level of the application:

* From the root of your project, go to `android` **>** `build.gradle`.
* In `buildscript`, update `minSdkVersion` to at least **23** (Android 6.0) or higher.

{% code title="android/build.gradle" %}

```gradle
buildscript {
    ext {
      minSdkVersion 23
    }
}
```

{% endcode %}

#### Raise Kotlin version

Since freeRASP 4.0.0, it is necessary to raise version of Kotlin in your project. This applies for projects running on RN < 0.77.&#x20;

* From the root of your project, go to `android` **>** `build.gradle` (or equivalent).
* In `buildscript.ext`, update `kotlinVersion` to at least **2.0.0** or higher.
* In `buildscript.dependencies`, specify the same version for`kotlin-gradle-plugin` .

```groovy
buildscript {
    ext {
        kotlinVersion = '2.0.0'
    }
    dependencies {
        classpath("org.jetbrains.kotlin:kotlin-gradle-plugin:2.0.0")
    }
```

#### Enable Screenshot and Screen Recording Detection

To [detect screenshots](/freerasp/freerasp/wiki/threat-detection/screen-capture.md#screenshot-detection) and [screen recordings ](/freerasp/freerasp/wiki/threat-detection/screen-capture.md#screen-recording-detection), add the following permissions to your `AndroidManifest.xml` file inside the `<manifest>` root tag:

```xml
 <uses-permission android:name="android.permission.DETECT_SCREEN_CAPTURE" />
 <uses-permission android:name="android.permission.DETECT_SCREEN_RECORDING" />
```

{% hint style="warning" %}
Screenshot Detection is supported **on Android 14 (API level 34) and higher**. \
\
Screen Recording Detection is supported **on Android 15 (API level 35) and higher**.\
\
Application of **FLAG\_SECURE** on Android Window or calling `blockScreenCapture(true)` disables this callback.
{% endhint %}

To utilize active protection, you can use&#x20;

```jsx
import { blockScreenCapture } from 'freerasp-react-native';
await blockScreenCapture(true);
```

To receive whether the screen capture is blocked, you can use

```jsx
import { isScreenCaptureBlocked } from 'freerasp-react-native';
const response = await isScreenCaptureBlocked();
```

For more details about all these screen capture methods, see [Screen Capture](/freerasp/freerasp/wiki/threat-detection/screen-capture.md).

### iOS

By default, freeRASP's iOS binary is integrated as a vendored CocoaPods framework. Alternatively, you can integrate it as a Swift Package.

{% hint style="info" %}
The choice of package manager only alters how the iOS binary is linked; the JavaScript API and all other integration steps remain unchanged.
{% endhint %}

Select your preferred installation method below.

{% tabs %}
{% tab title="CocoaPods" %}
Navigate to the `ios` folder and run:

```bash
cd ios
pod install
```

{% endtab %}

{% tab title="Swift Package Manager" %}
Integrate freeRASP's iOS binary as a Swift Package by gating the setup behind an environment variable in your `Podfile`.

{% hint style="info" %}
**Prerequisites**

* React Native 0.75+ (older versions automatically fall back to the vendored CocoaPods framework)
* iOS Deployment Target 13.0+
  {% endhint %}

{% stepper %}
{% step %}

### Update the Podfile

Enforce dynamic frameworks when SPM is requested, and embed the package inside your existing `post_install` block:

```ruby
platform :ios, min_ios_version_supported
prepare_react_native_project!

# Swift Package Manager integration requires dynamically linked frameworks
use_freerasp_spm = ENV['FREERASP_USE_SPM'] == '1'
use_frameworks! :linkage => :dynamic if use_freerasp_spm

target 'YourApp' do
  # ... your existing configuration ...

  post_install do |installer|
    # ... your existing post_install logic (react_native_post_install, etc.) ...

    require_relative '../node_modules/freerasp-react-native/freerasp_spm.rb'
    freerasp_embed_talsec_spm!(installer)
  end
end
```

{% hint style="warning" %}
Place the `require_relative` and `freerasp_embed_talsec_spm!(installer)` calls inside your existing `post_install do |installer|` block — do not create a second one, as a duplicate hook will override the first.
{% endhint %}
{% endstep %}

{% step %}

### Install with the SPM flag

```shellscript
cd ios
FREERASP_USE_SPM=1 pod install
```

{% endstep %}
{% endstepper %}

{% hint style="info" %}
**Reverting to CocoaPods**

Run `pod install` again without the `FREERASP_USE_SPM` environment variable set.
{% endhint %}
{% endtab %}
{% endtabs %}

***

## 📦 Install the plugin

* Install the plugin using your preferred package manager<br>

  <pre class="language-bash" data-title="npm"><code class="lang-bash">npm install freerasp-react-native
  </code></pre>

  <pre class="language-bash" data-title="yarn"><code class="lang-bash">yarn add freerasp-react-native
  </code></pre>
* Navigate to the `ios` folder and run:<br>

  ```bash
  $ pod install
  ```

***

## ⚙️ Setup the Configuration for your App

To ensure freeRASP functions correctly, you need to provide the necessary configuration and initialize it. All required values must be filled in for the plugin to operate properly. Use the following template to configure the plugin. Detailed descriptions of the configuration options are provided[ on the API page](/freerasp/freerasp/integration/react-native/api.md#talsecconfig).

In the the entry point to your app, import freeRASP and add the code below.&#x20;

For Android apps, you must get your expected signing certificate hashes in Base64 form. You can go through[ this manual](/freerasp/freerasp/wiki/getting-signing-certificate-hash.md) to learn how to sign your app in more detail, including manual signing and using Google's Play app signing.&#x20;

FreeRASP provides a React Custom Hook that handles all required logic as registration of freeRASP, mounting and unmounting of listeners for you.

{% code title="App.tsx" %}

```tsx
import { useFreeRasp } from 'freerasp-react-native';

// app configuration
const config = {
  androidConfig: {
    packageName: 'com.awesomeproject',
    certificateHashes: ['mVr/qQLO8DKTwqlL+B1qigl9NoBnbiUs8b4c2Ewcz0k='],  // replace with your release (!) signing certificate hash(es)
    supportedAlternativeStores: ['com.sec.android.app.samsungapps'],
  },
  iosConfig: {
    appBundleId: 'com.awesomeproject',
    appTeamId: 'your_team_ID',
  },
  watcherMail: 'your_email_address@example.com', // for Security Reports, Talsec Portal, Updates
  isProd: true,
  killOnBypass: true,
};
```

{% endcode %}

{% hint style="info" %}
**Configuration Parameters**

* **`isProd`** - a boolean flag that determines whether the freeRASP integration is in the Dev or Release version. If you want to learn more about `isProd`, visit this [wiki section](/freerasp/freerasp/wiki/prod-flag.md).
* **`killOnBypass`** - a boolean flag that enables the freeRASP in-SDK reaction to kill the application if it detects any unwanted manipulation with the callback mechanisms.
* **`watcherMail`** - By providing your watcherMail, you consent to receive security reports, product updates, and other essential communications from Talsec. [Learn more](/freerasp/freerasp/wiki/role-of-watchermail.md) about the role of `watcherMail`.
  {% endhint %}

***

## 👷 Handle detected threats

freeRASP executes periodical checks when the application is running. You can handle the detected threats using **listeners**. For example, you can log the event, show a window to the user or kill the application. See the [Threat detection](/freerasp/freerasp/wiki/threat-detection.md) in the wiki to learn more details about the performed checks and their importance for app security.

Threat reactions should be specified inside a JavaScript object.

<pre class="language-tsx"><code class="lang-tsx">// reactions for detected threats
const actions = {
  // Android &#x26; iOS
  <a data-footnote-ref href="#user-content-fn-1">privilegedAccess</a>: () => {
    console.log('privilegedAccess');
  },
  // Android &#x26; iOS
  <a data-footnote-ref href="#user-content-fn-2">debug</a>: () => {
    console.log('debug');
  },
  // Android &#x26; iOS
  <a data-footnote-ref href="#user-content-fn-3">simulator</a>: () => {
    console.log('simulator');
  },
  // Android &#x26; iOS
  <a data-footnote-ref href="#user-content-fn-4">appIntegrity</a>: () => {
    console.log('appIntegrity');
  },
  // Android &#x26; iOS
  <a data-footnote-ref href="#user-content-fn-5">unofficialStore</a>: () => {
    console.log('unofficialStore');
  },
  // Android &#x26; iOS
  <a data-footnote-ref href="#user-content-fn-6">hooks</a>: () => {
    console.log('hooks');
  },
  // Android &#x26; iOS
  <a data-footnote-ref href="#user-content-fn-7">deviceBinding</a>: () => {
    console.log('deviceBinding');
  },
  // Android &#x26; iOS
  <a data-footnote-ref href="#user-content-fn-8">secureHardwareNotAvailable</a>: () => {
    console.log('secureHardwareNotAvailable');
  },
  // Android &#x26; iOS
  <a data-footnote-ref href="#user-content-fn-9">systemVPN</a>: () => {
    console.log('systemVPN');
  },
  // Android &#x26; iOS
  <a data-footnote-ref href="#user-content-fn-10">passcode</a>: () => {
    console.log('passcode');
  },
  // iOS only
  <a data-footnote-ref href="#user-content-fn-7">deviceID</a>: () => {
    console.log('deviceID');
  },
  // Android only
  <a data-footnote-ref href="#user-content-fn-11">obfuscationIssues</a>: () => {
    console.log('obfuscationIssues');
  },
  // Android only
  <a data-footnote-ref href="#user-content-fn-12">devMode</a>: () => {
    console.log('devMode');
  },
  // Android only
  <a data-footnote-ref href="#user-content-fn-13">adbEnabled</a>: () => {
    console.log('adbEnabled');
  },
  // Android &#x26; iOS
  <a data-footnote-ref href="#user-content-fn-14">screenshot</a>: () => {
    console.log('screenshot');
  },
  // Android &#x26; iOS
  <a data-footnote-ref href="#user-content-fn-15">screenRecording</a>: () => {
    console.log('screenRecording');
  },  
  // Android only
  <a data-footnote-ref href="#user-content-fn-16">multiInstance</a>: () => {
    console.log('multiInstance');
  },
  // Android &#x26; iOS  
  timeSpoofing: () => {
    console.log('timeSpoofing');
  },
  // Android only
  locationSpoofing: () => {
    console.log('locationSpoofing');
  },
  // Android only
  unsecureWifi: () => {
    console.log('unsecureWifi');
  },
  // Android only
  automation: () => {
    console.log('automation');
  },
  // Android only
  bootloader: () => {
    console.log('bootloader');
  },
};
</code></pre>

## 👷 RASP Execution State Listener

freeRASP can also notify apps when initial checks are done using the raspExecutionStateActions callback:

{% code title="App.jsx/App.tsx" %}

```typescript
  const raspExecutionStateActions = {
    allChecksFinished: () => {
      console.log('allChecksFinished');
    },
  };
```

{% endcode %}

***

## 🛡️ Start freeRASP

Start freeRASP to detect threats by calling the `useFreeRasp` hook, below the created config and the callback handler:

```tsx
useFreeRasp(config, actions, raspExecutionStateActions);
```

{% hint style="info" %}
Please note that **useFreeRasp** Hook should be called **outside** **useEffect**.
{% endhint %}

When freeRASP initializes correctly, you should see `freeRASP initialized` message in the logs. Otherwise, you'll see a warning with a description of what went wrong.

{% hint style="info" %}
You can override this default behaviour by extending the **actions** object with **started** key (to change action after successful initialization), and **initializationError** key (to set up action after unsuccessful initialization)
{% endhint %}

{% hint style="info" %}
For the version you’re integrating, you can find the specific **dSYMs** for debugging in [Releases](https://github.com/talsec/Free-RASP-ReactNative/releases).
{% endhint %}

### Alternative: Initialize freeRASP in a Class component

Import methods from the freeRASP plugin:

```tsx
import {
  talsecStart,
  setThreatListeners,
  removeThreatListeners,
} from 'freerasp-react-native';
```

Override `componentDidMount()` method in the entry point to your app set listeners to threats and start freeRASP:

```tsx
async componentDidMount() {
  await setThreatListeners(actions);
  const response = await talsecStart(config);
  console.log(response); // freeRASP started
}
```

{% hint style="info" %}
*In this code snippet, `actions` is object with your reactions to threats and `config` is a freeRASP configuration object from previous parts of the readme.*
{% endhint %}

Override `componentWillUnmount()` method where you clean up the listeners:

```tsx
componentWillUnmount() {
  removeThreatListeners();
}
```

***

## 🌁 Enable source code obfuscation

The easiest way to obfuscate your app is via code minification, a technique that reduces the size of the compiled code by removing unnecessary characters, whitespace, and renaming variables and functions to shorter names. It can be configured for Android devices in `android/app/build.gradle` like:

```gradle
android {
    buildTypes {
        release {
            minifyEnabled true
            shrinkResources true
            proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
        }
    }
}
```

Please note that some other modules in your app may rely on reflection, therefore it may be necessary to add corresponding keep rules into proguard-rules.pro file.

If there is a problem with the obfuscation, freeRASP will notify you about it via `obfuscationIssues` callback.

Read more about why this is important in the[ wiki](/freerasp/freerasp/wiki/source-code-obfuscation.md).

***

## 🆔 (Optionally) Set External ID

The `externalId` allows you to send a custom identifier (such as a User ID) to the [Talsec Portal](https://my.talsec.app/). This identifier will be visible in the Dashboard, enabling you to correlate security incidents with specific users in your system.

```javascript
import { storeExternalId } from 'freerasp-react-native';

const yourCustomData = "user_123_456";

try {
    const result = await storeExternalId(yourCustomData);
    console.log("External ID successfully set:", result);
} catch (error) {
    console.error("Failed to set External ID:", error.message);
}

```

{% hint style="info" %}
**Requirements**

* **Allowed characters**: Only alphanumeric characters (a-z, A-Z, 0-9) and the following special characters: +, \_, -, /, :, =.
* If the ID contains any other characters, the promise will be rejected with an error message and the value will not be stored.
  {% endhint %}

***

## ☢️ (Optionally) Integrate freeMalwareDetection

**freeMalwareDetection** is a powerful feature designed to enhance the security of your Android application by quickly and efficiently **scanning for malicious or suspicious applications** (e.g. Android malware) based on **various blacklists and security policies**.&#x20;

It helps to detect apps with **suspicious package names, hashes, or potentially dangerous permissions**.

Visit the [freeMalwareDetection](https://docs.talsec.app/freemalwaredetection) repository to learn more about this feature! For the integration, refer to the [integration guide](https://docs.talsec.app/freemalwaredetection/integration-guide/malware-detection-configuration) for the React Native platform.

***

## 🖥️ Check Talsec Portal

Check out [Data Visualisation Portal](/freerasp/freerasp/data-visualisation-portal.md) and register using your [watcherMail](/freerasp/freerasp/wiki/role-of-watchermail.md) to see your data. If you integrated the SDK successfully, the application will be present **after a few hours**. The visualisations will be active later due to the bucketing mechanism.

{% hint style="warning" %}
You have to use the **same email for the Portal** as you used for the **watcherMail** parameter.
{% endhint %}

[^1]: Learn more: <https://docs.talsec.app/freerasp/wiki/threat-detection/detecting-rooted-or-jailbroken-devices>

[^2]: Learn more: <https://docs.talsec.app/freerasp/wiki/threat-detection/debugger-detection>

[^3]: Learn more: <https://docs.talsec.app/freerasp/wiki/threat-detection/emulator-detection>

[^4]: Learn more: <https://docs.talsec.app/freerasp/wiki/threat-detection/app-tampering-detection>

[^5]: Learn more: <https://docs.talsec.app/freerasp/wiki/threat-detection/detecting-unofficial-installation>

[^6]: Learn more: <https://docs.talsec.app/freerasp/wiki/threat-detection/hook-detection>

[^7]: Learn more: <https://docs.talsec.app/freerasp/wiki/threat-detection/device-binding-detection>

[^8]: Learn more: <https://docs.talsec.app/freerasp/wiki/threat-detection/secure-hardware-detection-keystore-keychain-secure-storage-check>

[^9]: Learn more: <https://docs.talsec.app/freerasp/wiki/threat-detection/system-vpn-detection>

[^10]: Learn more: <https://docs.talsec.app/freerasp/wiki/threat-detection/passcode>

[^11]: Learn more: <https://docs.talsec.app/freerasp/wiki/threat-detection/missing-obfuscation-detection-android-devices-only>

[^12]: Learn more: <https://docs.talsec.app/freerasp/wiki/threat-detection/developer-mode-detection-android-devices-only>

[^13]: Learn more: <https://docs.talsec.app/freerasp/wiki/threat-detection/adb-enabled-detection-android-devices-only>

[^14]: Learn more: <https://docs.talsec.app/freerasp/wiki/threat-detection/screen-capture#screenshot-detection>

[^15]: Learn more: <https://docs.talsec.app/freerasp/wiki/threat-detection/screen-capture#screen-recording-detection>

[^16]: Learn more:\
    [https://docs.talsec.app/freerasp/wiki/threat-detection/multi-instance-detection](https://docs.talsec.app/freerasp/wiki/threat-detection/multi-instance-detection-android-devices-only)


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

## Querying This Documentation
If you need additional information that is not directly available in this page, you can query the documentation by asking a question.

Perform an HTTP GET request on the following URL with the `ask` and `goal` query parameters:

```
GET https://docs.talsec.app/freerasp/freerasp/integration/react-native.md?ask=<question>&goal=<user_goal>
```

`ask` is the immediate question: it should be specific, self-contained, and written in natural language.
`goal` is what the user is ultimately trying to achieve, the reason they need the answer. Sharing it helps GitBook give you a better, more relevant answer. A goal is most helpful when it describes the outcome the user wants rather than restating the question. For example, with `ask=how do I create an API token`, a goal like `automate deployments from our CI pipeline` lets GitBook tailor the answer to that use case.

The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
