Skip to content

Conversation

lposen
Copy link
Contributor

@lposen lposen commented Sep 30, 2025

🔹 JIRA Ticket(s) if any

✏️ Description

Please provide a brief description of what this pull request does.

lposen and others added 30 commits August 1, 2025 14:05
…ew-arch/MOB-11828-add-backwards-compatibility
…ew-arch/MOB-11828-add-backwards-compatibility
…d-api-and-codegen

[MOB-11826] make-frontend-api-and-codegen
…ew-arch/MOB-11828-add-backwards-compatibility
…ew-arch/MOB-11828-add-backwards-compatibility
…s-compatibility

[MOB-11828] add-backwards-compatibility
Added copilot suggestion

Co-authored-by: Copilot <[email protected]>
…itecture-support

[MOB-11827] add-new-architecture-support
lposen and others added 22 commits August 28, 2025 19:36
…erableapimodule-so-that-its-major-func

[MOB-11954] restructure RNIterableAPIModule to delegate functionality to RNIterableAPIModuleImpl
…encies-correctly

[MOB-11994] align-dependencies-correctly
…w-architecture

[MOB-11955] configure-new-architecture
…when-clicking-track-push-open-with-ca

[MOB-11957] ios-crashes-when-clicking-track-push-open-with-ca
@lposen lposen requested a review from Copilot September 30, 2025 02:13
Copy link

@Copilot Copilot AI left a comment

Choose a reason for hiding this comment

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

Pull Request Overview

This PR implements React Native New Architecture support for the Iterable SDK, transitioning from legacy architecture to support both new TurboModules/Fabric and legacy patterns. Key changes include adding TurboModule specifications, updating native bridge implementations, and adjusting type signatures for compatibility.

Key Changes:

  • Added New Architecture support with TurboModule specifications and dual architecture compatibility
  • Refactored native iOS/Android bridge implementations to support both legacy and new architectures
  • Updated type signatures throughout codebase to use more precise null-safe types (string | null vs string | undefined)

Reviewed Changes

Copilot reviewed 37 out of 38 changed files in this pull request and generated 6 comments.

Show a summary per file
File Description
src/api/NativeRNIterableAPI.ts New TurboModule specification interface for New Architecture
src/api/index.ts Bridge module that exports either TurboModule or legacy NativeModule
ios/RNIterableAPI/ReactIterableAPI.swift Refactored Swift implementation to support both architectures
ios/RNIterableAPI/RNIterableAPI.mm Updated Objective-C bridge with dual architecture support
android/src/newarch/java/com/RNIterableAPIModule.java New Architecture Android implementation
android/src/oldarch/java/com/RNIterableAPIModule.java Legacy Architecture Android implementation
src/core/classes/Iterable.ts Updated type signatures for null-safe parameters
package.json Updated dependencies and build configuration for New Architecture

Tip: Customize your code reviews with copilot-instructions.md. Create the file or learn how to get started.

Comment on lines +367 to 370
if (messageId != null) {
IterableLogger.v(TAG, "inAppConsume");
IterableApi.getInstance().inAppConsume(RNIterableInternal.getMessageById(messageId), Serialization.getIterableDeleteActionTypeFromInteger((int) source), Serialization.getIterableInAppLocationFromInteger((int) location));
}
Copy link
Preview

Copilot AI Sep 30, 2025

Choose a reason for hiding this comment

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

The logic has been inverted from the original version (was if (messageId == null) { return; }). This change puts all the logic inside the if block, which increases nesting. Consider reverting to early return pattern for better readability: if (messageId == null) { return; }

Suggested change
if (messageId != null) {
IterableLogger.v(TAG, "inAppConsume");
IterableApi.getInstance().inAppConsume(RNIterableInternal.getMessageById(messageId), Serialization.getIterableDeleteActionTypeFromInteger((int) source), Serialization.getIterableInAppLocationFromInteger((int) location));
}
if (messageId == null) {
return;
}
IterableLogger.v(TAG, "inAppConsume");
IterableApi.getInstance().inAppConsume(
RNIterableInternal.getMessageById(messageId),
Serialization.getIterableDeleteActionTypeFromInteger((int) source),
Serialization.getIterableInAppLocationFromInteger((int) location)
);

