Keychain iOS-da: nədir, arxitektura və sirlərlə iş

Müəllif: IT Sectr Dərc olunub: 2026-04-04 Oxuma vaxtı: 9 dəq

Keychain (Açar zənciri) — iOS-da şifrələr, kriptoqrafik açarlar, sertifikatlar və məxfi qeydlərin təhlükəsiz saxlanması üçün nəzərdə tutulmuş qorunan anbardır. Apple Security Documentation (2025)-ya görə, Keychain A7 çipi və daha yeni olan bütün cihazlarda Secure Enclave vasitəsilə aparat şifrələməsindən istifadə edir. iOS Keychain arxitekturasını başa düşmək hər bir tətbiq inkişaf etdiricisi üçün tokenləri və tətbiq sirlərini düzgün saxlamaq üçün vacibdir.

Başlıca

  • iOS Keychain — Secure Enclave vasitəsilə aparat qoruması ilə sirləri saxlamaq üçün şifrələnmiş SQLite verilənlər bazası.
  • Protection Class məlumatların nə vaxt əlçatan olduğunu müyyənləşdirir: cihaz açıq olduqda, ilk açılışdan sonra və ya həmişə.
  • Access Control List (ACL) — biometrik autentifikasiya da daxil olmaqla Keychain elementlərinə girişi məhdudlaşdıran mexanizm.
  • SecItemAdd və SecItemCopyMatching — elementləri yazmaq və oxumaq üçün Security framework-ün əsas API-ləri.
  • kSecAttrSynchronizable — istifadəçinin bütün cihazlarında giriş üçün Keychain-in iCloud vasitəsilə sinxronizasiyasına icazə verən bayraq.

iOS-da Keychain nədir?

iOS Keychain — Apple əməliyyat sisteminə daxil edilmiş məxfi məlumatların qorunan saxlama mexanizmidir. UserDefaults və ya adi fayllardan fərqli olaraq, Keychain bütün elementləri aparat səviyyəsində şifrələyir və təhlükəsizlik siyasətlərinə əsaslanan incə giriş nəzarəti təmin edir.

Keychain iOS 2.0-da təqdim edildi və o vaxtdan bəri əhəmiyyətli dəyişikliklərə məruz qaldı: iOS 7-də Secure Enclave vasitəsilə aparat açarları dəstəyi, iOS 9-da Access Groups vasitəsilə tətbiqlər arasında Keychain bölgüsü, iOS 13-də isə LAContext vasitəsilə biometrik bağlama dəstəyi əlavə edildi. Apple WWDC Session (2024) məlumatlarına görə, App Store top 100-dəki iOS tətbiqlərinin 90%-dən çoxu autentifikasiya tokenlərini saxlamaq üçün Keychain-dən istifadə edir.

Arxitektura baxımından Keychain tətbiqin sandboxundan kənarda yerləşən şifrələnmiş SQLite verilənlər bazasıdır. Hər bir element (SecItem) ayrı bir açarla şifrələnir, bu açar isə öz növbəsində Secure Enclave-in aparat açarı tərəfindən qorunur. Sistem xidməti Securityd tətbiqin hüquqlarına (entitlements) və tələb olunan qoruma sinfinə əsaslanaraq Keychain-ə girişi idarə edir.

Keychain-in digər saxlama üsullarına nisbətən mühüm üstünlüyü: məlumatlar avtomatik olaraq ƏS tərəfindən şifrələnir və deşifrələnir. Tətbiq inkişaf etdiricisi kriptoqrafiyanı əllə hüyata keçirməli deyil — sadəcə düzgün parametrlərlə SecItemAdd-i çağırmaq kifayətdir. iOS, Access Groups-un düzgün konfiqurasiyası ilə Keychain-dən olan məlumatların digər tətbiqlər tərəfindən oxuna bilməyəcəyinə zəmanət verir.

Keychain arxitekturası

Keychain arxitekturası bir neçe səviyyəni əhatə edir: fiziki (Secure Enclave), sistem (Security.framework), tətbiq (API SecItem*) və məntiqi (Access Groups, Protection Classes). Hər səviyyəni başa düşmək sirlərin saxlanmasını düzgün planlaşdırmağa kömək edir.

SecItemAdd və SecItemCopyMatching

