Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
112 commits
Select commit Hold shift + click to select a range
96a9b53
Configuring successfully so far
Twigz Aug 18, 2025
b0f1483
Adds in registering crypto user
Twigz Aug 19, 2025
357b001
Additional compilation for registerWallet and collectKYC
Twigz Aug 19, 2025
e637349
No more error when trying to use the presenter, but not presenting yet
Twigz Aug 19, 2025
61fe94f
Example iOS configure implementation
Twigz Aug 19, 2025
c5de756
Fixing android side of things
Twigz Aug 19, 2025
a4352ff
Merge branch 'master' into twigz/onramp-rn-bridge
Twigz Aug 25, 2025
bcb1287
Functioning identity and payment selection
Twigz Aug 25, 2025
da3a2b9
Update coloring to be a string
Twigz Aug 25, 2025
10248d5
Update HomeScreen.tsx
Twigz Aug 25, 2025
e7e37b7
At least sometimes display the payment image
Twigz Aug 25, 2025
67b7c55
Added bank account button
Twigz Aug 25, 2025
afcf4e0
Adds in registering a wallet UI
Twigz Aug 25, 2025
1e49365
Fix string
Twigz Aug 26, 2025
5bfb074
Updates Stripe SDK to 24.21.0 and adds CryptoOnramp
Twigz Aug 26, 2025
b4616bd
Adds createCryptoPaymentToken api
Twigz Aug 26, 2025
0273ee1
Modeled perform checkout as if the clientSecret was just a string
Twigz Aug 26, 2025
8521b27
Merge branch 'twigz/update-stripe-ios-pod' into twigz/onramp-rn-bridge
Twigz Aug 26, 2025
97b7ee9
Wrap the collapsible in a StripeProvider
Twigz Aug 26, 2025
5c42c23
Updates the actual Android released version
Twigz Aug 26, 2025
f8cc15c
Stop creating a map for the isLinkUser response
Twigz Aug 26, 2025
1a9a356
Adds in emitting results for authorize and checkout callbacks
Twigz Aug 26, 2025
53a15c5
Adds in missing authorize call
Twigz Aug 26, 2025
e9f2361
handle through a promise instead of a listener
Twigz Aug 26, 2025
52b445e
Update to use promises with types
Twigz Aug 26, 2025
bcd0e9a
Remove unnecessary emitters
Twigz Aug 26, 2025
d6ec796
No need to return a map anymore
Twigz Aug 26, 2025
f85396a
Remove unnecessary type declarations
Twigz Aug 26, 2025
bb25388
update api naming
Twigz Aug 27, 2025
3f0fa5d
Rename collectPaymentMethod
Twigz Aug 27, 2025
7bdf61b
Add in code for checkout
Twigz Aug 27, 2025
eb3d15c
Implements first 5 iOS CryptoOnrampCoordinator methods
mliberatore Aug 27, 2025
67f3e08
Merge branch 'twigz/onramp-rn-bridge' of https://github.com/stripe/st…
mliberatore Aug 27, 2025
da97041
Implements onrampAuthorize
Twigz Aug 27, 2025
38275af
Implements attachKycInfo on iOS
mliberatore Aug 27, 2025
605d878
Implements createCryptoPaymentToken on iOS
mliberatore Aug 27, 2025
310d2d7
Minor refactor to reduce duplication around finding presenting view c…
mliberatore Aug 27, 2025
25530a2
Implements verifyIdentity on iOS
mliberatore Aug 27, 2025
056ddc5
Update build.gradle
Twigz Aug 27, 2025
c73b182
Moves view controller access out of Tasks
mliberatore Aug 27, 2025
4000bca
Merge branch 'twigz/onramp-rn-bridge' of https://github.com/stripe/st…
mliberatore Aug 27, 2025
67a5f76
Implements collectPaymentMethod on iOS
mliberatore Aug 27, 2025
3b4b55c
Adds in ui for creating a crypto payment token
Twigz Aug 27, 2025
223f0b6
Button for authorization, need LAI inserted
Twigz Aug 27, 2025
c135fb9
View controller access was still on a background thread (the RN bindi…
mliberatore Aug 27, 2025
10a4eae
Renames provideCheckoutClientSecret parameter
mliberatore Aug 27, 2025
e72cda8
Implements performCheckout on iOS
mliberatore Aug 27, 2025
7d9b944
Add in kyc attachment ui for testing
Twigz Aug 27, 2025
26eed25
Adds in the api for updating phone number
Twigz Aug 28, 2025
6fd3790
Adds Apple Pay support on iOS
mliberatore Aug 28, 2025
b4bfc24
Merge branch 'twigz/onramp-rn-bridge' of https://github.com/stripe/st…
mliberatore Aug 28, 2025
93a57e1
Removes unneeded structures surrounding single return values
mliberatore Aug 28, 2025
32bd009
zeros out kyc ssn
mliberatore Aug 28, 2025
b8ad64d
Propagates errors appropriately for kycInfo collection on iOS
mliberatore Aug 28, 2025
b21e84a
fix android build
lng-stripe Aug 28, 2025
b7d1ee8
Updates iOS SDK to latest
mliberatore Aug 28, 2025
cfdea91
Implements onrampAuthorize on iOS
mliberatore Aug 28, 2025
7fabe47
Adds test UI for onrampAuthorize
mliberatore Aug 28, 2025
f2218f8
Silences warning in unimplemented updatePhoneNumber on iOS
mliberatore Aug 28, 2025
49479e4
Update CryptoOnrampScreen.tsx
Twigz Aug 28, 2025
e70f290
Merge branch 'twigz/onramp-rn-bridge' of https://github.com/stripe/st…
Twigz Aug 28, 2025
cc32109
propagate configuration result
lng-stripe Aug 28, 2025
f0526dd
adds unimplemented logout api
Twigz Aug 28, 2025
98451ea
Merge branch 'twigz/onramp-rn-bridge' of https://github.com/stripe/st…
Twigz Aug 28, 2025
5133bfd
Uses appropriate emitter on iOS for checkout
mliberatore Aug 28, 2025
5f78069
Gets Check Out working in example; removes duplicate Authorize UI
mliberatore Aug 28, 2025
fbc9da3
Change emitting to use existing invocation
Twigz Aug 28, 2025
b5e38e9
Adds `StripeProvider` with publishableKey and merchantIdentifier for …
mliberatore Aug 28, 2025
5dd3e5a
Merge branch 'twigz/onramp-rn-bridge' of https://github.com/stripe/st…
mliberatore Aug 28, 2025
0b3c3ac
Silences warning in unimplemented API on iOS
mliberatore Aug 28, 2025
c492019
move functions to useOnramp() hook
lng-stripe Aug 28, 2025
9f703cd
refactor: move LinkUserInfo type to Onramp.ts and update imports
lng-stripe Aug 29, 2025
618e659
refactor: consolidate CryptoNetwork and KycInfo types in Onramp.ts
lng-stripe Aug 29, 2025
82db96e
rm idtype and kycinfo fields
lng-stripe Aug 29, 2025
58970cc
rm "onramp" from useOnramp() functions
lng-stripe Aug 29, 2025
fab4192
add OnrampConfiguration; cleanup defaults
lng-stripe Aug 29, 2025
cdadf9c
Switch iOS impl to use resolver instead of rejector in error cases
mats-stripe Aug 29, 2025
8cfbab9
Update example app to use new error handling pattern
mats-stripe Aug 29, 2025
23d1aac
inline for simplicity
lng-stripe Aug 29, 2025
b039846
update types
lng-stripe Aug 29, 2025
40ec1d5
fix codegen
lng-stripe Aug 29, 2025
fab6079
Use VoidResult type for remaining APIs on iOS
mats-stripe Aug 29, 2025
6e05bc6
update configureOnramp()
lng-stripe Aug 29, 2025
496baa1
update hasLinkAccount
lng-stripe Aug 29, 2025
872f13c
fix registerWalletAddress and registerLinkUser
lng-stripe Aug 29, 2025
b9f882f
fix rest of Android Onramp; update AuthorizeResult
lng-stripe Aug 29, 2025
cd51e12
Fix AuthorizeResult shape on iOS impl
mats-stripe Aug 29, 2025
cf32fee
fix handleOnrampAuthenticationResult
lng-stripe Aug 29, 2025
b65f09c
alert configuration success
lng-stripe Aug 29, 2025
117c0b9
set version
lng-stripe Aug 29, 2025
9e520de
improve demo UI
lng-stripe Aug 29, 2025
d2f1ee8
defaults
lng-stripe Aug 29, 2025
f13e645
more UI cleanup
lng-stripe Aug 29, 2025
f044a8f
Makes appearance specification more permissive on iOS in the case of …
mliberatore Sep 2, 2025
626ef85
[onramp][private-beta] Conditionally include Onramp; fixes & improvem…
lng-stripe Sep 8, 2025
c46aeef
logOut Android binding (#2098)
lng-stripe Sep 8, 2025
2b9051c
Merge remote-tracking branch 'origin/master' into beta/crypto-onramp
carlosmuvi-stripe Sep 8, 2025
1ca77a1
add update phone number example UX (#2100)
lng-stripe Sep 8, 2025
eb6912f
[Onramp] Bumps native versions (#2101)
carlosmuvi-stripe Sep 9, 2025
194c847
[Onramp] Implements Remaining Bindings for StripeCryptoOnramp on iOS …
mliberatore Sep 9, 2025
88a1ff4
fix: add missing await to NativeStripeSdk.initialise calls (#2113) (#…
lng-stripe Sep 11, 2025
feb04b4
Crypto Onramp Example Cleanup (#2106)
Twigz Sep 11, 2025
e718aca
Crypto Onramp Example Refactoring (#2126)
Twigz Sep 16, 2025
130ac95
[onramp] Configure with crypto customer ID (#2138)
lng-stripe Sep 22, 2025
ffde7d6
Crypto Onramp Payment Display Data (#2132)
Twigz Sep 22, 2025
7da784d
Revert "Use files instead of npmignore to cleanup npm package (#2081)…
porter-stripe Sep 8, 2025
b4aaa5d
Update package.json (#2105)
porter-stripe Sep 9, 2025
f905dad
Bump version number to 0.52.0-crypto-onramp-2-private-beta
gbirch-stripe Sep 22, 2025
4848f86
fix current version
lng-stripe Sep 23, 2025
96a771e
bump 0.52.0-crypto-onramp-2-private-beta.1
lng-stripe Sep 23, 2025
a588e9d
Update NativeOnrampSdkModuleSpec.java (#2141)
Twigz Sep 23, 2025
dd847e3
bump 0.52.0-crypto-onramp-2-private-beta.2
lng-stripe Sep 23, 2025
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
24 changes: 24 additions & 0 deletions .npmignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
example/
e2e-tests/
docs/
scripts/
.tmp/
.github/
lib/typescript/example/
**/__tests__
**/__fixtures__
**/__mocks__

android/src/androidTest/
android/src/test/
android/build/
android/bin/

ios/Tests/

yarn-error.log
CODEOWNERS
CONTRIBUTING.md
babel.config.js
tsconfig.json
yarn.lock
14 changes: 14 additions & 0 deletions android/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,11 @@ def isNewArchitectureEnabled() {
return project.hasProperty("newArchEnabled") && project.newArchEnabled == "true"
}

def isOnrampIncluded() {
return rootProject.ext.has("StripeSdk_includeOnramp") &&
rootProject.ext.StripeSdk_includeOnramp.toString().toLowerCase() == "true"
}

def reactNativeArchitectures() {
def value = project.getProperties().get("reactNativeArchitectures")
return value ? value.split(",") : [
Expand Down Expand Up @@ -98,6 +103,7 @@ android {
testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
consumerProguardFiles 'proguard-rules.txt'
buildConfigField "boolean", "IS_NEW_ARCHITECTURE_ENABLED", isNewArchitectureEnabled().toString()
buildConfigField "boolean", "IS_ONRAMP_INCLUDED", isOnrampIncluded().toString()

ndk {
abiFilters(*reactNativeArchitectures())
Expand Down Expand Up @@ -129,6 +135,9 @@ android {
if (!isNewArchitectureEnabled()) {
srcDirs += ["src/oldarch/java"]
}
if (isOnrampIncluded()) {
srcDirs += ["src/onramp/java"]
}
}
}
}
Expand Down Expand Up @@ -214,6 +223,11 @@ dependencies {
implementation("com.stripe:stripe-android:$stripe_version") {
exclude group: 'androidx.emoji2', module: 'emoji2'
}
if (isOnrampIncluded()) {
implementation("com.stripe:crypto-onramp:$stripe_version") {
exclude group: 'androidx.emoji2', module: 'emoji2'
}
}
implementation("com.stripe:financial-connections:$stripe_version") {
exclude group: 'androidx.emoji2', module: 'emoji2'
}
Expand Down
2 changes: 1 addition & 1 deletion android/gradle.properties
Original file line number Diff line number Diff line change
Expand Up @@ -3,4 +3,4 @@ StripeSdk_compileSdkVersion=30
StripeSdk_targetSdkVersion=28
StripeSdk_minSdkVersion=21
# Keep StripeSdk_stripeVersion in sync with https://github.com/stripe/stripe-identity-react-native/blob/main/android/gradle.properties
StripeSdk_stripeVersion=21.23.+
StripeSdk_stripeVersion=21.27.0
Original file line number Diff line number Diff line change
@@ -0,0 +1,138 @@
package com.reactnativestripesdk

import com.facebook.react.bridge.Promise
import com.facebook.react.bridge.ReactApplicationContext
import com.facebook.react.bridge.ReactMethod
import com.facebook.react.bridge.ReadableMap
import com.facebook.react.module.annotations.ReactModule
import com.reactnativestripesdk.utils.createFailedError

@ReactModule(name = NativeOnrampSdkModuleSpec.NAME)
class FakeOnrampSdkModule(
reactContext: ReactApplicationContext,
) : NativeOnrampSdkModuleSpec(reactContext) {
@ReactMethod
override fun initialise(
params: ReadableMap?,
promise: Promise?,
) {
promise?.resolve(null)
}

@ReactMethod
override fun configureOnramp(
config: ReadableMap?,
promise: Promise?,
) {
promise?.resolveNotImplemented()
}

@ReactMethod
override fun hasLinkAccount(
email: String?,
promise: Promise?,
) {
promise?.resolveNotImplemented()
}

@ReactMethod
override fun registerLinkUser(
info: ReadableMap?,
promise: Promise?,
) {
promise?.resolveNotImplemented()
}

@ReactMethod
override fun registerWalletAddress(
walletAddress: String?,
network: String?,
promise: Promise?,
) {
promise?.resolveNotImplemented()
}

@ReactMethod
override fun attachKycInfo(
kycInfo: ReadableMap?,
promise: Promise?,
) {
promise?.resolveNotImplemented()
}

@ReactMethod
override fun updatePhoneNumber(
phone: String?,
promise: Promise?,
) {
promise?.resolveNotImplemented()
}

@ReactMethod
override fun authenticateUser(promise: Promise?) {
promise?.resolveNotImplemented()
}

@ReactMethod
override fun verifyIdentity(promise: Promise?) {
promise?.resolveNotImplemented()
}

@ReactMethod
override fun collectPaymentMethod(
paymentMethod: String?,
platformPayParams: ReadableMap?,
promise: Promise?,
) {
promise?.resolveNotImplemented()
}

@ReactMethod
override fun provideCheckoutClientSecret(clientSecret: String?) {
// No-op
}

@ReactMethod
override fun createCryptoPaymentToken(promise: Promise?) {
promise?.resolveNotImplemented()
}

@ReactMethod
override fun performCheckout(
onrampSessionId: String?,
promise: Promise?,
) {
promise?.resolveNotImplemented()
}

@ReactMethod
override fun onrampAuthorize(
linkAuthIntentId: String?,
promise: Promise?,
) {
promise?.resolveNotImplemented()
}

@ReactMethod
override fun logout(promise: Promise?) {
promise?.resolveNotImplemented()
}

@ReactMethod
override fun getCryptoTokenDisplayData(
token: ReadableMap,
promise: Promise,
) {
promise?.resolveNotImplemented()
}

private fun Promise.resolveNotImplemented() {
this.resolve(
createFailedError(
NotImplementedError(
"To enable Onramp, add 'StripeSdk_includeOnramp=true' to gradle.properties.",
),
),
)
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -381,6 +381,7 @@ class PaymentLauncherFragment : StripeFragment() {
StripeIntent.NextActionType.DisplayOxxoDetails,
StripeIntent.NextActionType.DisplayBoletoDetails,
StripeIntent.NextActionType.DisplayKonbiniDetails,
StripeIntent.NextActionType.DisplayPayNowDetails,
StripeIntent.NextActionType.VerifyWithMicrodeposits,
StripeIntent.NextActionType.DisplayMultibancoDetails,
-> true
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -71,6 +71,7 @@ import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.launch
import org.json.JSONObject

@SuppressLint("RestrictedApi")
@ReactModule(name = StripeSdkModule.NAME)
class StripeSdkModule(
reactContext: ReactApplicationContext,
Expand Down Expand Up @@ -242,7 +243,10 @@ class StripeSdkModule(
val customPaymentMethodConfig = params.getMap("customPaymentMethodConfiguration")
if (customPaymentMethodConfig != null) {
// Store the original ReadableMap for custom payment methods
bundle.putSerializable("customPaymentMethodConfigurationReadableMap", customPaymentMethodConfig.toHashMap())
bundle.putSerializable(
"customPaymentMethodConfigurationReadableMap",
customPaymentMethodConfig.toHashMap(),
)
}

paymentSheetFragment =
Expand Down Expand Up @@ -1405,11 +1409,14 @@ class StripeSdkModule(

private fun setupComposeCompatView() {
UiThreadUtil.runOnUiThread {
composeCompatView = composeCompatView ?: StripeAbstractComposeView.CompatView(context = reactApplicationContext).also {
currentActivity?.findViewById<ViewGroup>(android.R.id.content)?.addView(
it,
)
}
composeCompatView =
composeCompatView ?: StripeAbstractComposeView
.CompatView(context = reactApplicationContext)
.also {
currentActivity?.findViewById<ViewGroup>(android.R.id.content)?.addView(
it,
)
}
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -19,11 +19,20 @@ class StripeSdkPackage : BaseReactPackage() {
): NativeModule? =
when (name) {
StripeSdkModule.NAME -> StripeSdkModule(reactContext)
NativeOnrampSdkModuleSpec.NAME -> {
val onrampModuleClass = getOnrampModuleClass()
val constructor = onrampModuleClass.getConstructor(ReactApplicationContext::class.java)
constructor.newInstance(reactContext) as NativeModule
}
else -> null
}

override fun getReactModuleInfoProvider(): ReactModuleInfoProvider {
val moduleList: Array<Class<out NativeModule?>> = arrayOf(StripeSdkModule::class.java)
val moduleList: Array<Class<out NativeModule?>> =
arrayOf(
StripeSdkModule::class.java,
getOnrampModuleClass(),
)
val reactModuleInfoMap: MutableMap<String, ReactModuleInfo> = HashMap()
for (moduleClass in moduleList) {
val reactModule = moduleClass.getAnnotation(ReactModule::class.java) ?: continue
Expand Down Expand Up @@ -51,4 +60,13 @@ class StripeSdkPackage : BaseReactPackage() {
AddressSheetViewManager(),
EmbeddedPaymentElementViewManager(),
)

private fun getOnrampModuleClass(): Class<out NativeModule?> {
if (BuildConfig.IS_ONRAMP_INCLUDED) {
@Suppress("UNCHECKED_CAST")
return Class.forName("com.reactnativestripesdk.OnrampSdkModule") as Class<out NativeModule?>
} else {
return FakeOnrampSdkModule::class.java
}
}
}
10 changes: 10 additions & 0 deletions android/src/main/java/com/reactnativestripesdk/utils/Errors.kt
Original file line number Diff line number Diff line change
Expand Up @@ -178,8 +178,18 @@ internal fun createError(
return mapError(code, error.message, error.localizedMessage, null, null, null)
}

internal fun createCanceledError(message: String? = null): WritableMap = createError(ErrorType.Canceled.toString(), message)

internal fun createFailedError(error: Throwable): WritableMap = createError(ErrorType.Failed.toString(), error)

internal fun createMissingInitError(): WritableMap =
createError(
ErrorType.Failed.toString(),
"Stripe has not been initialized. Initialize Stripe in your app with the StripeProvider component or the initStripe method.",
)

internal fun createOnrampNotConfiguredError(): WritableMap =
createError(
ErrorType.Failed.toString(),
"Onramp is not configured.",
)
14 changes: 12 additions & 2 deletions android/src/main/java/com/reactnativestripesdk/utils/Mappers.kt
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,8 @@ import com.stripe.android.model.Token
import com.stripe.android.paymentelement.ExperimentalCustomPaymentMethodsApi
import com.stripe.android.paymentsheet.PaymentSheet

internal fun createEmptyResult(): WritableMap = WritableNativeMap()

internal fun createResult(
key: String,
value: WritableMap,
Expand Down Expand Up @@ -586,6 +588,12 @@ internal fun mapNextAction(
nextActionMap.putString("voucherURL", it.hostedVoucherUrl)
}
}
NextActionType.DisplayPayNowDetails -> {
(data as? NextActionData.DisplayPayNowDetails)?.let {
nextActionMap.putString("type", "paynow")
nextActionMap.putString("qrCodeUrl", it.qrCodeUrl)
}
}
}
return nextActionMap
}
Expand Down Expand Up @@ -1073,7 +1081,8 @@ internal fun parseCustomPaymentMethods(customPaymentMethodConfig: Bundle?): List
return emptyList()
}

val configHashMap = customPaymentMethodConfig.getSerializable("customPaymentMethodConfigurationReadableMap") as? HashMap<String, Any>
val configHashMap =
customPaymentMethodConfig.getSerializable("customPaymentMethodConfigurationReadableMap") as? HashMap<String, Any>
if (configHashMap != null) {
val customPaymentMethods = configHashMap["customPaymentMethods"] as? List<HashMap<String, Any>>
if (customPaymentMethods != null) {
Expand All @@ -1083,7 +1092,8 @@ internal fun parseCustomPaymentMethods(customPaymentMethodConfig: Bundle?): List
val id = customPaymentMethodMap["id"] as? String
if (id != null) {
val subtitle = customPaymentMethodMap["subtitle"] as? String
val disableBillingDetailCollection = customPaymentMethodMap["disableBillingDetailCollection"] as? Boolean ?: false
val disableBillingDetailCollection =
customPaymentMethodMap["disableBillingDetailCollection"] as? Boolean ?: false
result.add(
PaymentSheet.CustomPaymentMethod(
id = id,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,18 @@ public void setProperty(T view, String propName, @Nullable Object value) {
case "borderRadius":
mViewManager.setBorderRadius(view, value == null ? 4 : ((Double) value).intValue());
break;
case "hasShippingMethodCallback":
mViewManager.setHasShippingMethodCallback(view, value == null ? false : (boolean) value);
break;
case "hasShippingContactCallback":
mViewManager.setHasShippingContactCallback(view, value == null ? false : (boolean) value);
break;
case "hasCouponCodeCallback":
mViewManager.setHasCouponCodeCallback(view, value == null ? false : (boolean) value);
break;
case "hasOrderTrackingCallback":
mViewManager.setHasOrderTrackingCallback(view, value == null ? false : (boolean) value);
break;
default:
super.setProperty(view, propName, value);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,4 +16,8 @@ public interface ApplePayButtonManagerInterface<T extends View> {
void setType(T view, int value);
void setButtonStyle(T view, int value);
void setBorderRadius(T view, int value);
void setHasShippingMethodCallback(T view, boolean value);
void setHasShippingContactCallback(T view, boolean value);
void setHasCouponCodeCallback(T view, boolean value);
void setHasOrderTrackingCallback(T view, boolean value);
}
Loading