diff --git a/iOS_SDK/OneSignalDevApp/OneSignalDevApp/AppDelegate.m b/iOS_SDK/OneSignalDevApp/OneSignalDevApp/AppDelegate.m index 8c2daa5dd..7fecdd48d 100644 --- a/iOS_SDK/OneSignalDevApp/OneSignalDevApp/AppDelegate.m +++ b/iOS_SDK/OneSignalDevApp/OneSignalDevApp/AppDelegate.m @@ -237,13 +237,9 @@ - (void)userNotificationCenter:(UNUserNotificationCenter *)center willPresentNotificationWithPayload:notification.request.content.userInfo completion:^(OSNotification *notif) { if (notif) { - if (@available(iOS 14.0, *)) { - completionHandler(UNNotificationPresentationOptionBanner | - UNNotificationPresentationOptionList | - UNNotificationPresentationOptionSound); - } else { - completionHandler(UNNotificationPresentationOptionAlert | UNNotificationPresentationOptionSound); - } + completionHandler(UNNotificationPresentationOptionBanner | + UNNotificationPresentationOptionList | + UNNotificationPresentationOptionSound); } else { completionHandler(UNNotificationPresentationOptionNone); } diff --git a/iOS_SDK/OneSignalDevApp/OneSignalDevApp/LiveActivityController.swift b/iOS_SDK/OneSignalDevApp/OneSignalDevApp/LiveActivityController.swift index f61eab7c1..a6708669e 100644 --- a/iOS_SDK/OneSignalDevApp/OneSignalDevApp/LiveActivityController.swift +++ b/iOS_SDK/OneSignalDevApp/OneSignalDevApp/LiveActivityController.swift @@ -81,7 +81,6 @@ class LiveActivityController: NSObject { An example of starting a Live Activity whose attributes are "OneSignal SDK aware". The SDK will handle listening for update tokens on behalf of the app. */ static var counter1 = 0 - @available(iOS 13.0, *) @objc static func createOneSignalAwareActivity(activityId: String) { if #available(iOS 16.1, *) { @@ -103,7 +102,6 @@ class LiveActivityController: NSObject { /** An example of starting a Live Activity using the DefaultLiveActivityAttributes. The SDK will handle listening for update tokens on behalf of the app. */ - @available(iOS 13.0, *) @objc static func createDefaultActivity(activityId: String) { if #available(iOS 16.1, *) { @@ -118,7 +116,6 @@ class LiveActivityController: NSObject { An example of starting a Live Activity whose attributes are **not** "OneSignal SDK aware". The app must handle listening for update tokens and notify the OneSignal SDK. */ static var counter2 = 0 - @available(iOS 13.0, *) @objc static func createActivity(activityId: String) async { if #available(iOS 16.1, *) { diff --git a/iOS_SDK/OneSignalDevApp/OneSignalDevApp/ViewController.m b/iOS_SDK/OneSignalDevApp/OneSignalDevApp/ViewController.m index 083b34a67..e0c0a2961 100644 --- a/iOS_SDK/OneSignalDevApp/OneSignalDevApp/ViewController.m +++ b/iOS_SDK/OneSignalDevApp/OneSignalDevApp/ViewController.m @@ -238,19 +238,15 @@ - (IBAction)sendUniqueOutcomeEvent:(id)sender { - (IBAction)startAndEnterLiveActivity:(id)sender { #if TARGET_OS_MACCATALYST #else - if (@available(iOS 13.0, *)) { - NSString *activityId = [self.activityId text]; - // Will not make a live activity if activityId is empty - if (activityId && activityId.length) { - // 1. Create a Default activity - // [LiveActivityController createDefaultActivityWithActivityId:activityId ]; - // 2. Create non-OneSignal-aware activity - // [LiveActivityController createActivityWithActivityId:activityId completionHandler:^(void) {} ]; - // 3. Create OneSignal-aware activity - [LiveActivityController createOneSignalAwareActivityWithActivityId:activityId]; - } - } else { - NSLog(@"Must use iOS 13 or later for swift concurrency which is required for [LiveActivityController createActivityWithCompletionHandler..."); + NSString *activityId = [self.activityId text]; + // Will not make a live activity if activityId is empty + if (activityId && activityId.length) { + // 1. Create a Default activity + // [LiveActivityController createDefaultActivityWithActivityId:activityId ]; + // 2. Create non-OneSignal-aware activity + // [LiveActivityController createActivityWithActivityId:activityId completionHandler:^(void) {} ]; + // 3. Create OneSignal-aware activity + [LiveActivityController createOneSignalAwareActivityWithActivityId:activityId]; } #endif } diff --git a/iOS_SDK/OneSignalSDK/OneSignal.xcodeproj/project.pbxproj b/iOS_SDK/OneSignalSDK/OneSignal.xcodeproj/project.pbxproj index fe5496cf7..2b73ef84c 100644 --- a/iOS_SDK/OneSignalSDK/OneSignal.xcodeproj/project.pbxproj +++ b/iOS_SDK/OneSignalSDK/OneSignal.xcodeproj/project.pbxproj @@ -294,6 +294,7 @@ 473542672B8F93830016DB4C /* OneSignalUserMocks.framework in Embed Frameworks */ = {isa = PBXBuildFile; fileRef = 3CC063DD2B6D7F2A002BB07F /* OneSignalUserMocks.framework */; settings = {ATTRIBUTES = (CodeSignOnCopy, RemoveHeadersOnCopy, ); }; }; 4746E2A72B86B64100D6324C /* LiveActivitiesSwiftTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = 4746E2A62B86B64100D6324C /* LiveActivitiesSwiftTests.swift */; }; 4746E2AB2B8775C400D6324C /* LiveActivitiesObjcTests.m in Sources */ = {isa = PBXBuildFile; fileRef = 4746E2AA2B8775C400D6324C /* LiveActivitiesObjcTests.m */; }; + 53075307A11C000000000A02 /* OneSignalAttachmentHandlerTests.m in Sources */ = {isa = PBXBuildFile; fileRef = 53075307A11C000000000A01 /* OneSignalAttachmentHandlerTests.m */; }; 475F47212B8E398E00EC05B3 /* OneSignalLiveActivities.h in Headers */ = {isa = PBXBuildFile; fileRef = 475F47202B8E398E00EC05B3 /* OneSignalLiveActivities.h */; settings = {ATTRIBUTES = (Public, ); }; }; 475F47242B8E398E00EC05B3 /* OneSignalLiveActivities.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 475F471E2B8E398D00EC05B3 /* OneSignalLiveActivities.framework */; }; 475F47252B8E398E00EC05B3 /* OneSignalLiveActivities.framework in Embed Frameworks */ = {isa = PBXBuildFile; fileRef = 475F471E2B8E398D00EC05B3 /* OneSignalLiveActivities.framework */; settings = {ATTRIBUTES = (CodeSignOnCopy, RemoveHeadersOnCopy, ); }; }; @@ -1537,6 +1538,7 @@ 4735424C2B8F93340016DB4C /* OSLiveActivitiesExecutorTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = OSLiveActivitiesExecutorTests.swift; sourceTree = ""; }; 4746E2A62B86B64100D6324C /* LiveActivitiesSwiftTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = LiveActivitiesSwiftTests.swift; sourceTree = ""; }; 4746E2AA2B8775C400D6324C /* LiveActivitiesObjcTests.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = LiveActivitiesObjcTests.m; sourceTree = ""; }; + 53075307A11C000000000A01 /* OneSignalAttachmentHandlerTests.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = OneSignalAttachmentHandlerTests.m; sourceTree = ""; }; 475F471E2B8E398D00EC05B3 /* OneSignalLiveActivities.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = OneSignalLiveActivities.framework; sourceTree = BUILT_PRODUCTS_DIR; }; 475F47202B8E398E00EC05B3 /* OneSignalLiveActivities.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = OneSignalLiveActivities.h; sourceTree = ""; }; 475F47482B8E3A4400EC05B3 /* Info.plist */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; @@ -2736,6 +2738,7 @@ 3C2C7DC2288E007E0020F9AE /* UnitTests-Bridging-Header.h */, 4746E2A62B86B64100D6324C /* LiveActivitiesSwiftTests.swift */, 4746E2AA2B8775C400D6324C /* LiveActivitiesObjcTests.m */, + 53075307A11C000000000A01 /* OneSignalAttachmentHandlerTests.m */, 3C4319082F4CE9D90075492D /* SessionEndOutcomesRequestTests.swift */, 658E6E9E6BC6BBF702BCBD33 /* OSRemoteLoggingControllerTests.swift */, ); @@ -4766,6 +4769,7 @@ DE5EFECA24D8DBF70032632D /* OSInAppMessageViewControllerOverrider.m in Sources */, DE7D18E12703B49B002D3A5D /* OSFocusRequests.m in Sources */, 4746E2AB2B8775C400D6324C /* LiveActivitiesObjcTests.m in Sources */, + 53075307A11C000000000A02 /* OneSignalAttachmentHandlerTests.m in Sources */, 03CCCC832835D90F004BF794 /* OneSignalUNUserNotificationCenterHelper.m in Sources */, 03866CC12378A67B0009C1D8 /* RestClientAsserts.m in Sources */, 7ADF891C230DB5BD0054E0D6 /* UnitTestAppDelegate.m in Sources */, diff --git a/iOS_SDK/OneSignalSDK/OneSignalCore/Source/OSBundleUtils.m b/iOS_SDK/OneSignalSDK/OneSignalCore/Source/OSBundleUtils.m index dfd407799..63e6e8cec 100644 --- a/iOS_SDK/OneSignalSDK/OneSignalCore/Source/OSBundleUtils.m +++ b/iOS_SDK/OneSignalSDK/OneSignalCore/Source/OSBundleUtils.m @@ -25,10 +25,7 @@ of this software and associated documentation files (the "Software"), to deal @implementation OSBundleUtils + (BOOL)isAppUsingUIScene { - if (@available(iOS 13.0, *)) { - return [[NSBundle mainBundle] objectForInfoDictionaryKey:@"UIApplicationSceneManifest"] != nil; - } - return NO; + return [[NSBundle mainBundle] objectForInfoDictionaryKey:@"UIApplicationSceneManifest"] != nil; } @end diff --git a/iOS_SDK/OneSignalSDK/OneSignalCoreMocks/OneSignalCoreMocks.swift b/iOS_SDK/OneSignalSDK/OneSignalCoreMocks/OneSignalCoreMocks.swift index 20cddf0cd..a05160c99 100644 --- a/iOS_SDK/OneSignalSDK/OneSignalCoreMocks/OneSignalCoreMocks.swift +++ b/iOS_SDK/OneSignalSDK/OneSignalCoreMocks/OneSignalCoreMocks.swift @@ -71,10 +71,8 @@ public class OneSignalCoreMocks: NSObject { @objc public static func backgroundApp() { if OSBundleUtils.isAppUsingUIScene() { - if #available(iOS 13.0, *) { - NotificationCenter.default.post(name: UIScene.willDeactivateNotification, object: nil) - NotificationCenter.default.post(name: UIScene.didEnterBackgroundNotification, object: nil) - } + NotificationCenter.default.post(name: UIScene.willDeactivateNotification, object: nil) + NotificationCenter.default.post(name: UIScene.didEnterBackgroundNotification, object: nil) } else { NotificationCenter.default.post(name: UIApplication.willResignActiveNotification, object: nil) NotificationCenter.default.post(name: UIApplication.didEnterBackgroundNotification, object: nil) @@ -83,10 +81,8 @@ public class OneSignalCoreMocks: NSObject { @objc public static func foregroundApp() { if OSBundleUtils.isAppUsingUIScene() { - if #available(iOS 13.0, *) { - NotificationCenter.default.post(name: UIScene.willEnterForegroundNotification, object: nil) - NotificationCenter.default.post(name: UIScene.didActivateNotification, object: nil) - } + NotificationCenter.default.post(name: UIScene.willEnterForegroundNotification, object: nil) + NotificationCenter.default.post(name: UIScene.didActivateNotification, object: nil) } else { NotificationCenter.default.post(name: UIApplication.willEnterForegroundNotification, object: nil) NotificationCenter.default.post(name: UIApplication.didBecomeActiveNotification, object: nil) @@ -95,9 +91,7 @@ public class OneSignalCoreMocks: NSObject { @objc public static func resignActive() { if OSBundleUtils.isAppUsingUIScene() { - if #available(iOS 13.0, *) { - NotificationCenter.default.post(name: UIScene.willDeactivateNotification, object: nil) - } + NotificationCenter.default.post(name: UIScene.willDeactivateNotification, object: nil) } else { NotificationCenter.default.post(name: UIApplication.willResignActiveNotification, object: nil) } @@ -105,9 +99,7 @@ public class OneSignalCoreMocks: NSObject { @objc public static func becomeActive() { if OSBundleUtils.isAppUsingUIScene() { - if #available(iOS 13.0, *) { - NotificationCenter.default.post(name: UIScene.didActivateNotification, object: nil) - } + NotificationCenter.default.post(name: UIScene.didActivateNotification, object: nil) } else { NotificationCenter.default.post(name: UIApplication.didBecomeActiveNotification, object: nil) } diff --git a/iOS_SDK/OneSignalSDK/OneSignalExtension/OneSignalAttachmentHandler.m b/iOS_SDK/OneSignalSDK/OneSignalExtension/OneSignalAttachmentHandler.m index e955a408e..c3209c6bb 100644 --- a/iOS_SDK/OneSignalSDK/OneSignalExtension/OneSignalAttachmentHandler.m +++ b/iOS_SDK/OneSignalSDK/OneSignalExtension/OneSignalAttachmentHandler.m @@ -47,35 +47,8 @@ @implementation DirectDownloadDelegate @synthesize error, response, done; -(void)URLSession:(NSURLSession *)session dataTask:(NSURLSessionDataTask *)dataTask didReceiveData:(NSData *)data { - NSError * __autoreleasing fileHandleError; - NSError * __autoreleasing *fileHandleErrorPointer = &fileHandleError; - if (@available(iOS 13.0, *)) { - // We need to use NSInvocation for reflection because performSelector cannot take pointer parameters - SEL writeDataSelector = NSSelectorFromString(@"writeData:error:"); - NSInvocation *invocation = [NSInvocation invocationWithMethodSignature:[NSFileHandle instanceMethodSignatureForSelector:writeDataSelector]]; - [invocation setTarget:outputHandle]; - [invocation setSelector:writeDataSelector]; - /* - From Apple's Documentation on NSInvocation: - Indices 0 and 1 indicate the hidden arguments self and _cmd, respectively; - you should set these values directly with the target and selector properties. - Use indices 2 and greater for the arguments normally passed in a message. - */ - [invocation setArgument:&data atIndex:2]; - [invocation setArgument:&fileHandleErrorPointer atIndex:3]; - [invocation invoke]; - } else { - @try { - [outputHandle writeData:data]; - } @catch (NSException *e) { - NSDictionary *userInfo = @{ - NSLocalizedDescriptionKey : @"Failed to write attachment data to filehandle", - }; - fileHandleError = [NSError errorWithDomain:@"com.onesignal.download" code:0 userInfo:userInfo]; - } - } - - if (fileHandleError != nil) { + NSError *fileHandleError; + if (![outputHandle writeData:data error:&fileHandleError]) { [OneSignalLog onesignalLog:ONE_S_LL_ERROR message:[NSString stringWithFormat:@"OneSignal Error encountered while downloading attachment: %@", fileHandleError]]; } } @@ -265,46 +238,16 @@ + (void)addAttachments:(OSNotification*)notification + (UNNotificationAction *)createActionForButton:(NSDictionary *)button { NSString *buttonId = button[@"id"]; NSString *buttonText = button[@"text"]; - - if (@available(iOS 15.0, *)) { - // Using reflection for Xcode versions lower than 13 - id icon; // UNNotificationActionIcon - let UNNotificationActionIconClass = NSClassFromString(@"UNNotificationActionIcon"); - if (UNNotificationActionIconClass) { - if (button[@"systemIcon"]) { - icon = [UNNotificationActionIconClass performSelector:@selector(iconWithSystemImageName:) - withObject:button[@"systemIcon"]]; - } else if (button[@"templateIcon"]) { - icon = [UNNotificationActionIconClass performSelector:@selector(iconWithTemplateImageName:) - withObject:button[@"templateIcon"]]; - } - } - - // We need to use NSInvocation because performSelector only allows up to 2 arguments - SEL actionSelector = NSSelectorFromString(@"actionWithIdentifier:title:options:icon:"); - UNNotificationAction * __unsafe_unretained action; - NSInvocation *invocation = [NSInvocation invocationWithMethodSignature:[UNNotificationAction methodSignatureForSelector:actionSelector]]; - [invocation setTarget:[UNNotificationAction class]]; - [invocation setSelector:actionSelector]; - /* - From Apple's Documentation on NSInvocation: - Indices 0 and 1 indicate the hidden arguments self and _cmd, respectively; - you should set these values directly with the target and selector properties. - Use indices 2 and greater for the arguments normally passed in a message. - */ - NSUInteger actionOption = UNNotificationActionOptionForeground; - [invocation setArgument:&buttonId atIndex:2]; - [invocation setArgument:&buttonText atIndex:3]; - [invocation setArgument:&actionOption atIndex:4]; - [invocation setArgument:&icon atIndex:5]; - [invocation invoke]; - [invocation getReturnValue:&action]; - return action; - } else { - return [UNNotificationAction actionWithIdentifier:buttonId - title:buttonText - options:UNNotificationActionOptionForeground]; + UNNotificationActionIcon *icon; + if (button[@"systemIcon"]) { + icon = [UNNotificationActionIcon iconWithSystemImageName:button[@"systemIcon"]]; + } else if (button[@"templateIcon"]) { + icon = [UNNotificationActionIcon iconWithTemplateImageName:button[@"templateIcon"]]; } + return [UNNotificationAction actionWithIdentifier:buttonId + title:buttonText + options:UNNotificationActionOptionForeground + icon:icon]; } /* diff --git a/iOS_SDK/OneSignalSDK/OneSignalInAppMessages/Controller/OSMessagingController.m b/iOS_SDK/OneSignalSDK/OneSignalInAppMessages/Controller/OSMessagingController.m index 5e1256482..3d855ab8c 100644 --- a/iOS_SDK/OneSignalSDK/OneSignalInAppMessages/Controller/OSMessagingController.m +++ b/iOS_SDK/OneSignalSDK/OneSignalInAppMessages/Controller/OSMessagingController.m @@ -1173,13 +1173,7 @@ - (void)webViewContentFinishedLoading:(OSInAppMessageInternal *)message { // Required to display if the app is using a Scene // See https://github.com/OneSignal/OneSignal-iOS-SDK/issues/648 - (void)addKeySceneToWindow:(UIWindow*)window { - if (@available(iOS 13.0, *)) { - // The below lines can be replace with this single line once Xcode 10 support is dropped - // window.windowScene = UIApplication.sharedApplication.keyWindow.windowScene; - UIWindow *keyWindow = UIApplication.sharedApplication.keyWindow; - id windowScene = [keyWindow performSelector:@selector(windowScene)]; - [window performSelector:@selector(setWindowScene:) withObject:windowScene]; - } + window.windowScene = UIApplication.sharedApplication.keyWindow.windowScene; } - (void)dynamicTriggerCompleted:(NSString *)triggerId { diff --git a/iOS_SDK/OneSignalSDK/OneSignalInAppMessages/UIApplication+OneSignal.m b/iOS_SDK/OneSignalSDK/OneSignalInAppMessages/UIApplication+OneSignal.m index d48950e0d..9ffec9c07 100644 --- a/iOS_SDK/OneSignalSDK/OneSignalInAppMessages/UIApplication+OneSignal.m +++ b/iOS_SDK/OneSignalSDK/OneSignalInAppMessages/UIApplication+OneSignal.m @@ -33,13 +33,8 @@ @implementation UIApplication (OneSignal) + (BOOL)applicationIsActive { if ([OSBundleUtils isAppUsingUIScene] && [NSThread isMainThread]) { - if (@available(iOS 13.0, *)) { - UIWindow *keyWindow = UIApplication.sharedApplication.keyWindow; - id windowScene = [keyWindow performSelector:@selector(windowScene)]; - id session = [windowScene performSelector:@selector(session)]; - id scene = [session performSelector:@selector(scene)]; - return [scene performSelector:@selector(activationState)] == 0; - } + UIWindow *keyWindow = UIApplication.sharedApplication.keyWindow; + return keyWindow.windowScene.activationState == UISceneActivationStateForegroundActive; } return [[UIApplication sharedApplication] applicationState] == UIApplicationStateActive; } diff --git a/iOS_SDK/OneSignalSDK/OneSignalNotifications/Categories/UNUserNotificationCenter+OneSignalNotifications.m b/iOS_SDK/OneSignalSDK/OneSignalNotifications/Categories/UNUserNotificationCenter+OneSignalNotifications.m index 24cca02dd..58c11d141 100644 --- a/iOS_SDK/OneSignalSDK/OneSignalNotifications/Categories/UNUserNotificationCenter+OneSignalNotifications.m +++ b/iOS_SDK/OneSignalSDK/OneSignalNotifications/Categories/UNUserNotificationCenter+OneSignalNotifications.m @@ -345,8 +345,8 @@ + (void)forwardReceivedNotificationResponseWithCenter:(UNUserNotificationCenter // Or call a legacy AppDelegate selector // - If not a dismiss event as their isn't a iOS 9 selector for it. else if (![OneSignalNotificationsUNUserNotificationCenter isDismissEvent:response]) { - BOOL isTextReply = [response isKindOfClass:NSClassFromString(@"UNTextInputNotificationResponse")]; - NSString* userText = isTextReply ? [response valueForKey:@"userText"] : nil; + BOOL isTextReply = [response isKindOfClass:[UNTextInputNotificationResponse class]]; + NSString* userText = isTextReply ? ((UNTextInputNotificationResponse *)response).userText : nil; [OneSignalNotificationsUNUserNotificationCenter callLegacyAppDeletegateSelector:response.notification isTextReply:isTextReply actionIdentifier:response.actionIdentifier @@ -406,7 +406,7 @@ The iOS SDK used to call some local notification selectors (such as didReceiveLo the SDK will now print warnings when a developer's app implements these selectors */ BOOL isCustomAction = actionIdentifier && ![@"com.apple.UNNotificationDefaultActionIdentifier" isEqualToString:actionIdentifier]; - BOOL isRemote = [notification.request.trigger isKindOfClass:NSClassFromString(@"UNPushNotificationTrigger")]; + BOOL isRemote = [notification.request.trigger isKindOfClass:[UNPushNotificationTrigger class]]; if (isRemote) { NSDictionary* remoteUserInfo = notification.request.content.userInfo; diff --git a/iOS_SDK/OneSignalSDK/OneSignalNotifications/NotificationSettings/OneSignalNotificationSettings.m b/iOS_SDK/OneSignalSDK/OneSignalNotifications/NotificationSettings/OneSignalNotificationSettings.m index 86bafd846..5f80874fd 100644 --- a/iOS_SDK/OneSignalSDK/OneSignalNotifications/NotificationSettings/OneSignalNotificationSettings.m +++ b/iOS_SDK/OneSignalSDK/OneSignalNotifications/NotificationSettings/OneSignalNotificationSettings.m @@ -74,12 +74,8 @@ - (void)getNotificationPermissionState:(void (^)(OSPermissionStateInternal *subs status.answeredPrompt = settings.authorizationStatus != UNAuthorizationStatusNotDetermined && settings.authorizationStatus != provisionalStatus; status.provisional = (settings.authorizationStatus == 3); status.accepted = settings.authorizationStatus == UNAuthorizationStatusAuthorized && !status.provisional; - if (@available(iOS 14.0, *)) { - status.ephemeral = (settings.authorizationStatus == AUTH_STATUS_EPHEMERAL); - status.accepted = status.accepted || status.ephemeral; - } else { - status.ephemeral = false; - } + status.ephemeral = (settings.authorizationStatus == AUTH_STATUS_EPHEMERAL); + status.accepted = status.accepted || status.ephemeral; status.notificationTypes = (settings.badgeSetting == UNNotificationSettingEnabled ? 1 : 0) + (settings.soundSetting == UNNotificationSettingEnabled ? 2 : 0) diff --git a/iOS_SDK/OneSignalSDK/OneSignalNotifications/OSNotificationsManager.m b/iOS_SDK/OneSignalSDK/OneSignalNotifications/OSNotificationsManager.m index 6e70adddf..d855d0c7a 100644 --- a/iOS_SDK/OneSignalSDK/OneSignalNotifications/OSNotificationsManager.m +++ b/iOS_SDK/OneSignalSDK/OneSignalNotifications/OSNotificationsManager.m @@ -264,10 +264,8 @@ + (void)registerLifecycleObserver { } + (void)registerLifecycleObserverAsUIScene { - if (@available(iOS 13.0, *)) { - [OneSignalLog onesignalLog:ONE_S_LL_VERBOSE message:@"OSNotificationManager registering for Scene Lifecycle notifications"]; - [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(willEnterForeground) name:@"UISceneWillEnterForegroundNotification" object:nil]; - } + [OneSignalLog onesignalLog:ONE_S_LL_VERBOSE message:@"OSNotificationManager registering for Scene Lifecycle notifications"]; + [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(willEnterForeground) name:UISceneWillEnterForegroundNotification object:nil]; } + (void)registerLifecycleObserverAsUIApplication { diff --git a/iOS_SDK/OneSignalSDK/Source/OSRemoteLoggingController.swift b/iOS_SDK/OneSignalSDK/Source/OSRemoteLoggingController.swift index b60a1ad77..a957bdcd4 100644 --- a/iOS_SDK/OneSignalSDK/Source/OSRemoteLoggingController.swift +++ b/iOS_SDK/OneSignalSDK/Source/OSRemoteLoggingController.swift @@ -261,9 +261,9 @@ final class OSRemoteLoggingController: NSObject, OSInternalLogSink { private extension OSRemoteLoggingController { func registerLifecycleObservers() { if usesScenes() { - observe(Notification.Name("UISceneDidActivateNotification"), appState: "foreground") - observe(Notification.Name("UISceneWillDeactivateNotification"), appState: "unknown") - observe(Notification.Name("UISceneDidEnterBackgroundNotification"), appState: "background", flush: true) + observe(UIScene.didActivateNotification, appState: "foreground") + observe(UIScene.willDeactivateNotification, appState: "unknown") + observe(UIScene.didEnterBackgroundNotification, appState: "background", flush: true) } else { observe(UIApplication.didBecomeActiveNotification, appState: "foreground") observe(UIApplication.willResignActiveNotification, appState: "unknown") diff --git a/iOS_SDK/OneSignalSDK/Source/OneSignalLifecycleObserver.m b/iOS_SDK/OneSignalSDK/Source/OneSignalLifecycleObserver.m index bd20945c2..a2e9a9f08 100644 --- a/iOS_SDK/OneSignalSDK/Source/OneSignalLifecycleObserver.m +++ b/iOS_SDK/OneSignalSDK/Source/OneSignalLifecycleObserver.m @@ -58,12 +58,10 @@ + (void)registerLifecycleObserver { } + (void)registerLifecycleObserverAsUIScene { - if (@available(iOS 13.0, *)) { - [OneSignalLog onesignalLog:ONE_S_LL_VERBOSE message:@"registering for Scene Lifecycle notifications"]; - [[NSNotificationCenter defaultCenter] addObserver:[OneSignalLifecycleObserver sharedInstance] selector:@selector(didEnterBackground) name:@"UISceneDidEnterBackgroundNotification" object:nil]; - [[NSNotificationCenter defaultCenter] addObserver:[OneSignalLifecycleObserver sharedInstance] selector:@selector(didBecomeActive) name:@"UISceneDidActivateNotification" object:nil]; - [[NSNotificationCenter defaultCenter] addObserver:[OneSignalLifecycleObserver sharedInstance] selector:@selector(willResignActive) name:@"UISceneWillDeactivateNotification" object:nil]; - } + [OneSignalLog onesignalLog:ONE_S_LL_VERBOSE message:@"registering for Scene Lifecycle notifications"]; + [[NSNotificationCenter defaultCenter] addObserver:[OneSignalLifecycleObserver sharedInstance] selector:@selector(didEnterBackground) name:UISceneDidEnterBackgroundNotification object:nil]; + [[NSNotificationCenter defaultCenter] addObserver:[OneSignalLifecycleObserver sharedInstance] selector:@selector(didBecomeActive) name:UISceneDidActivateNotification object:nil]; + [[NSNotificationCenter defaultCenter] addObserver:[OneSignalLifecycleObserver sharedInstance] selector:@selector(willResignActive) name:UISceneWillDeactivateNotification object:nil]; } + (void)registerLifecycleObserverAsUIApplication { diff --git a/iOS_SDK/OneSignalSDK/UnitTests/OSRemoteLoggingControllerTests.swift b/iOS_SDK/OneSignalSDK/UnitTests/OSRemoteLoggingControllerTests.swift index 7ba395a26..4fbe32a0a 100644 --- a/iOS_SDK/OneSignalSDK/UnitTests/OSRemoteLoggingControllerTests.swift +++ b/iOS_SDK/OneSignalSDK/UnitTests/OSRemoteLoggingControllerTests.swift @@ -217,7 +217,7 @@ final class OSRemoteLoggingControllerTests: XCTestCase { wait(for: [telemetry.flushExpectation!], timeout: 0.2) telemetry.flushExpectation = expectation(description: "flushes on scene background") - notificationCenter.post(name: Notification.Name("UISceneDidEnterBackgroundNotification"), object: nil) + notificationCenter.post(name: UIScene.didEnterBackgroundNotification, object: nil) wait(for: [telemetry.flushExpectation!], timeout: 2) } diff --git a/iOS_SDK/OneSignalSDK/UnitTests/OneSignalAttachmentHandlerTests.m b/iOS_SDK/OneSignalSDK/UnitTests/OneSignalAttachmentHandlerTests.m new file mode 100644 index 000000000..9a0bb9bfc --- /dev/null +++ b/iOS_SDK/OneSignalSDK/UnitTests/OneSignalAttachmentHandlerTests.m @@ -0,0 +1,73 @@ +/* + Modified MIT License + + Copyright 2026 OneSignal + + Permission is hereby granted, free of charge, to any person obtaining a copy + of this software and associated documentation files (the "Software"), to deal + in the Software without restriction, including without limitation the rights + to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + copies of the Software, and to permit persons to whom the Software is + furnished to do so, subject to the following conditions: + + 1. The above copyright notice and this permission notice shall be included in + all copies or substantial portions of the Software. + + 2. All copies of substantial portions of the Software may only be used in connection + with services provided by OneSignal. + + THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + THE SOFTWARE. + */ + +#import +#import +#import + +@interface OneSignalAttachmentHandlerTests : XCTestCase +@end + +@implementation OneSignalAttachmentHandlerTests + +- (void)testCreateActionForButtonWithSystemIcon { + UNNotificationAction *action = [OneSignalAttachmentHandler createActionForButton:@{ + @"id": @"id1", + @"text": @"text1", + @"systemIcon": @"hand.thumbsup" + }]; + + XCTAssertEqualObjects(action.identifier, @"id1"); + XCTAssertEqualObjects(action.title, @"text1"); + XCTAssertEqual(action.options, UNNotificationActionOptionForeground); + XCTAssertNotNil(action.icon); +} + +- (void)testCreateActionForButtonWithTemplateIcon { + UNNotificationAction *action = [OneSignalAttachmentHandler createActionForButton:@{ + @"id": @"id1", + @"text": @"text1", + @"templateIcon": @"myImage/thumbsup" + }]; + + XCTAssertEqualObjects(action.identifier, @"id1"); + XCTAssertNotNil(action.icon); +} + +- (void)testCreateActionForButtonWithoutIcon { + UNNotificationAction *action = [OneSignalAttachmentHandler createActionForButton:@{ + @"id": @"id1", + @"text": @"text1" + }]; + + XCTAssertEqualObjects(action.identifier, @"id1"); + XCTAssertEqualObjects(action.title, @"text1"); + XCTAssertEqual(action.options, UNNotificationActionOptionForeground); + XCTAssertNil(action.icon); +} + +@end