Keychain ilə işləmək üçün əsas API Security framework funksiyalarıdır: əlavə etmək üçün SecItemAdd, oxumaq üçün SecItemCopyMatching, yeniləmək üçün SecItemUpdate və silmək üçün SecItemDelete. Hər bir funksiya axtarılan və ya saxlanılan elementin atributlarını təsvir edən query lüğəti qəbul edir.

Query-in əsas atributları: kSecClass — element növü (kSecClassGenericPassword, kSecClassKey, kSecClassCertificate), kSecAttrAccount — sinif daxilində unikal identifikator, kSecValueData — saxlanılan məlumatlar (Data), kSecAttrAccessible — qoruma sinfi. SecItemCopyMatching kSecReturnData bayrağı ilə elementin məlumatlarını, kSecMatchLimit ilə isə nəticələrin sayını qaytarır.

Vacibdir: bütün funksiyalar OSStatus statusu qaytarır. Uğurlu əməliyyat errSecSuccess (0) qaytarır. Xətalarlar: errSecItemNotFound (-25300) — element tapılmadı, errSecDuplicateItem (-25299) — element artıq mövcuddur, errSecAuthFailed (-25293) — biometrik autentifikasiya keçilmədi. Tətbiq inkişaf etdiricisi hər bir statusu düzgün idarə etməlidir.

Qoruma sinifləri (Protection Class)

Protection Class — Keychain-dəki məlumatların nə vaxt oxumaq üçün əlçatan olduğunu müyyənləşdirən kSecAttrAccessible atributudur. iOS müxtəlif səviyyəli əlçatanlıq və təhlükəsizliklə altı qoruma sinfini dəstəkləyir.

Əksər ssenarilər üçün tövsiyə olunan sinif kSecAttrAccessibleWhenUnlockedThisDeviceOnly-dir: məlumatlar yalnız cihaz açıq olduqda əlçatandır və iCloud Backup-a kopyalanmır. Yenidən başlatmadan sonra əlçatan olmalı (lakin yalnız ilk açılışdan sonra) məlumatlar üçün kSecAttrAccessibleAfterFirstUnlockThisDeviceOnly istifadə edin. Hər girişdə biometrik autentifikasiya tələb edən kritik məlumatlar üçün kSecAttrAccessibleWhenUnlockedThisDeviceOnly-ni biometriya tələb edən ACL ilə birləşdirin.

ThisDeviceOnly şəkilçisi olmayan siniflər (kSecAttrAccessibleWhenUnlocked, kSecAttrAccessibleAfterFirstUnlock) iCloud Backup-a kopyalanmağa icazə verir. Bu istifadəçi üçün rahatdır, lakin təhlükəsizliyi azaldır — məlumatlar ehtiyat nüsxədən bərpa edilə bilər. Autentifikasiya tokenləri üçün həmişə ThisDeviceOnly istifadə edin.

Access Control Lists (ACL)

Access Control List (ACL) — istifadəçinin autentifikasiyasına əsaslanaraq Keychain elementi ilə əməliyyatları məhdudlaşdıran mexanizmdir. ACL SecAccessControlCreateWithFlags vasitəsilə yaradılır və elementi saxlayarkən kSecAttrAccessControl atributuna ötürülür.

Dəstəklənən bayraqlar: kSecAccessControlUserPresence — istənilən autentifikasiya (Face ID, Touch ID və ya parol kodu), kSecAccessControlBiometryCurrentSet — yalnız biometriya (hazırda qeydiyyatdan keçmiş barmaq izləri və ya üz), kSecAccessControlDevicePasscode — yalnız parol kodu. ACL hər əməliyyata tətbiq edilir: elementin oxunması, yenilənməsi və silinməsi də autentifikasiya tələb edir.

iOS 15+-də kSecAccessControlWatch bayrağı əlavə edildi — Apple Watch üçün, cütləşdirilmiş saat vasitəsilə autentifikasiyaya icazə verir. ACL birləşdirilə bilər: məsələn, kSecAccessControlUserPresence və ya kSecAccessControlBiometryAny seçimli parol kodu ilə (.or oriyentasiyası).

Keychain-də məlumat növləri

iOS Keychain dörd əsas element sinfini (kSecClass) dəstəkləyir, hər biri öz məlumat növü üçün nəzərdə tutulmuşdur. Sinifin düzgün seçimi elementlərin təşkilini və axtarışını sadələşdirir.

