Skip to content

Commit 2ba8d65

Browse files
chore: refactor
1 parent aa09e91 commit 2ba8d65

3 files changed

Lines changed: 88 additions & 67 deletions

File tree

example/ios/MendixNativeExample/AppDelegate.swift

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,7 @@ class AppDelegate: RCTAppDelegate {
1515
super.application(application, didFinishLaunchingWithOptions: launchOptions)
1616

1717
//Start - For MendixApplication compatibility only, not part of React Native template
18-
NativeCookieModule.restoreSessionCookies()
18+
SessionCookieStore.restore()
1919
MxConfiguration.update(from:
2020
MendixApp.init(
2121
identifier: nil,
@@ -34,11 +34,11 @@ class AppDelegate: RCTAppDelegate {
3434
}
3535

3636
override func applicationDidEnterBackground(_ application: UIApplication) {
37-
NativeCookieModule.persistSessionCookies()
37+
SessionCookieStore.persist()
3838
}
3939

4040
override func applicationWillTerminate(_ application: UIApplication) {
41-
NativeCookieModule.persistSessionCookies()
41+
SessionCookieStore.persist()
4242
}
4343

4444
override func sourceURL(for bridge: RCTBridge) -> URL? {

ios/Modules/NativeCookieModule/NativeCookieModule.swift

Lines changed: 0 additions & 64 deletions
Original file line numberDiff line numberDiff line change
@@ -14,68 +14,4 @@ public class NativeCookieModule: NSObject {
1414
}
1515
SessionCookieStore.clear()
1616
}
17-
18-
public static func persistSessionCookies() {
19-
SessionCookieStore.persist()
20-
}
21-
22-
public static func restoreSessionCookies() {
23-
SessionCookieStore.restore()
24-
}
25-
26-
final class SessionCookieStore {
27-
28-
private static let bundleIdentifier = Bundle.main.bundleIdentifier ?? "com.mendix.app"
29-
private static let storageKey = bundleIdentifier + "sessionCookies"
30-
private static let queue = DispatchQueue(label: bundleIdentifier + ".session-cookie-store", qos: .utility)
31-
32-
// MARK: - Public API
33-
public static func restore() {
34-
35-
guard
36-
let data = UserDefaults.standard.data(forKey: storageKey),
37-
let cookies = try? NSKeyedUnarchiver.unarchivedObject(ofClasses: [NSArray.self, HTTPCookie.self], from: data) as? [HTTPCookie]
38-
else {
39-
NSLog("SessionCookieStore: No cookies to restore")
40-
return
41-
}
42-
43-
let storage = HTTPCookieStorage.shared
44-
let existing = Set(storage.cookies ?? [])
45-
46-
cookies.filter { !existing.contains($0) }.forEach { storage.setCookie($0) }
47-
48-
// Clear stored cookies after restoration to avoid any side effects
49-
clear()
50-
}
51-
52-
public static func persist() {
53-
queue.async {
54-
55-
let cookies = HTTPCookieStorage.shared.cookies ?? []
56-
let sessionCookies = cookies.filter { isSessionCookie($0) }
57-
58-
guard !sessionCookies.isEmpty else {
59-
clear()
60-
NSLog("SessionCookieStore: Clear existing session cookies from storage")
61-
return
62-
}
63-
64-
do {
65-
let data = try NSKeyedArchiver.archivedData(withRootObject: sessionCookies, requiringSecureCoding: false)
66-
UserDefaults.standard.set(data, forKey: storageKey)
67-
} catch {
68-
NSLog("SessionCookieStore: Failed to persist session cookies: \(error.localizedDescription)")
69-
}
70-
}
71-
}
72-
73-
public static func clear() {
74-
UserDefaults.standard.removeObject(forKey: storageKey)
75-
}
76-
77-
public static func isSessionCookie(_ cookie: HTTPCookie) -> Bool {
78-
return cookie.expiresDate == nil
79-
}
80-
}
8117
}
Lines changed: 85 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,85 @@
1+
import Foundation
2+
3+
public class SessionCookieStore {
4+
5+
// MARK: - Private properties
6+
private static let bundleIdentifier = Bundle.main.bundleIdentifier ?? "com.mendix.app"
7+
private static let storageKey = bundleIdentifier + "sessionCookies"
8+
private static let queue = DispatchQueue(label: bundleIdentifier + ".session-cookie-store", qos: .utility)
9+
10+
// MARK: - Public API
11+
public static func restore() {
12+
13+
guard let cookies = get(key: storageKey) else {
14+
NSLog("SessionCookieStore: No cookies to restore")
15+
return
16+
}
17+
18+
let storage = HTTPCookieStorage.shared
19+
let existing = Set(storage.cookies ?? [])
20+
cookies.filter { !existing.contains($0) }.forEach { storage.setCookie($0) }
21+
22+
clear() // Clear stored cookies after restoration to avoid any side effects
23+
}
24+
25+
public static func persist() {
26+
queue.async {
27+
let sessionCookies = HTTPCookieStorage.shared.cookies?.filter { isSessionCookie($0) } ?? []
28+
guard !sessionCookies.isEmpty else {
29+
clear()
30+
NSLog("SessionCookieStore: Clear existing session cookies from storage")
31+
return
32+
}
33+
set(key: storageKey, cookies: sessionCookies)
34+
}
35+
}
36+
37+
public static func clear() {
38+
clear(key: storageKey)
39+
}
40+
41+
// MARK: - Private API
42+
private static func isSessionCookie(_ cookie: HTTPCookie) -> Bool {
43+
return cookie.expiresDate == nil
44+
}
45+
46+
private static func set(key: String, cookies: [HTTPCookie]) {
47+
do {
48+
let data = try NSKeyedArchiver.archivedData(withRootObject: cookies, requiringSecureCoding: false)
49+
let storeQuery = [kSecClass: kSecClassGenericPassword, kSecAttrAccount: key, kSecValueData: data] as CFDictionary
50+
SecItemDelete(storeQuery)
51+
let status = SecItemAdd(storeQuery, nil)
52+
if status != noErr {
53+
NSLog("SessionCookieStore: Failed to persist session cookies with status: \(status)")
54+
}
55+
} catch {
56+
NSLog("SessionCookieStore: Failed to persist session cookies: \(error.localizedDescription)")
57+
}
58+
}
59+
60+
private static func get(key: String) -> [HTTPCookie]? {
61+
do {
62+
let query: [CFString: Any] = [kSecClass: kSecClassGenericPassword, kSecAttrAccount: key, kSecReturnData: true]
63+
var item: CFTypeRef?
64+
let status = SecItemCopyMatching(query as CFDictionary, &item)
65+
if status == errSecSuccess, let data = item as? Data {
66+
let cookies = try NSKeyedUnarchiver.unarchivedObject(ofClasses: [NSArray.self, HTTPCookie.self], from: data) as? [HTTPCookie]
67+
return cookies
68+
} else {
69+
NSLog("SessionCookieStore: No session cookies found with status: \(status)")
70+
return nil
71+
}
72+
} catch {
73+
NSLog("SessionCookieStore: Failed to retrieve session cookies: \(error.localizedDescription)")
74+
return nil
75+
}
76+
}
77+
78+
private static func clear(key: String) {
79+
let query = [kSecClass: kSecClassGenericPassword, kSecAttrAccount: key, kSecReturnData: true] as CFDictionary
80+
let status = SecItemDelete(query)
81+
if status != errSecSuccess {
82+
NSLog("SessionCookieStore: Failed to clear cookies with status: \(status)")
83+
}
84+
}
85+
}

0 commit comments

Comments
 (0)