iOSアプリでデータを端末に保存する方法でよく利用されるのが、UserDefaults
だと思われます。
ただ、UserDefaultsは、アプリを削除するとデータが消えてしまうので、アプリ削除を繰り返すと不正が行われてしまう場合などは、KeyChainを使ってデータを保存した方がいいです。
実装方法
swiftでKeyChainに保存する場合は、以下のようなコードになります。
保存
ViewController.swift
// 保存
func saveKeyChain() {
// 保存する文字列
let str = "hoge"
let data = str.data(using: .utf8)
guard let _data = data else {
return
}
let dic: [String: Any] = [kSecClass as String: kSecClassGenericPassword,
kSecAttrGeneric as String: "key",
kSecAttrAccount as String: "account",
kSecValueData as String: _data]
var itemAddStatus: OSStatus?
// 保存データが存在するかの確認
let matchingStatus = SecItemCopyMatching(dic as CFDictionary, nil)
if matchingStatus == errSecItemNotFound {
// 保存
itemAddStatus = SecItemAdd(dic as CFDictionary, nil)
} else if matchingStatus == errSecSuccess {
// 更新
itemAddStatus = SecItemUpdate(dic as CFDictionary, [kSecValueData as String: _data] as CFDictionary)
} else {
print("保存失敗")
}
// 保存・更新ステータス確認
if itemAddStatus == errSecSuccess {
print("正常終了")
} else {
print("保存失敗")
}
}
取得
ViewController.swift
// 取得
func getKeyChain(key: String) -> String? {
let dic: [String: Any] = [kSecClass as String: kSecClassGenericPassword,
kSecAttrGeneric as String: key,
kSecReturnData as String: kCFBooleanTrue]
var data: AnyObject?
let matchingStatus = withUnsafeMutablePointer(to: &data){
SecItemCopyMatching(dic as CFDictionary, UnsafeMutablePointer($0))
}
if matchingStatus == errSecSuccess {
print("取得成功")
if let getData = data as? Data,
let getStr = String(data: getData, encoding: .utf8) {
return getStr
}
print("取得失敗: Dataが不正")
return nil
} else {
print("取得失敗")
return nil
}
}
削除
ViewController.swift
// 削除
func deleteKeyChain() {
// 削除するqueryを設定
let dic: [String: Any] = [kSecClass as String: kSecClassGenericPassword,
kSecAttrGeneric as String: "key",
kSecAttrAccount as String: "account"]
if SecItemDelete(dic as CFDictionary) == errSecSuccess {
print("削除成功")
} else {
print("削除失敗")
}
}