kSecClassGenericPassword — ümumi şifrə: ən çox istifadə edilən sinif. Unikal açarla (kSecAttrAccount) istənilən ikili məlumatları (Data) saxlayır. Tokenlər, API açarları, PIN-kodlar üçün uyğundur. İstifadə üçün əlavə hüquqlar (entitlements) tələb etmir.

kSecClassInternetPassword — internet şifrəsi: şəbək resursu ilə əlaqəli məlumatları saxlayır. Əlavə atributlar: kSecAttrServer (server domeni), kSecAttrProtocol (https, ftp), kSecAttrPort, kSecAttrAuthenticationType. iOS AutoFill vasitəsilə belə şifrələri avtomatik doldura bilər.

kSecClassKey — kriptoqrafik açar: şifrələmə açarlarının (AES, RSA, EC) saxlanması üçün. Açar Data kimi deyil, SecKeyRef kimi saxlanılır. kSecClassCertificate — rəqəmsal sertifikatların saxlanması və yoxlanması üçün X.509 sertifikatı. Hər iki sinif kriptoqrafik əməliyyatların başa düşülməsini və atributların düzgün konfiqurasiyasını tələb edir.

Praktikada mobil tətbiqlərdə Keychain istifadəsinin 95% halları autentifikasiya tokenlərinin saxlanması üçün kSecClassGenericPassword və şəxsi şifrələmə açarlarının saxlanması üçün kSecClassKey ilə əhatə olunur. kSecClassCertificate nadir hallarda istifadə olunur — adətən öz PKI-si olan korporativ tətbiqlərdə.

Kod nümunələri: Swift-də Keychain ilə iş

Keychain ilə Swift-də Security framework-dan istifadə edərək praktiki nümunələri nəzərdən keçirək. Hər bir nümunə xəta idarəetməsi və Protection Class-ın düzgün konfiqurasiyasını ehtiva edir.

Tokenin saxlanması və oxunması

Əsas nümunə autentifikasiya tokenini WhenUnlockedThisDeviceOnly qoruması ilə Keychain-də saxlayır. Açar (kSecAttrAccount) xidmət identifikatorudur, məlumatlar (kSecValueData) isə Data formatında tokendir.

swift
import Security

enum KeychainError: Error {
    case unexpectedStatus(OSStatus)
}

func saveToken(token: String, service: String) throws {
    let data = Data(token.utf8)
    let query: [String: Any] = [
        kSecClass as String: kSecClassGenericPassword,
        kSecAttrService as String: service,
        kSecAttrAccount as String: "auth_token",
        kSecValueData as String: data,
        kSecAttrAccessible as String:
            kSecAttrAccessibleWhenUnlockedThisDeviceOnly
    ]
    SecItemDelete(query as CFDictionary)
    let status = SecItemAdd(query as CFDictionary, nil)
    guard status == errSecSuccess else {
        throw KeychainError.unexpectedStatus(status)
    }
}

func readToken(service: String) throws -> String {
    let query: [String: Any] = [
        kSecClass as String: kSecClassGenericPassword,
        kSecAttrService as String: service,
        kSecAttrAccount as String: "auth_token",
        kSecReturnData as String: true,
        kSecMatchLimit as String: kSecMatchLimitOne
    ]
    var result: AnyObject?
    let status = SecItemCopyMatching(
        query as CFDictionary, &result
    )
    guard status == errSecSuccess,
        let data = result as? Data else {
        throw KeychainError.unexpectedStatus(status)
    }
    return String(decoding: data, as: UTF8.self)
}

Biometrik bağlama ilə saxlama

Nümunə açarı biometriyaya bağlamaq üçün SecAccessControlCreateWithFlags istifadəsini göstərir. Elementə hər giriş Face ID və ya Touch ID tələb edəcək.

swift
import LocalAuthentication

func saveWithBiometry(data: Data, key: String) throws {
    let accessControl = SecAccessControlCreateWithFlags(
        nil,
        kSecAttrAccessibleWhenUnlockedThisDeviceOnly,
        .biometryCurrentSet,
        nil
    )

    let query: [String: Any] = [
        kSecClass as String: kSecClassGenericPassword,
        kSecAttrAccount as String: key,
        kSecValueData as String: data,
        kSecAttrAccessControl as String: accessControl as Any
    ]

    SecItemDelete(query as CFDictionary)
    let status = SecItemAdd(query as CFDictionary, nil)
    guard status == errSecSuccess else {
        throw KeychainError.unexpectedStatus(status)
    }
}

