Sobes.tech
Junior

Aký je rozdiel medzi Keychain a User Defaults?

sobes.tech AI

Odpoveď od AI

UserDefaults sa používa na ukladanie malých, ne dôverných údajov, ako sú používateľské nastavenia alebo stav aplikácie. Dáta sa ukladajú vo forme párov kľúč-hodnota v súbore .plist a sú dostupné všetkým častiam aplikácie. UserDefaults nešifruje dáta a nie je vhodný na ukladanie kritických informácií.

Keychain sa používa na bezpečné uloženie dôverných údajov, ako sú heslá, certifikáty, tokeny a iné citlivé informácie. Dáta sú šifrované a uložené v špecializovanom úložisku, ku ktorému má prístup iba aplikácia, ktorá ich zaznamenala. Keychain je podporovaný na úrovni operačného systému a zabezpečuje vysokú úroveň ochrany dát.

Kľúčové rozdiely:

Charakteristika UserDefaults Keychain
Účel Ukladanie ne dôverných nastavení Ukladanie dôverných dát (heslá, tokeny)
Bezpečnosť Neobsahuje vstavané šifrovanie Dáta sú šifrované
Prístup Prístupné všetkým častiam aplikácie Prístupné iba aplikácii, ktorá ich zaznamenala
Objem dát Vhodné pre malé objemy dát Vhodné pre malé objemy dôverných dát
Implementácia Jednoduché API, ukladanie do súboru .plist Zložitejšie API, ukladanie do systémového úložiska

Príklad použitia UserDefaults:

// Uloženie hodnoty
UserDefaults.standard.set("dark", forKey: "theme")

// Získanie hodnoty
let theme = UserDefaults.standard.string(forKey: "theme")

Príklad použitia Keychain (vyžaduje prácu s API SecItem alebo obálkami):

// Príklad pridania hesla (zjednodušene, vyžaduje spracovanie chýb a ďalšie parametre)
let password = "mySecretPassword".data(using: .utf8)!
let query: [String: Any] = [
    kSecClass as String: kSecClassGenericPassword,
    kSecAttrAccount as String: "myAccount",
    kSecValueData as String: password
]

let statusAdd = SecItemAdd(query as CFDictionary, nil)
// Spracovanie stavu

// Príklad získania hesla (zjednodušene, vyžaduje spracovanie chýb)
let queryGet: [String: Any] = [
    kSecClass as String: kSecClassGenericPassword,
    kSecAttrAccount as String: "myAccount",
    kSecReturnData as String: kCFBooleanTrue!,
    kSecMatchLimit as String: kSecMatchLimitOne
]

var item: CFTypeRef?
let statusGet = SecItemCopyMatching(queryGet as CFDictionary, &item)

if statusGet == errSecSuccess {
    let retrievedData = item as! Data
    let retrievedPassword = String(data: retrievedData, encoding: .utf8)
    // Použitie hesla
}