Skip to content
Merged
Show file tree
Hide file tree
Changes from 4 commits
Commits
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
33 changes: 20 additions & 13 deletions android/build.gradle
Original file line number Diff line number Diff line change
@@ -1,24 +1,20 @@
buildscript {
// Buildscript is evaluated before everything else so we can't use getExtOrDefault
def kotlin_version = rootProject.ext.has("kotlinVersion") ? rootProject.ext.get("kotlinVersion") : project.properties["RNIterable_kotlinVersion"]
ext.getExtOrDefault = {name ->
return rootProject.ext.has(name) ? rootProject.ext.get(name) : project.properties['RNIterable_' + name]

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What is this line doing? Getting the project name from new arch vs. old arch?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No -- it's either getting the value of a parameter in the users app or, if it doesn't exist, getting the value in our sdk

}

repositories {
google()
mavenCentral()
}

dependencies {
classpath "com.android.tools.build:gradle:7.2.1"
classpath "com.android.tools.build:gradle:8.7.2"
// noinspection DifferentKotlinGradleVersion
classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlin_version"
classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:${getExtOrDefault('kotlinVersion')}"
}
}

def reactNativeArchitectures() {
def value = rootProject.getProperties().get("reactNativeArchitectures")
return value ? value.split(",") : ["armeabi-v7a", "x86", "x86_64", "arm64-v8a"]
}