Copilot uses AI. Check for mistakes.

return
}
delegate?.sendEvent(
withName: EventName.receivedIterableInboxChanged.rawValue, body: nil as Any?)
Copy link
Preview

Copilot AI Sep 30, 2025

Choose a reason for hiding this comment

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

The explicit cast nil as Any? is unnecessary in Swift. Simply using nil would be sufficient as the parameter is already typed as Any?. This makes the code cleaner and more idiomatic.

Suggested change
withName: EventName.receivedIterableInboxChanged.rawValue, body: nil as Any?)
withName: EventName.receivedIterableInboxChanged.rawValue, body: nil)

Copilot uses AI. Check for mistakes.

Copy link

github-actions bot commented Sep 30, 2025

Lines Statements Branches Functions
Coverage: 38%
38.51% (181/470) 13.97% (26/186) 33.33% (52/156)

Copy link

qltysh bot commented Sep 30, 2025

Diff Coverage: The code coverage on the diff in this pull request is 64.3%.

Total Coverage: This PR will decrease coverage by 0.13%.

File Coverage Changes
Path File Coverage Δ Indirect
src/api/NativeRNIterableAPI.ts 100.0
src/api/index.ts 100.0
src/core/classes/Iterable.ts -0.2
src/inApp/classes/IterableInAppManager.ts -1.9
src/inbox/classes/IterableInboxDataModel.ts -2.2
src/inbox/components/IterableInbox.tsx -1.2
🛟 Help
  • Diff Coverage: Coverage for added or modified lines of code (excludes deleted files). Learn more.

  • Total Coverage: Coverage for the whole repository, calculated as the sum of all File Coverage. Learn more.

  • File Coverage: Covered Lines divided by Covered Lines plus Missed Lines. (Excludes non-executable lines including blank lines and comments.)

    • Indirect Changes: Changes to File Coverage for files that were not modified in this PR. Learn more.

This is from Qlty Cloud, the successor to Code Climate Quality. Learn more.

Copy link

qltysh bot commented Sep 30, 2025

❌ 2 blocking issues (20 total)

Tool Category Rule Count
eslint Lint Error loading TSDoc config file:
Error encountered for /home/runner/work/react-native-sdk/tsdoc.json:
Unable to resolve "extends" reference to "typedoc/tsdoc.json": Cannot find module 'typedoc/tsdoc.json' from '/home/runner/work/react-native-sdk'
2
qlty Structure Function with high complexity (count = 5): initializeWithApiKey 2
qlty Structure Function with many parameters (count = 4): initializeWithApiKey 16

This is from Qlty Cloud, the successor to Code Climate Quality. Learn more.

@ReactMethod
public void trackPushOpenWithCampaignId(Integer campaignId, Integer templateId, String messageId, Boolean appAlreadyRunning, ReadableMap dataFields) {
RNIterableInternal.trackPushOpenWithCampaignId(campaignId, templateId, messageId, optSerializedDataFields(dataFields));
public void trackPushOpenWithCampaignId(double campaignId, @Nullable Double templateId, String messageId, boolean appAlreadyRunning, @Nullable ReadableMap dataFields) {
Copy link

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]


@ReactMethod
public void updateSubscriptions(ReadableArray emailListIds, ReadableArray unsubscribedChannelIds, ReadableArray unsubscribedMessageTypeIds, ReadableArray subscribedMessageTypeIds, Integer campaignId, Integer templateId) {
public void updateSubscriptions(@Nullable ReadableArray emailListIds, @Nullable ReadableArray unsubscribedChannelIds, @Nullable ReadableArray unsubscribedMessageTypeIds, @Nullable ReadableArray subscribedMessageTypeIds, double campaignId, double templateId) {
Copy link

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]


@ReactMethod
public void trackInAppClose(String messageId, Integer location, Integer source, @Nullable String clickedUrl) {
public void trackInAppClose(String messageId, double location, double source, @Nullable String clickedUrl) {
Copy link

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]

}

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

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]

}