Tətbiqlər arasında Keychain Sharing

Nümunə eyni tətbiq inkişaf etdiricisinin tətbiqləri arasında Keychain-ə ümumi giriş üçün Access Group konfiqurasiyasını göstərir. keychain-access-groups entitlement tələb edir.

swift
// Capabilities: Keychain Sharing aktivdir
// App IDs: group.com.example.shared

func saveSharedToken(token: Data) {
    let query: [String: Any] = [
        kSecClass as String: kSecClassGenericPassword,
        kSecAttrAccount as String: "shared_token",
        kSecValueData as String: token,
        kSecAttrAccessGroup as String:
            "group.com.example.shared",
        kSecAttrAccessible as String:
            kSecAttrAccessibleWhenUnlockedThisDeviceOnly
    ]
    SecItemAdd(query as CFDictionary, nil)
}

Keychain ilə işləmək üçün ən yaxşı təcrübələr

iOS Keychain-dən düzgün istifadə tipik zəifliklərin və məlumat itkisinin qarşısını alan bir neçə əsas qaydaya riayət etməyi tələb edir.

Bütün autentifikasiya sirləri üçün ThisDeviceOnly istifadə edin: kSecAttrAccessibleWhenUnlockedThisDeviceOnly tokenlərin iCloud Backup-a düşməyəcəyinə zəmanət verir. Əgər təcavüzçü ehtiyat nüsxəyə çıxış əldə edərsə, bu bayraqlı Keychain məlumatları əlçatan olmayacaq. İstisna, istifadəçinin bütün cihazlarında əlçatan olmalı məlumatlardır (məsələn, öz xidmətləri üçün şifrələmə açarları), bunlar üçün kSecAttrAccessibleWhenUnlocked-u kSecAttrSynchronizable ilə istifadə edin.

Xam şifrələri saxlamayın — heşləri və ya sessiya tokenlərini saxlayın. Apple Security Guide (2025) istifadəçinin şifrəsinin Keychain-də açıq mətndə saxlanmasını qətiyyənlə tövsiyə etmir. Bunun əvəzinə, OAuth 2.0 vasitəsilə uğurlu autentifikasiyadan sonra serverdən alınan refresh tokeni saxlayın. Şifrə yalnız token əldə etmək üçün istifadə olunur və dərhal yaddaşdan silinir.

Keychain xətalarını düzgün idarə edin: Keychain ilə hər əməliyyat yoxlanılmalı olan OSStatus qaytarır. Xüsusilə diqqət edilməli olanlar: errSecItemNotFound (token müddəti bitib və ya silinib) və errSecAuthFailed (biometriya keçilmədi). Birinci halda tətbiq yeni autentifikasiya tələb etməli, ikincidə — istifadəçiyə alternativ üsul göstərməlidir (parol kodu). Heç vaxt errSecItemNotFound statusuna məhəl qoymayın — bu, nil oxumağa cəhd edərkən tətbiqin çökməsinə səbəb olacaq.

Keychain-i real cihazda test edin: simulatorun Secure Enclave-ı yoxdur və biometrik ACL-ləri dəstəkləmir. Həmişə ssenariləri yoxlayın: ilk işə salma, ehtiyat nüsxədən bərpa, cihaz parolunun dəyişdirilməsi, tətbiqin silinməsi və yenidən quraşdırılması. Real cihazda Keychain tətbiq silindikdən sonra qorunur, ancaq kSecAttrAccessibleWhenPasscodeSetThisDeviceOnly bayrağı istifadə edilməyibsə — bu bayraq parol kodu silindikdə təmizlənir.

Keychain əməliyyatlarının sayını minimuma endirin: hər oxu və ya yazma əməliyyatı axını bloklaya bilən Securityd sistem xidmətinə müraciətdir. Oxunmuş tokenləri sessiya müddətincə yaddaşda keşləyin və Keychain-ə yalnız tətbiq yenidən başladıqda və ya autentifikasiya xətası (serverdən 401) olduqda yenidən müraciət edin. iOS cihaz bağlandıqda Keychain-i avtomatik bloklayır, buna görə də LAContext vasitəsilə biometriya tələbi ilə oxumağı planlaşdırın.

