Last active
March 3, 2022 13:08
-
-
Save Tak783/446b4921cf0894f031eacbd641122928 to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import UIKit | |
import SafariServices | |
import AuthenticationServices | |
import AppAuth | |
import Reachability | |
class OIDExternalUserAgentASWebAuthenticationSession: NSObject, OIDExternalUserAgent { | |
private let presentingViewController: UIViewController | |
private var externalUserAgentFlowInProgress: Bool = false | |
private var authenticationViewController: ASWebAuthenticationSession? | |
private weak var session: OIDExternalUserAgentSession? | |
init(with presentingViewController: UIViewController) { | |
self.presentingViewController = presentingViewController | |
super.init() | |
} | |
func present(_ request: OIDExternalUserAgentRequest, session: OIDExternalUserAgentSession) -> Bool { | |
if externalUserAgentFlowInProgress { | |
return false | |
} | |
guard let requestURL = request.externalUserAgentRequestURL() else { | |
return false | |
} | |
self.externalUserAgentFlowInProgress = true | |
self.session = session | |
var openedUserAgent = false | |
// ASWebAuthenticationSession doesn't work with guided access (Search web for "rdar://40809553") | |
// Make sure that the device is not in Guided Access mode "(Settings -> General -> Accessibility -> Enable Guided Access)" | |
if UIAccessibility.isGuidedAccessEnabled == false { | |
let redirectScheme = request.redirectScheme() | |
let authenticationViewController = ASWebAuthenticationSession(url: requestURL, callbackURLScheme: redirectScheme) { (callbackURL, error) in | |
self.authenticationViewController = nil | |
if let url = callbackURL { | |
self.session?.resumeExternalUserAgentFlow(with: url) | |
} else { | |
let webAuthenticationError = OIDErrorUtilities.error(with: OIDErrorCode.userCanceledAuthorizationFlow, | |
underlyingError: error, | |
description: nil) | |
self.session?.failExternalUserAgentFlowWithError(webAuthenticationError) | |
} | |
} | |
authenticationViewController.presentationContextProvider = self | |
/// ** Key Line of code -> `.prefersEphemeralWebBrowserSession`** allows for private browsing | |
authenticationViewController.prefersEphemeralWebBrowserSession = true | |
self.authenticationViewController = authenticationViewController | |
openedUserAgent = authenticationViewController.start() | |
} else { | |
let webAuthenticationError = OIDErrorUtilities.error(with: OIDErrorCode.safariOpenError, | |
underlyingError: AuthenticationManager.AuthenticationError.appInGuidedAccessMode, | |
description: nil) | |
self.session?.failExternalUserAgentFlowWithError(webAuthenticationError) | |
} | |
return openedUserAgent | |
} | |
func dismiss(animated: Bool, completion: @escaping () -> Void) { | |
// Ignore this call if there is no authorization flow in progress. | |
if externalUserAgentFlowInProgress == false { | |
completion() | |
} | |
cleanUp() | |
if authenticationViewController != nil { | |
authenticationViewController?.cancel() | |
completion() | |
} else { | |
completion() | |
} | |
return | |
} | |
} | |
extension OIDExternalUserAgentASWebAuthenticationSession { | |
/// Sets class variables to nil. Note 'weak references i.e. session are set to nil to avoid accidentally using them while not in an authorization flow. | |
func cleanUp() { | |
session = nil | |
authenticationViewController = nil | |
externalUserAgentFlowInProgress = false | |
} | |
} | |
extension OIDExternalUserAgentASWebAuthenticationSession: ASWebAuthenticationPresentationContextProviding { | |
func presentationAnchor(for session: ASWebAuthenticationSession) -> ASPresentationAnchor { | |
return presentingViewController.view.window! | |
} | |
} |
"prefersEphemeralWebBrowserSession" is only available on iOS 13 and later. Is there any other solution so it works on lower iOS versions?
Just add if #available(iOS 13, *) {...}
around the line setting prefersEphemeralWebBrowserSession
.
i mean is there any solution to make permission dialog not appearing on lower versions than iOS 13.
Depending on the scenario you could use SFSafariViewController as an external user agent, check the discussion here: openid/AppAuth-iOS#402
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Call Like this
let sceneDelegate = viewController.view.window?.windowScene?.delegate as? SceneDelegate
let externalAgent = OIDExternalUserAgentASWebAuthSession(with: viewController)
sceneDelegate?.currentAuthorizationFlow = OIDAuthState.authState(byPresenting: request, externalUserAgent: externalAgent,
callback: { authState, error in
handleAuthState(authState, error, completion)
})