@ReactMethod
public void updateSubscriptions(@Nullable ReadableArray emailListIds, @Nullable ReadableArray unsubscribedChannelIds, @Nullable ReadableArray unsubscribedMessageTypeIds, @Nullable ReadableArray subscribedMessageTypeIds, double campaignId, double templateId) {
Copy link

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]

}

@ReactMethod
public void trackInAppClose(String messageId, double location, double source, @Nullable String clickedUrl) {
Copy link

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]

@@ -0,0 +1,140 @@
import type { TurboModule } from 'react-native';
Copy link

Choose a reason for hiding this comment

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

Error loading TSDoc config file:
Error encountered for /home/runner/work/react-native-sdk/tsdoc.json:
Unable to resolve "extends" reference to "typedoc/tsdoc.json": Cannot find module 'typedoc/tsdoc.json' from '/home/runner/work/react-native-sdk'
[eslint:tsdoc/syntax]

@@ -0,0 +1,6 @@
import { NativeModules } from 'react-native';
Copy link

Choose a reason for hiding this comment

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

Error loading TSDoc config file:
Error encountered for /home/runner/work/react-native-sdk/tsdoc.json:
Unable to resolve "extends" reference to "typedoc/tsdoc.json": Cannot find module 'typedoc/tsdoc.json' from '/home/runner/work/react-native-sdk'
[eslint:tsdoc/syntax]

Comment on lines +70 to +97
public void initializeWithApiKey(String apiKey, ReadableMap configReadableMap, String version, Promise promise) {
IterableLogger.d(TAG, "initializeWithApiKey: " + apiKey);
IterableConfig.Builder configBuilder = Serialization.getConfigFromReadableMap(configReadableMap);

@Override
public String getName() {
return "RNIterableAPI";
if (configReadableMap.hasKey("urlHandlerPresent") && configReadableMap.getBoolean("urlHandlerPresent") == true) {
configBuilder.setUrlHandler(this);
}

if (configReadableMap.hasKey("customActionHandlerPresent") && configReadableMap.getBoolean("customActionHandlerPresent") == true) {
configBuilder.setCustomActionHandler(this);
}

if (configReadableMap.hasKey("inAppHandlerPresent") && configReadableMap.getBoolean("inAppHandlerPresent") == true) {
configBuilder.setInAppHandler(this);
}

if (configReadableMap.hasKey("authHandlerPresent") && configReadableMap.getBoolean("authHandlerPresent") == true) {
configBuilder.setAuthHandler(this);
}

IterableApi.initialize(reactContext, apiKey, configBuilder.build());
IterableApi.getInstance().setDeviceAttribute("reactNativeSDKVersion", version);

IterableApi.getInstance().getInAppManager().addListener(this);

// MOB-10421: Figure out what the error cases are and handle them appropriately
// This is just here to match the TS types and let the JS thread know when we are done initializing
promise.resolve(true);
Copy link

Choose a reason for hiding this comment

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

Found 2 issues:

1. Function with high complexity (count = 5): initializeWithApiKey [qlty:function-complexity]


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

Comment on lines 893 to 899
static updateSubscriptions(
emailListIds: number[] | undefined,
unsubscribedChannelIds: number[] | undefined,
unsubscribedMessageTypeIds: number[] | undefined,
subscribedMessageTypeIds: number[] | undefined,
emailListIds: number[] | null,
unsubscribedChannelIds: number[] | null,
unsubscribedMessageTypeIds: number[] | null,
subscribedMessageTypeIds: number[] | null,
campaignId: number,
templateId: number
Copy link

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]

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

1 participant