def isNewArchitectureEnabled() {
return rootProject.hasProperty("newArchEnabled") && rootProject.getProperty("newArchEnabled") == "true"
}
Expand Down Expand Up @@ -63,7 +59,11 @@ android {
defaultConfig {
minSdkVersion getExtOrIntegerDefault("minSdkVersion")
targetSdkVersion getExtOrIntegerDefault("targetSdkVersion")
buildConfigField("boolean", "IS_NEW_ARCHITECTURE_ENABLED", isNewArchitectureEnabled().toString())
}

buildFeatures {
buildConfig true
}

buildTypes {
Expand All @@ -80,6 +80,16 @@ android {
sourceCompatibility JavaVersion.VERSION_1_8
targetCompatibility JavaVersion.VERSION_1_8
}

sourceSets {
main {
if (isNewArchitectureEnabled()) {
java.srcDirs += ['src/newarch']
} else {
java.srcDirs += ['src/oldarch']
}
}
}
}

repositories {
Expand All @@ -90,10 +100,7 @@ repositories {
def kotlin_version = getExtOrDefault("kotlinVersion")

dependencies {
// For < 0.71, this will be from the local maven repo
// For > 0.71, this will be replaced by `com.facebook.react:react-android:$version` by react gradle plugin
//noinspection GradleDynamicVersion
implementation "com.facebook.react:react-native:+"
implementation "com.facebook.react:react-android"
implementation "org.jetbrains.kotlin:kotlin-stdlib:$kotlin_version"
api "com.iterable:iterableapi:3.5.2"
// api project(":iterableapi") // links to local android SDK repo rather than by release
Expand Down
12 changes: 6 additions & 6 deletions android/gradle.properties
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
RNIterable_kotlinVersion=1.7.0
RNIterable_minSdkVersion=21
RNIterable_targetSdkVersion=31
RNIterable_compileSdkVersion=31
RNIterable_ndkversion=21.4.7075529
RNIterable_kotlinVersion=2.0.21
RNIterable_minSdkVersion=24
RNIterable_targetSdkVersion=35
RNIterable_compileSdkVersion=35
RNIterable_ndkversion=27.1.12297006
android.useAndroidX=true
android.enableJetifier=true
android.enableJetifier=true
Original file line number Diff line number Diff line change
Expand Up @@ -3,27 +3,47 @@
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import com.facebook.react.ReactPackage;
import androidx.annotation.Nullable;
import com.facebook.react.bridge.NativeModule;
import com.facebook.react.bridge.ReactApplicationContext;
import com.facebook.react.module.model.ReactModuleInfo;
import com.facebook.react.module.model.ReactModuleInfoProvider;
import com.facebook.react.TurboReactPackage;
import com.facebook.react.uimanager.ViewManager;
import com.facebook.react.bridge.JavaScriptModule;

public class RNIterableAPIPackage implements ReactPackage {
@Override
public List<NativeModule> createNativeModules(
ReactApplicationContext reactContext) {
List<NativeModule> modules = new ArrayList<>();

modules.add(new RNIterableAPIModule(reactContext));

return modules;
public class RNIterableAPIPackage extends TurboReactPackage {
@Nullable
@Override
public NativeModule getModule(String name, ReactApplicationContext reactContext) {
if (name.equals(RNIterableAPIModuleImpl.NAME)) {
return new RNIterableAPIModule(reactContext);
} else {
return null;
}
}

@Override
public List<ViewManager> createViewManagers(ReactApplicationContext reactContext) {
return Collections.emptyList();
public ReactModuleInfoProvider getReactModuleInfoProvider() {
return () -> {
final Map<String, ReactModuleInfo> moduleInfos = new HashMap<>();
boolean isTurboModule = BuildConfig.IS_NEW_ARCHITECTURE_ENABLED;
moduleInfos.put(
RNIterableAPIModuleImpl.NAME,
new ReactModuleInfo(
RNIterableAPIModuleImpl.NAME,
RNIterableAPIModuleImpl.NAME,
false, // canOverrideExistingModule
false, // needsEagerInit
true, // hasConstants
false, // isCxxModule
isTurboModule // isTurboModule
));
return moduleInfos;
};
}
}
236 changes: 236 additions & 0 deletions android/src/newarch/java/com/reactnative/RNIterableAPIModule.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,236 @@
package com.iterable.reactnative;

Copilot AI Aug 21, 2025

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The package declaration does not match the file path. The file is in com/reactnative/ directory but declares package com.iterable.reactnative. This will cause compilation errors.

Suggested change
package com.iterable.reactnative;
package com.reactnative;

Copilot uses AI. Check for mistakes.

import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import com.facebook.react.bridge.Callback;
import com.facebook.react.bridge.NativeModule;
import com.facebook.react.bridge.Promise;
import com.facebook.react.bridge.ReactApplicationContext;
import com.facebook.react.bridge.ReactContext;
import com.facebook.react.bridge.ReactContextBaseJavaModule;
import com.facebook.react.bridge.ReactMethod;
import com.facebook.react.bridge.ReadableArray;
import com.facebook.react.bridge.ReadableMap;
import java.util.Map;
import java.util.HashMap;

public class RNIterableAPIModule extends NativeRNIterableAPISpec {
private final ReactApplicationContext reactContext;
private static RNIterableAPIModuleImpl moduleImpl;

RNIterableAPIModule(ReactApplicationContext context) {
super(context);
this.reactContext = context;
if (moduleImpl == null) {
moduleImpl = new RNIterableAPIModuleImpl(reactContext);
}
}

@Override
@NonNull
public String getName() {
return RNIterableAPIModuleImpl.NAME;
}

@Override
public void initializeWithApiKey(String apiKey, ReadableMap configReadableMap, String version, Promise promise) {

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Function with many parameters (count = 4): initializeWithApiKey [qlty:function-parameters]

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Function with many parameters (count = 4): initializeWithApiKey [qlty:function-parameters]

moduleImpl.initializeWithApiKey(apiKey, configReadableMap, version, promise);
}

@Override
public void initialize2WithApiKey(String apiKey, ReadableMap configReadableMap, String apiEndPointOverride, String version, Promise promise) {

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Function with many parameters (count = 5): initialize2WithApiKey [qlty:function-parameters]

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Function with many parameters (count = 5): initialize2WithApiKey [qlty:function-parameters]

moduleImpl.initialize2WithApiKey(apiKey, configReadableMap, apiEndPointOverride, version, promise);
}

@Override
public void setEmail(@Nullable String email, @Nullable String authToken) {
moduleImpl.setEmail(email, authToken);
}

@Override
public void updateEmail(String email, @Nullable String authToken) {
moduleImpl.updateEmail(email, authToken);
}

@Override
public void getEmail(Promise promise) {
moduleImpl.getEmail(promise);
}

public void sampleMethod(String stringArgument, int numberArgument, Callback callback) {
moduleImpl.sampleMethod(stringArgument, numberArgument, callback);
}

Copilot AI Aug 21, 2025

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The sampleMethod appears to be leftover test/example code and should be removed from production code as it doesn't match the other API methods.

Suggested change
}

Copilot uses AI. Check for mistakes.

@Override
public void setUserId(@Nullable String userId, @Nullable String authToken) {
moduleImpl.setUserId(userId, authToken);
}

@Override
public void updateUser(ReadableMap dataFields, boolean mergeNestedObjects) {
moduleImpl.updateUser(dataFields, mergeNestedObjects);
}

@Override
public void getUserId(Promise promise) {
moduleImpl.getUserId(promise);
}

@Override
public void trackEvent(String name, ReadableMap dataFields) {
moduleImpl.trackEvent(name, dataFields);
}

@Override
public void updateCart(ReadableArray items) {
moduleImpl.updateCart(items);
}

@Override
public void trackPurchase(double total, ReadableArray items, ReadableMap dataFields) {
moduleImpl.trackPurchase(total, items, dataFields);
}

@Override
public void trackPushOpenWithCampaignId(double campaignId, Double templateId, String messageId, boolean appAlreadyRunning, ReadableMap dataFields) {

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Function with many parameters (count = 5): trackPushOpenWithCampaignId [qlty:function-parameters]

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Function with many parameters (count = 5): trackPushOpenWithCampaignId [qlty:function-parameters]

moduleImpl.trackPushOpenWithCampaignId(campaignId, templateId, messageId, appAlreadyRunning, dataFields);
}

@Override
public void updateSubscriptions(ReadableArray emailListIds, ReadableArray unsubscribedChannelIds, ReadableArray unsubscribedMessageTypeIds, ReadableArray subscribedMessageTypeIds, double campaignId, double templateId) {

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Function with many parameters (count = 6): updateSubscriptions [qlty:function-parameters]

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Function with many parameters (count = 6): updateSubscriptions [qlty:function-parameters]

moduleImpl.updateSubscriptions(emailListIds, unsubscribedChannelIds, unsubscribedMessageTypeIds, subscribedMessageTypeIds, campaignId, templateId);
}

@Override
public void showMessage(String messageId, boolean consume, final Promise promise) {
moduleImpl.showMessage(messageId, consume, promise);
}

@Override
public void setReadForMessage(String messageId, boolean read) {
moduleImpl.setReadForMessage(messageId, read);
}

@Override
public void removeMessage(String messageId, double location, double deleteSource) {
moduleImpl.removeMessage(messageId, location, deleteSource);
}

@Override
public void getHtmlInAppContentForMessage(String messageId, final Promise promise) {
moduleImpl.getHtmlInAppContentForMessage(messageId, promise);
}

@Override
public void getAttributionInfo(Promise promise) {
moduleImpl.getAttributionInfo(promise);
}

@Override
public void setAttributionInfo(ReadableMap attributionInfoReadableMap) {
moduleImpl.setAttributionInfo(attributionInfoReadableMap);
}

@Override
public void getLastPushPayload(Promise promise) {
moduleImpl.getLastPushPayload(promise);
}

@Override
public void disableDeviceForCurrentUser() {
moduleImpl.disableDeviceForCurrentUser();
}

@Override
public void handleAppLink(String uri, Promise promise) {
moduleImpl.handleAppLink(uri, promise);
}

@Override
public void trackInAppOpen(String messageId, double location) {
moduleImpl.trackInAppOpen(messageId, location);
}

@Override
public void trackInAppClick(String messageId, double location, String clickedUrl) {
moduleImpl.trackInAppClick(messageId, location, clickedUrl);
}

@Override
public void trackInAppClose(String messageId, double location, double source, @Nullable String clickedUrl) {

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Function with many parameters (count = 4): trackInAppClose [qlty:function-parameters]

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Function with many parameters (count = 4): trackInAppClose [qlty:function-parameters]

moduleImpl.trackInAppClose(messageId, location, source, clickedUrl);
}

@Override
public void inAppConsume(String messageId, double location, double source) {
moduleImpl.inAppConsume(messageId, location, source);
}

@Override
public void getInAppMessages(Promise promise) {
moduleImpl.getInAppMessages(promise);
}

@Override
public void getInboxMessages(Promise promise) {
moduleImpl.getInboxMessages(promise);
}

@Override
public void getUnreadInboxMessagesCount(Promise promise) {
moduleImpl.getUnreadInboxMessagesCount(promise);
}

@Override
public void setInAppShowResponse(double number) {
moduleImpl.setInAppShowResponse(number);
}

@Override
public void setAutoDisplayPaused(final boolean paused) {
moduleImpl.setAutoDisplayPaused(paused);
}

@Override
public void wakeApp() {
moduleImpl.wakeApp();
}

@Override
public void startSession(ReadableArray visibleRows) {
moduleImpl.startSession(visibleRows);
}

@Override
public void endSession() {
moduleImpl.endSession();
}

@Override
public void updateVisibleRows(ReadableArray visibleRows) {
moduleImpl.updateVisibleRows(visibleRows);
}

@Override
public void addListener(String eventName) {
moduleImpl.addListener(eventName);
}

@Override
public void removeListeners(double count) {
moduleImpl.removeListeners(count);
}

@Override
public void passAlongAuthToken(String authToken) {
moduleImpl.passAlongAuthToken(authToken);
}

public void sendEvent(@NonNull String eventName, @Nullable Object eventData) {
moduleImpl.sendEvent(eventName, eventData);
}

public void onInboxUpdated() {
moduleImpl.onInboxUpdated();
}
}