diff --git a/CHANGELOG.md b/CHANGELOG.md index 4cddd6b74..bf63acb29 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -7,6 +7,7 @@ - Display the whole chapter title, without truncating it [#2499](https://github.com/Automattic/pocket-casts-ios/pull/2499) - Allow sending user logs using email [#2525](https://github.com/Automattic/pocket-casts-ios/pull/2525) - Fix Default Player crash by passing the reference of the proxy if needed [#2522](https://github.com/Automattic/pocket-casts-ios/pull/2522) +- Remove logout from failed background HTTP requests. [#2586](https://github.com/Automattic/pocket-casts-ios/pull/2586) 7.78 ----- diff --git a/Modules/Server/Sources/PocketCastsServer/Private/TokenHelper.swift b/Modules/Server/Sources/PocketCastsServer/Private/TokenHelper.swift index f3f4a99c9..e8c4dff0b 100644 --- a/Modules/Server/Sources/PocketCastsServer/Private/TokenHelper.swift +++ b/Modules/Server/Sources/PocketCastsServer/Private/TokenHelper.swift @@ -1,5 +1,10 @@ import Foundation import PocketCastsUtils +#if os(iOS) +import UIKit +#elseif os(watchOS) +import WatchKit +#endif class TokenHelper { @@ -85,17 +90,21 @@ class TokenHelper { ServerSettings.setRefreshToken(refreshedRefreshToken) } else { - if ServerConfig.avoidLogoutOnError { - // if the user doesn't have an email and password or SSO token, they aren't going to be able to acquire a sync token - switch error as? APIError { - case APIError.TOKEN_DEAUTH?, APIError.PERMISSION_DENIED?: + if isApplicationBackgrounded() && ServerConfig.avoidLogoutInBackground { + FileLog.shared.addMessage("TokenHelper: Skipped logout in background due to error: \(String(describing: error))") + } else { + if ServerConfig.avoidLogoutOnError { + // if the user doesn't have an email and password or SSO token, they aren't going to be able to acquire a sync token + switch error as? APIError { + case APIError.TOKEN_DEAUTH?, APIError.PERMISSION_DENIED?: + tokenCleanUp() + default: + // Do nothing so the user is not disrupted in the case of non-auth errors + FileLog.shared.addMessage("TokenHelper: Unable to acquire token but avoided logout due to error: \(String(describing: error))") + } + } else { tokenCleanUp() - default: - // Do nothing so the user is not disrupted in the case of non-auth errors - FileLog.shared.addMessage("TokenHelper: Unable to acquire token but avoided logout due to error: \(String(describing: error))") } - } else { - tokenCleanUp() } return nil @@ -104,6 +113,24 @@ class TokenHelper { return refreshedToken } + private func isApplicationBackgrounded() -> Bool { + let semaphore = DispatchSemaphore(value: 0) + var isBackgrounded = false + + DispatchQueue.main.async { + #if os(iOS) + isBackgrounded = UIApplication.shared.applicationState == .background + #elseif os(watchOS) + isBackgrounded = WKExtension.shared().applicationState == .background + #endif + + semaphore.signal() + } + + semaphore.wait() + return isBackgrounded + } + // MARK: - Email / Password Token func acquirePasswordToken() throws -> AuthenticationResponse? { diff --git a/Modules/Server/Sources/PocketCastsServer/Public/ServerConfig.swift b/Modules/Server/Sources/PocketCastsServer/Public/ServerConfig.swift index c02a34b49..5ab9697bd 100644 --- a/Modules/Server/Sources/PocketCastsServer/Public/ServerConfig.swift +++ b/Modules/Server/Sources/PocketCastsServer/Public/ServerConfig.swift @@ -4,6 +4,7 @@ public class ServerConfig { public static let shared = ServerConfig() public static var avoidLogoutOnError = false + public static var avoidLogoutInBackground = false private var backgroundSessionHandler: (() -> Void)? diff --git a/Modules/Utils/Sources/PocketCastsUtils/Feature Flags/FeatureFlag.swift b/Modules/Utils/Sources/PocketCastsUtils/Feature Flags/FeatureFlag.swift index 62ef2c5a1..dbfd1037d 100644 --- a/Modules/Utils/Sources/PocketCastsUtils/Feature Flags/FeatureFlag.swift +++ b/Modules/Utils/Sources/PocketCastsUtils/Feature Flags/FeatureFlag.swift @@ -146,6 +146,12 @@ public enum FeatureFlag: String, CaseIterable { /// Uses the episode IDs from the server's response rather than our local database IDs case useSyncResponseEpisodeIDs + ///Use html description for podcast details + case usePodcastHTMLDescription + + /// Disables logout / keychain clearing when errors occur in the background + case avoidLogoutInBackground + public var enabled: Bool { if let overriddenValue = FeatureFlagOverrideStore().overriddenValue(for: self) { return overriddenValue @@ -244,6 +250,10 @@ public enum FeatureFlag: String, CaseIterable { true case .useSyncResponseEpisodeIDs: true + case .usePodcastHTMLDescription: + false + case .avoidLogoutInBackground: + true } } diff --git a/podcasts/AppDelegate.swift b/podcasts/AppDelegate.swift index 2e463bcbb..ef4c1b9ae 100644 --- a/podcasts/AppDelegate.swift +++ b/podcasts/AppDelegate.swift @@ -296,6 +296,7 @@ class AppDelegate: UIResponder, UIApplicationDelegate { self?.updateEndOfYearRemoteValue() self?.updateRemoteFeatureFlags() ServerConfig.avoidLogoutOnError = FeatureFlag.errorLogoutHandling.enabled + ServerConfig.avoidLogoutInBackground = FeatureFlag.avoidLogoutInBackground.enabled } }