Skip to content

Commit

Permalink
FR-19079 added saving the credentials to keychain
Browse files Browse the repository at this point in the history
  • Loading branch information
Diana Khortiuk authored and Diana Khortiuk committed Dec 18, 2024
1 parent 6b5a236 commit c1eef01
Show file tree
Hide file tree
Showing 3 changed files with 57 additions and 20 deletions.
61 changes: 46 additions & 15 deletions Sources/FronteggSwift/FronteggAuth.swift
Original file line number Diff line number Diff line change
Expand Up @@ -208,8 +208,8 @@ public class FronteggAuth: ObservableObject {

let decode = try JWTHelper.decode(jwtToken: accessToken)
let user = try await self.api.me(accessToken: accessToken)


DispatchQueue.main.sync {
self.refreshToken = refreshToken
self.accessToken = accessToken
Expand All @@ -218,26 +218,32 @@ public class FronteggAuth: ObservableObject {
self.appLink = false
self.initializing = false
self.appLink = false


if let email = user?.email {
saveCredentialsToKeychain(email: email, password: "")
} else {
print("❌ Email is nil; cannot save to Keychain")
}

// isLoading must be at the bottom
self.isLoading = false


let offset = calculateOffset(expirationTime: decode["exp"] as! Int)

scheduleTokenRefresh(offset: offset)

}
} catch {
logger.error("Failed to load user data, \(error)")
logger.error("Failed to load user data: \(error)")
DispatchQueue.main.sync {
self.refreshToken = nil
self.accessToken = nil
self.user = nil
self.isAuthenticated = false
self.initializing = false
self.appLink = false

// isLoading must be at the last bottom
self.isLoading = false
}
Expand Down Expand Up @@ -499,7 +505,7 @@ public class FronteggAuth: ObservableObject {
public typealias CompletionHandler = (Result<User, FronteggError>) -> Void

public func login(_ _completion: FronteggAuth.CompletionHandler? = nil, loginHint: String? = nil) {

if(self.embeddedMode){
self.embeddedLogin(_completion, loginHint: loginHint)
return
Expand All @@ -510,12 +516,37 @@ public class FronteggAuth: ObservableObject {
}

let oauthCallback = createOauthCallbackHandler(completion)
let (authorizeUrl, codeVerifier) = AuthorizeUrlGenerator.shared.generate(loginHint: loginHint)
let (authorizeUrl, codeVerifier) = AuthorizeUrlGenerator.shared.generate(loginHint: loginHint)
CredentialManager.saveCodeVerifier(codeVerifier)


WebAuthenticator.shared.start(authorizeUrl, completionHandler: oauthCallback)
}


private func saveCredentialsToKeychain(email: String, password: String) {
let account = email
let service = "com.frontegg.demo" // Unique service identifier for your app

// Prepare Keychain query
let query: [String: Any] = [
kSecClass as String: kSecClassGenericPassword,
kSecAttrAccount as String: account,
kSecAttrService as String: service,
kSecValueData as String: password.data(using: .utf8)!
]

// Delete any existing entry for the account to avoid duplicates
SecItemDelete(query as CFDictionary)

// Add the new item to the Keychain
let status = SecItemAdd(query as CFDictionary, nil)

if status == errSecSuccess {
logger.info("✅ Saved to Keychain successfully for \(email)")
} else {
logger.error("❌ Keychain save error: \(status)")
}
}


Expand Down Expand Up @@ -620,11 +651,11 @@ public class FronteggAuth: ObservableObject {

if let appleConfig = socialConfig.apple, appleConfig.active {
if #available(iOS 15.0, *), appleConfig.customised, !config.useAsWebAuthenticationForAppleLogin {
AppleAuthenticator.shared.start(completionHandler: completion)
await AppleAuthenticator.shared.start(completionHandler: completion)
}else {
let oauthCallback = self.createOauthCallbackHandler(completion)
let url = try await self.generateAppleAuthorizeUrl(config: appleConfig)
WebAuthenticator.shared.start(url, ephemeralSession: true, completionHandler: oauthCallback)
await WebAuthenticator.shared.start(url, ephemeralSession: true, completionHandler: oauthCallback)

}
} else {
Expand Down Expand Up @@ -710,7 +741,7 @@ public class FronteggAuth: ObservableObject {
return urlComponent.url!
}

func loginWithSocialLogin(socialLoginUrl: String, _ _completion: FronteggAuth.CompletionHandler? = nil) {
func loginWithSocialLogin(socialLoginUrl: String, _ _completion: FronteggAuth.CompletionHandler? = nil) {
let completion = _completion ?? { res in

}
Expand Down
6 changes: 3 additions & 3 deletions demo-embedded/demo-embedded/Frontegg.plist
Original file line number Diff line number Diff line change
Expand Up @@ -3,11 +3,11 @@
<plist version="1.0">
<dict>
<key>useAsWebAuthenticationForAppleLogin</key>
<false/>
<key>embeddedMode</key>
<true/>
<key>embeddedMode</key>
<false/>
<key>baseUrl</key>
<string>https://auth.davidantoon.me</string>
<string>https://autheu.davidantoon.me</string>
<key>clientId</key>
<string>04ae2174-d8d9-4a90-8bab-2548e210a508</string>
<key>logLevel</key>
Expand Down
10 changes: 8 additions & 2 deletions demo-embedded/demo-embedded/demo-embedded.entitlements
Original file line number Diff line number Diff line change
Expand Up @@ -8,9 +8,15 @@
</array>
<key>com.apple.developer.associated-domains</key>
<array>
<string>webcredentials:auth.davidantoon.me</string>
<string>applinks:auth.davidantoon.me</string>
<string>webcredentials:autheu.davidantoon.me</string>
<string>applinks:autheu.davidantoon.me</string>
<string>webcredentials:davidantoon.me</string>
</array>
<key>com.apple.developer.authentication-services.autofill-credential-provider</key>
<true/>
<key>keychain-access-groups</key>
<array>
<string>$(AppIdentifierPrefix)com.frontegg.demo</string>
</array>
</dict>
</plist>

0 comments on commit c1eef01

Please sign in to comment.