jio-payment-sdk
v1.3.4
Published
A React Native payment SDK supporting Cards, UPI, and Net Banking
Maintainers
Readme
Jio Payment SDK – Full Integration Guide
📦 Prerequisites
Before starting integration, ensure the following are installed and configured:
- Node.js (>= 16.x)
- npm or yarn
- Watchman (macOS recommended)
- Xcode (latest) with Command Line Tools — required for iOS
- CocoaPods — run:
sudo gem install cocoapods - Android Studio with:
- Android SDK Platform 36
- Android SDK Build-Tools 36
- NDK 27.x
- CMake 3.22.x
- Java 17 (Recommended for RN 0.73+)
- Physical device or emulators for Android & iOS testing
- React Native CLI installed globally (optional)
npm install -g react-native-cli
A complete React Native SDK to integrate Jio Payment Gateway supporting Cards, UPI, and Net Banking.
This guide provides step‑by‑step setup for Android and iOS including Metro config, Gradle config, permissions, Pods setup, and a sample implementation.
📋 Current Version
Latest Stable: 1.3.4
Note: This version is automatically updated from
package.json. No manual updates needed!
What's New in v1.3.4
- ✅ Fixed Metro Bundler Module Resolution - Resolved
index.jsresolution errors - ✅ Improved Package Structure - Added
exportsfield for better module resolution - ✅ React Native 0.82+ Compatibility - Full support for latest React Native versions
- ✅ Removed Invalid Types Reference - Fixed package.json structure
Installation:
npm install [email protected] --legacy-peer-deps📌 1. Install React Native CLI (if not installed)
npm install -g react-native-cli📌 2. Create a New React Native Project
npx @react-native-community/cli init JioPGMerchantAppSampleor specify RN version:
npx @react-native-community/cli init JioPGMerchantAppSample --version 0.73.6For iOS builds, when asked:
Do you want to install CocoaPods now? → y📌 3. Run the Fresh Project
Android
cd JioPGMerchantAppSample
npx react-native run-androidiOS
cd JioPGMerchantAppSample
npx react-native run-iosor open:
ios/JioPGMerchantAppSample.xcworkspace📌 4. Install SDK from NPM
Install the latest version of the SDK:
npm install jio-payment-sdk@latest --legacy-peer-depsCurrent Version: 1.3.4
Note: Use
--legacy-peer-depsflag to handle peer dependency conflicts with React Native 0.82+
📌 5. Update package.json Dependencies
Add these inside "dependencies":
"dependencies": {
"@react-navigation/native": "^6.1.6",
"@react-navigation/native-stack": "^6.9.12",
"axios": "^1.5.0",
"crypto-js": "^4.2.0",
"jio-payment-sdk": "^1.3.4",
"@babel/runtime": "^7.28.4",
"react-native-fast-image": "^8.6.3",
"react-native-gif": "^1.0.3",
"react-native-qrcode-svg": "^6.3.15",
"react-native-screens": "^4.13.1",
"react-native-svg": "^15.12.1",
"react-native-vector-icons": "^10.3.0",
"react-native-webview": "^13.15.0"
}Important: Ensure you're using SDK version
1.3.4or later for React Native 0.82+ compatibility.
Then run:
npm install --legacy-peer-deps📌 6. Install iOS Pods
cd ios
pod install
cd ..📌 7. Clean Android Build
cd android
./gradlew clean
cd ..📌 8. Update Android Build Config (android/build.gradle)
buildscript {
ext {
buildToolsVersion = "36.0.0"
minSdkVersion = 29
compileSdkVersion = 36
targetSdkVersion = 36
ndkVersion = "27.1.12297006"
kotlinVersion = "2.1.20"
FLIPPER_VERSION = "0.0.0"
}
repositories {
google()
mavenCentral()
}
dependencies {
classpath("com.android.tools.build:gradle")
classpath("com.facebook.react:react-native-gradle-plugin")
classpath("org.jetbrains.kotlin:kotlin-gradle-plugin")
}
}
apply plugin: "com.facebook.react.rootproject"📌 9. Android App Build Config (android/app/build.gradle)
Inside android { ... }
namespace "com.jiopgmerchantappsample"
defaultConfig {
versionName "1.0"
externalNativeBuild {
cmake {
cppFlags "-Wno-deprecated-declarations"
}
}
}
lintOptions {
abortOnError false
checkReleaseBuilds false
}📌 10. Add Android Permissions & Queries (AndroidManifest.xml)
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.QUERY_ALL_PACKAGES" />
<uses-permission android:name="android.permission.QUERY_PACKAGES" />
<queries>
<package android:name="com.google.android.apps.nbu.paisa.user" />
<package android:name="net.one97.paytm" />
<package android:name="com.phonepe.app" />
<package android:name="com.dreamplug.androidapp" />
<package android:name="in.org.npci.upiapp" />
<package android:name="com.whatsapp" />
<package android:name="com.axis.bank" />
<package android:name="com.hdfcbank" />
<package android:name="com.icici.bank" />
<package android:name="com.sbi.SBIFreedomPlus" />
</queries>Inside <application>:
android:usesCleartextTraffic="true"(Set false for production)
📌 11. MainApplication.kt (Android)
Use:
class MainApplication : Application(), ReactApplication {
override val reactNativeHost: ReactNativeHost =
object : DefaultReactNativeHost(this) {
override fun getPackages(): List<ReactPackage> =
PackageList(this).packages
override fun getJSMainModuleName(): String = "index"
override fun getUseDeveloperSupport(): Boolean = BuildConfig.DEBUG
override val isNewArchEnabled: Boolean = BuildConfig.IS_NEW_ARCHITECTURE_ENABLED
override val isHermesEnabled: Boolean = BuildConfig.IS_HERMES_ENABLED
}
override val reactHost: ReactHost
get() = getDefaultReactHost(applicationContext, reactNativeHost)
override fun onCreate() {
super.onCreate()
loadReactNative(this)
}
}📌 12. Metro Configuration (metro.config.js)
const { getDefaultConfig, mergeConfig } = require('@react-native/metro-config');
const path = require('path');
const sdkPath = path.resolve(__dirname, 'node_modules/jio-payment-sdk');
const defaultConfig = getDefaultConfig(__dirname);
module.exports = mergeConfig(defaultConfig, {
resolver: {
sourceExts: [
...defaultConfig.resolver.sourceExts,
'ts','tsx','jsx','cjs',
],
extraNodeModules: {
react: path.resolve(__dirname, 'node_modules/react'),
'react-native': path.resolve(__dirname, 'node_modules/react-native'),
},
unstable_enablePackageExports: true,
},
transformer: {
unstable_allowRequireContext: true,
minifierConfig: {
keep_classnames: true,
keep_fnames: true,
mangle: false,
},
},
watchFolders: [sdkPath],
});📌 13. Sample Integration (App.tsx)
Important: When the user cancels (e.g. taps back on the Checkout screen), the SDK calls onError with error.message === 'CANCELLED' and optionally onRequestClose. The host app must unmount or hide the PaymentSDK (e.g. set showPayment to false) so the payment screen closes. Otherwise the back button will appear to do nothing.
import React, { useState } from 'react';
import {
View, Text, TouchableOpacity, ScrollView, StyleSheet, StatusBar
} from 'react-native';
import { SafeAreaProvider, SafeAreaView, useSafeAreaInsets } from 'react-native-safe-area-context';
import { PaymentSDK, PaymentMode, EnvironmentType, CANCELLED_ERROR_MESSAGE } from 'jio-payment-sdk';
function App() {
return (
<SafeAreaProvider>
<StatusBar barStyle="dark-content" />
<AppContent />
</SafeAreaProvider>
);
}
function AppContent() {
const [showPayment, setShowPayment] = useState(false);
const [successResponse, setSuccessResponse] = useState(null);
const priceSummary = {
subtotal: 100,
tax: 18,
total: 118,
};
const onSuccess = data => setSuccessResponse(data);
const onError = err => {
setSuccessResponse(err);
// Close payment UI when user cancels (e.g. back on Checkout)
if (err?.message === CANCELLED_ERROR_MESSAGE) {
setShowPayment(false);
}
};
const onRequestClose = () => setShowPayment(false);
const onTimeout = data => setSuccessResponse(data);
if (showPayment) {
const txn_no = `TXN_NO_${Date.now()}`;
return (
<PaymentSDK
amount={priceSummary.total}
merchantId="JP3000000666666"
aggregatorId="JP4000000765432"
customerName="John Doe"
customerEmail="[email protected]"
merchantName="Jio Payment Demo"
merchantImage="https://yourlogo.png"
merchantTransactionNumber={txn_no}
onSuccess={onSuccess}
onError={onError}
onRequestClose={onRequestClose}
secretKey="your_secret_key"
environment={EnvironmentType.UAT}
//Below are optional parameters
// customerMobileNumber='9875431234'
// themePrimaryColor="#FF6B6B"
// themeSecondaryColor="#FF6B6B"
// allowedPaymentModes={[PaymentMode.CARD, PaymentMode.UPI, PaymentMode.NETBANKING]}
/>
);
}
return (
<SafeAreaView>
<ScrollView>
<TouchableOpacity onPress={() => setShowPayment(true)}>
<Text>Proceed to Payment</Text>
</TouchableOpacity>
<Text>Callback Response:</Text>
<Text>{JSON.stringify(successResponse)}</Text>
</ScrollView>
</SafeAreaView>
);
}
export default App;Callbacks for closing the payment UI
onError(error)— When the user cancels (e.g. back on Checkout), the SDK calls this witherror.message === 'CANCELLED'. The host should unmount or hide the PaymentSDK so the screen closes.onRequestClose()— Called when the user requests to close the payment flow (e.g. back on Checkout). Implement this to set your "show payment" state tofalseso the SDK is unmounted. Using bothonError(check for CANCELLED) andonRequestCloseensures the back button works regardless of integration style.
📌 14. Starting Metro
npm startIf Metro gets stuck or you encounter module resolution errors:
# Clear Metro cache and restart
rm -rf node_modules/.cache
npx react-native start --reset-cacheIf Metro is stuck on a port:
lsof -i :8081
kill -9 <PID>Troubleshooting Metro Issues:
- If you see errors about
index.jsnot being found, ensure you're using SDK version1.1.7+ - Clear Metro cache:
npx react-native start --reset-cache - Verify SDK installation:
npm list jio-payment-sdk
📌 15. Run Android App
cd android
./gradlew clean
cd ..
npx react-native run-android📌 16. iOS Podfile Required Config
Inside ios/Podfile:
use_react_native!(
:path => config[:reactNativePath],
:app_path => "#{Pod::Config.instance.installation_root}/..",
:new_arch_enabled => true,
:fabric_enabled => true
)📌 17. Run iOS App
cd ios
pod install --repo-update
cd ..
npx react-native run-iosIf build fails → open Xcode and build manually.
✅ Integration Complete
You should now have the Jio Payment SDK working on both Android & iOS with correct Codegen, Metro config, permissions, Gradle setup, and sample payment flow.
🔧 Troubleshooting
Metro Bundler Module Resolution Errors
If you encounter errors like:
Unable to resolve module `jio-payment-sdk` from file...
the package itself specifies a `main` module field that could not be resolvedSolution:
Ensure you're using SDK version
1.3.4or later:npm install jio-payment-sdk@latest --legacy-peer-depsClear Metro cache:
rm -rf node_modules/.cache npx react-native start --reset-cacheVerify the SDK package structure:
ls node_modules/jio-payment-sdk/ # Should show: index.js, package.json, src/, assets/, etc.
Package Structure Fixes (v1.1.7+)
Version 1.1.7 includes important fixes:
- ✅ Removed invalid
typesfield reference - ✅ Added
exportsfield for better module resolution - ✅ Fixed Metro bundler compatibility with React Native 0.82+
Common Issues
Issue: App crashes on launch with SDK import error
- Fix: Update to
[email protected]+and clear Metro cache
Issue: @babel/runtime not found
- Fix: Install it:
npm install @babel/runtime --legacy-peer-deps
Issue: Android build fails
- Fix: Clean build:
cd android && ./gradlew clean && cd ..
📦 SDK Version History
- v1.1.9 - Back button issue resolved, Stable version.
- v1.1.8 - Faced back button issue
- v1.1.7 - Fixed Metro bundler module resolution, added exports field
- v1.1.6 - Previous version (had Metro resolution issues)
- v1.1.5 - Earlier stable version
Recommended: Always use the latest version for best compatibility.