Tez-tez verilən suallar

Keychain-də məlumatları saxlamaq və yenidən başlatmadan sonra oxumaq olarmı?

Bəli, kSecAttrAccessibleAfterFirstUnlockThisDeviceOnly və ya kSecAttrAccessibleAfterFirstUnlock qoruma sinifindən istifadə edin. Məlumatlar yenidən başlatmadan sonra cihazın ilk açılışından etibarən əlçatan olacaq. Tətbiq işə salındıqda avtomatik giriş üçün (açılışı gözləmədən) kSecAttrAccessibleAlways istifadə edin, lakin bu təhlükəsizliyi azaldır.

İstifadəçi çıxış etdikdə Keychain-i necə təmizləmək olar?

Hər məlumat növü üçün kSecClass ehtiva edən query ilə SecItemDelete-i çağırın. Tətbiqin bütün elementlərini tam təmizləmək üçün bunu edin: SecItemDelete([kSecClass as String: kSecClassGenericPassword] as CFDictionary). kSecClassKey, kSecClassCertificate və kSecClassInternetPassword üçün təkrarlayın.

kSecAttrAccessible və kSecAttrAccessControl arasındakı fərq nədir?

kSecAttrAccessible məlumatların nə vaxt əlçatan olduğunu müyyənləşdirir (açılışda, ilk açılışdan sonra və s.). kSecAttrAccessControl kimin giriş əldə edə biləcəyini müyyənləşdirir (biometriya, parol kodu, istənilən autentifikasiya). Onlar birləşdirilir: əvvəlcə Protection Class, sonra ACL. Məsələn, məlumatlar yalnız açılışda Və yalnız Face ID-dən sonra əlçatandır.

Niyə SecItemCopyMatching errSecItemNotFound qaytarır?

Səbəblər: element heç vaxt saxlanmayıb, element parol kodu silindikdə təmizlənib (kSecAttrAccessibleWhenPasscodeSet istifadə edilibsə), tətbiq yenidən quraşdırılıb (Keychain qorunur, lakin yeni cihazda ehtiyat nüsxədən bərpa edilmir), Access Group və ya tətbiq inkişaf etdiricisi identifikatoru dəyişib. kSecAttrService və kSecAttrAccount-u yoxlayın.

Cihazın Keychain-də biometriyanı dəstəklədiyini necə yoxlamaq olar?

LocalAuthentication-dan LAContext istifadə edin: context.canEvaluatePolicy(.deviceOwnerAuthenticationWithBiometrics, error: nil) çağırın. Əgər true qaytarırsa — cihaz Touch ID və ya Face ID dəstəkləyir. Keychain ACL üçün biometryCurrentSet (yalnız cari biometrik məlumatlar) və ya biometryAny (əvvəllər qeydiyyatdan keçmiş istənilən) bayrağından istifadə edin.

Nəticə

  • iOS Keychain — Secure Enclave vasitəsilə şifrələmə və ACL vasitəsilə giriş nəzarəti ilə sirlərin aparat qorumalı anbarı.
  • Security framework elementlərlə işləmək üçün SecItemAdd, SecItemCopyMatching, SecItemUpdate və SecItemDelete funksiyalarını təmin edir.
  • Protection Class (kSecAttrAccessible) ssenari əsasında seçilir: WhenUnlockedThisDeviceOnly tokenlər üçün standartdır.
  • Biometrik ACL (kSecAttrAccessControl) hər oxu əməliyyatı üçün Face ID və ya Touch ID tələbi əlavə edir.
  • kSecClassGenericPassword 95% halları əhatə edir — tokenlərin, API açarlarının, PIN-kodların və qeydlərin saxlanması.
  • ThisDeviceOnly sirlərin iCloud Backup-a kopyalanmasının qarşısını alır — autentifikasiya tokenləri üçün məcburidir.
  • OSStatus-un düzgün idarə edilməsi və real cihazda test etmə Keychain ilə etibarlı iş üçün məcburi təcrübələrdir.

Açar təslim mobil tətbiq hazırlayacağıq

IT Sectr 2017-ci ildən startaplar və bizneslər üçün iOS və Android tətbiqləri yaradır. Sizə məsləhət verəcəyik və ən yaxşı həlli təklif edəcəyik.

Layihəni müzakirə et

Həm də oxuyun