diff --git a/Signal/src/AppDelegate.m b/Signal/src/AppDelegate.m index 72b5650f5..e6b4745b2 100644 --- a/Signal/src/AppDelegate.m +++ b/Signal/src/AppDelegate.m @@ -645,14 +645,19 @@ static NSTimeInterval launchStartedAt; - (void)enableBackgroundRefreshIfNecessary { [AppReadiness runNowOrWhenAppDidBecomeReady:^{ - if (OWS2FAManager.sharedManager.is2FAEnabled && [self.tsAccountManager isRegisteredAndReady]) { - // Ping server once a day to keep-alive 2FA clients. - const NSTimeInterval kBackgroundRefreshInterval = 24 * 60 * 60; - [[UIApplication sharedApplication] setMinimumBackgroundFetchInterval:kBackgroundRefreshInterval]; - } else { - [[UIApplication sharedApplication] - setMinimumBackgroundFetchInterval:UIApplicationBackgroundFetchIntervalNever]; - } + const NSTimeInterval minimumBackgroundFetchInterval = 5 * 60; // This seems to be the lower bound on what iOS allows + [UIApplication.sharedApplication setMinimumBackgroundFetchInterval:minimumBackgroundFetchInterval]; + // Loki: Original code + // ======== +// if (OWS2FAManager.sharedManager.is2FAEnabled && [self.tsAccountManager isRegisteredAndReady]) { +// // Ping server once a day to keep-alive 2FA clients. +// const NSTimeInterval kBackgroundRefreshInterval = 24 * 60 * 60; +// [[UIApplication sharedApplication] setMinimumBackgroundFetchInterval:kBackgroundRefreshInterval]; +// } else { +// [[UIApplication sharedApplication] +// setMinimumBackgroundFetchInterval:UIApplicationBackgroundFetchIntervalNever]; +// } + // ======== }]; } @@ -712,7 +717,16 @@ static NSTimeInterval launchStartedAt; [self.socketManager requestSocketOpen]; [Environment.shared.contactsManager fetchSystemContactsOnceIfAlreadyAuthorized]; [[AppEnvironment.shared.messageFetcherJob run] retainUntilComplete]; - + + [[LokiAPI objc_getMessages].then(^(id result) { + // TODO: Handle result + + }).catch(^(NSError *error) { + + }) retainUntilComplete]; + + // TODO: Ping friends to let them know we're online + if (![UIApplication sharedApplication].isRegisteredForRemoteNotifications) { OWSLogInfo(@"Retrying to register for remote notifications since user hasn't registered yet."); // Push tokens don't normally change while the app is launched, so checking once during launch is @@ -1145,21 +1159,30 @@ static NSTimeInterval launchStartedAt; { OWSLogInfo(@"performing background fetch"); [AppReadiness runNowOrWhenAppDidBecomeReady:^{ - __block AnyPromise *job = [AppEnvironment.shared.messageFetcherJob run].then(^{ - // HACK: Call completion handler after n seconds. - // - // We don't currently have a convenient API to know when message fetching is *done* when - // working with the websocket. - // - // We *could* substantially rewrite the TSSocketManager to take advantage of the `empty` message - // But once our REST endpoint is fixed to properly de-enqueue fallback notifications, we can easily - // use the rest endpoint here rather than the websocket and circumvent making changes to critical code. - dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(5 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{ - completionHandler(UIBackgroundFetchResultNewData); - job = nil; - }); - }); - [job retainUntilComplete]; + [[LokiAPI objc_getMessages].then(^(id result) { + completionHandler(UIBackgroundFetchResultNewData); + }).catch(^(NSError *error) { + completionHandler(UIBackgroundFetchResultFailed); + }) retainUntilComplete]; + + // Loki: Original code + // ======== +// __block AnyPromise *job = [AppEnvironment.shared.messageFetcherJob run].then(^{ +// // HACK: Call completion handler after n seconds. +// // +// // We don't currently have a convenient API to know when message fetching is *done* when +// // working with the websocket. +// // +// // We *could* substantially rewrite the TSSocketManager to take advantage of the `empty` message +// // But once our REST endpoint is fixed to properly de-enqueue fallback notifications, we can easily +// // use the rest endpoint here rather than the websocket and circumvent making changes to critical code. +// dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(5 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{ +// completionHandler(UIBackgroundFetchResultNewData); +// job = nil; +// }); +// }); +// [job retainUntilComplete]; + // ======== }]; } diff --git a/SignalServiceKit/src/Loki/LokiAPI.swift b/SignalServiceKit/src/Loki/LokiAPI.swift index ed6453202..68ad3e0df 100644 --- a/SignalServiceKit/src/Loki/LokiAPI.swift +++ b/SignalServiceKit/src/Loki/LokiAPI.swift @@ -66,7 +66,17 @@ import PromiseKit } // MARK: Obj-C API - @objc public static func sendSignalMessage(_ signalMessage: SignalMessage, to destination: String, requiringPoW isPoWRequired: Bool, completionHandler: @escaping (RawResponse?, NSError?) -> Void) { - LokiMessage.fromSignalMessage(signalMessage, requiringPoW: isPoWRequired).then(sendMessage).done { completionHandler($0, nil) }.catch { completionHandler(nil, $0 as NSError) } + @objc public static func objc_getMessages() -> AnyPromise { + let promise = getMessages() + let anyPromise = AnyPromise(promise) + anyPromise.retainUntilComplete() + return anyPromise + } + + @objc public static func objc_sendSignalMessage(_ signalMessage: SignalMessage, to destination: String, requiringPoW isPoWRequired: Bool) -> AnyPromise { + let promise = LokiMessage.fromSignalMessage(signalMessage, requiringPoW: isPoWRequired).then(sendMessage) + let anyPromise = AnyPromise(promise) + anyPromise.retainUntilComplete() + return anyPromise } } diff --git a/SignalServiceKit/src/Messages/OWSMessageSender.m b/SignalServiceKit/src/Messages/OWSMessageSender.m index 1137328f0..74c3340c3 100644 --- a/SignalServiceKit/src/Messages/OWSMessageSender.m +++ b/SignalServiceKit/src/Messages/OWSMessageSender.m @@ -1111,9 +1111,33 @@ NSString *const OWSMessageSenderRateLimitedException = @"RateLimitedException"; // Convert the message to a Loki message and send it using the Loki messaging API NSDictionary *signalMessage = deviceMessages.firstObject; BOOL isPoWRequired = YES; // TODO: Base on message type - [LokiAPI sendSignalMessage:signalMessage to:recipient.recipientId requiringPoW:isPoWRequired completionHandler:^(id response, NSError *error) { - // TODO: Use the response - }]; + [[LokiAPI objc_sendSignalMessage:signalMessage to:recipient.recipientId requiringPoW:isPoWRequired] + .thenOn([OWSDispatch sendingQueue], ^(id result) { + [self messageSendDidSucceed:messageSend + deviceMessages:deviceMessages + wasSentByUD:false + wasSentByWebsocket:false]; + }) + .catchOn(OWSDispatch.sendingQueue, ^(NSError *error) { + NSUInteger statusCode = 0; + NSData *_Nullable responseData = nil; + if ([error.domain isEqualToString:TSNetworkManagerErrorDomain]) { + statusCode = error.code; + NSError *_Nullable underlyingError = error.userInfo[NSUnderlyingErrorKey]; + if (underlyingError) { + responseData = underlyingError.userInfo[AFNetworkingOperationFailingURLResponseDataErrorKey]; + } else { + OWSFailDebug(@"Missing underlying error: %@", error); + } + } else { + OWSFailDebug(@"Unexpected error: %@", error); + } + [self messageSendDidFail:messageSend + deviceMessages:deviceMessages + statusCode:statusCode + error:error + responseData:responseData]; + }) retainUntilComplete]; // Loki: Original code /*