Building a React Native wrapper for the Zendesk Mobile SDK
React Native is a popular framework for building native iOS and Android apps using JavaScript and React. To use native SDKs such as the Zendesk Mobile SDK, React Native apps rely on wrapper modules that expose native functionality to JavaScript.
Zendesk does not officially provide a React Native library for Messaging. This article outlines your options for integrating the Zendesk Mobile SDK into a React Native app.
What you need
Before you begin, make sure you have the following:
- A working React Native project. See Setting up the development environment in the React Native documentation.
- A Zendesk account with Messaging enabled.
- A channel key from your Zendesk account. See Getting a channel key.
- Android Studio for Android development.
- Xcode for iOS development.
Community libraries
Several open-source React Native wrappers for the Zendesk Messaging SDK are available from the developer community, including:
- react-native-zendesk-messaging by leegeunhyeok
- react-native-zendesk-messaging by robbywh
You can use either library as-is, or clone them if you need additional functionality.
Building your own wrapper
A React Native wrapper is a bridge module that exposes native SDK methods to your JavaScript code. You write the native implementation once for Android (Kotlin) and once for iOS (Swift), then call both through a shared JavaScript interface.
You don't need to wrap every API in the Messaging SDK. Most apps only need a small subset of the available methods. You can start with the minimum required APIs and add more as your app's requirements grow.
Minimum required APIs
For a basic integration without user authentication, your wrapper needs to support the following two SDK calls:
-
Initialize the SDK: This call configures the SDK with your channel key and must be made once when the app starts, before any other SDK methods are called. Calling it more than once has no effect.
-
Show the messaging interface: This call launches the Zendesk Messaging UI as a native screen. On Android it starts a new Activity, and on iOS it presents a
UIViewController. Your wrapper triggers this in response to a user action, such as tapping a button.
Adding JWT user authentication
If your app requires authenticated users (for example, to associate conversations with a logged-in customer), you need to add JWT authentication support to your wrapper. This involves two additional SDK calls:
- Login: passes a JWT to the SDK to identify the current user
- Logout: clears the user session when they sign out of your app
Without these calls, all conversations are anonymous and can't be linked to a user identity in Zendesk.
Bridge architecture
When bridging native Android and iOS code into React Native, you can use either the messageQueue or the newer TurboModules architecture.
For a complete walkthrough of building a wrapper using Native Modules, see Building a React Native wrapper below.
Using AI code generation
Because wrapper code follows a predictable, repeatable pattern for both iOS and Android, it's a strong candidate for AI-assisted generation using tools like Claude Code or OpenAI Codex.
For example, you can use the following prompt as a starting point:
Create a React Native wrapper for the Zendesk Mobile SDK for Android and iOS. The SDKs are documented here: https://zendesk.github.io/sdk_zendesk_ios/ and https://zendesk.github.io/mobile_sdk_javadocs/zendesk-sdks/
Building a React Native wrapper
The following steps show you how to build a minimal React Native wrapper that initializes the Zendesk Messaging SDK and presents the messaging interface to the user.
Step 1: Configuring your project
Before you can use the Zendesk Messaging SDK in React Native, add the native SDK dependencies to each platform project. This ensures your Android and iOS builds can access the Zendesk APIs that your wrapper will expose to JavaScript.
Android
-
In android/build.gradle (project-level), add the Zendesk Maven repository:
allprojects {repositories {maven { url 'https://zendesk.jfrog.io/artifactory/repo' }}} -
In android/app/build.gradle, add the Messaging SDK dependency:
dependencies {implementation "zendesk.messaging:messaging-android:x.x.x"}Replace
x.x.xwith the latest version from the Android SDK release notes.
iOS
On iOS, add the Messaging SDK with Swift Package Manager. You can use Xcode or edit Package.swift directly, depending on how your project is structured.
Option A: Xcode
- In Xcode, select File > Add Package Dependencies.
- Enter the repository URL:
https://github.com/zendesk/sdk_messaging_ios - Set the version rule to Up to Next Major from the latest release.
Option B: Package.swift
Add the following entry to your Package.swift dependencies:
dependencies: [.package(name: "ZendeskSDKMessaging",url: "https://github.com/zendesk/sdk_messaging_ios",from: "x.x.x")]
Replace x.x.x with the latest version from the
iOS SDK release notes.
Then add ZendeskSDKMessaging as a dependency to your target. This transitively includes
ZendeskSDK and all other required packages.
Step 2: Creating the Android bridge
Next, expose the Android SDK methods you need to React Native. In this example, the bridge includes two methods: one to initialize the SDK and one to show the messaging UI. The bridge consists of two files:
- a module that wraps the SDK calls
- a package class that registers the module with React Native
-
In your Android project, create a file named ZendeskMessagingModule.kt and add the following:
package com.yourprojectimport com.facebook.react.bridge.ReactApplicationContextimport com.facebook.react.bridge.ReactContextBaseJavaModuleimport com.facebook.react.bridge.ReactMethodimport zendesk.messaging.android.Zendeskclass ZendeskMessagingModule(reactContext: ReactApplicationContext) : ReactContextBaseJavaModule(reactContext) {override fun getName(): String = "ZendeskMessaging"@ReactMethodfun initialize(channelKey: String) {Zendesk.initialize(context = reactApplicationContext,channelKey = channelKey,successCallback = { _ -> /* Initialization successful */ },failureCallback = { error -> /* Handle error: log or notify the user */ })}@ReactMethodfun showMessaging() {val activity = currentActivity ?: returnZendesk.instance.messaging.showMessaging(activity)}}For more information on handling initialization errors, see the Android SDK documentation.
-
In your Android project, create a file named ZendeskMessagingPackage.kt and add the following:
package com.yourprojectimport com.facebook.react.ReactPackageimport com.facebook.react.bridge.NativeModuleimport com.facebook.react.bridge.ReactApplicationContextimport com.facebook.react.uimanager.ViewManagerclass ZendeskMessagingPackage : ReactPackage {override fun createNativeModules(reactContext: ReactApplicationContext): List<NativeModule> =listOf(ZendeskMessagingModule(reactContext))override fun createViewManagers(reactContext: ReactApplicationContext): List<ViewManager<*, *>> =emptyList()}Replace
com.yourprojectwith your app's actual package name. You can find this in your AndroidManifest.xml file. -
In MainApplication.kt, add
ZendeskMessagingPackageto the list of packages:override fun getPackages(): List<ReactPackage> =PackageList(this).packages.apply {add(ZendeskMessagingPackage())}
Step 3: Creating the iOS bridge
On iOS, you expose the native SDK to React Native by creating a Swift implementation file and an Objective-C file that registers the module with the bridge.
Swift implementation
In your iOS project, create a file named ZendeskMessaging.swift and add the following:
import Foundationimport ZendeskSDKMessagingimport ZendeskSDK@objc(ZendeskMessaging)class ZendeskMessaging: NSObject {@objc(initialize:)func initialize(channelKey: String) {Zendesk.initialize(withChannelKey: channelKey, messagingFactory: DefaultMessagingFactory()) { result inif case .failure(let error) = result {// Handle error: log or notify the userprint("Zendesk initialization error: \(error)")}}}@objcfunc showMessaging() {DispatchQueue.main.async {guard let rootVC = UIApplication.shared.delegate?.window??.rootViewController else { return }if let messagingVC = Zendesk.instance?.messaging?.messagingViewController() {rootVC.present(messagingVC, animated: true, completion: nil)}}}}
For more information on handling initialization errors, see the iOS SDK documentation.
Objective-C bridge file
In your iOS project, create a file named ZendeskMessaging.m to expose the Swift module to React Native. Add the following:
#import <React/RCTBridgeModule.h>@interface RCT_EXTERN_MODULE(ZendeskMessaging, NSObject)RCT_EXTERN_METHOD(initialize:(NSString *)channelKey)RCT_EXTERN_METHOD(showMessaging)@end
Step 4: Creating the JavaScript interface
Now that the native methods are available, create a thin JavaScript interface to keep your React Native components clean and easy to read. In your project's src folder, create a file named Zendesk.js and add the following:
import { NativeModules } from 'react-native';const { ZendeskMessaging } = NativeModules;export default {init: (channelKey) => ZendeskMessaging.initialize(channelKey),open: () => ZendeskMessaging.showMessaging(),};
Step 5: Using the wrapper in your app
Finally, import the wrapper in your React Native app and call it when the app loads or when the user taps a button.
import React, { useEffect } from 'react';import { Button } from 'react-native';import Zendesk from './Zendesk';const App = () => {useEffect(() => {Zendesk.init('YOUR_CHANNEL_KEY');}, []);return (<Button title="Chat Now" onPress={() => Zendesk.open()} />);};
Replace YOUR_CHANNEL_KEY with the channel key from your Zendesk account. The same channel key works for both Android and iOS. For more information, see Get a channel key.