OAuth 기반 서버에서 인증이 필요한 API를 호출할 경우 Access Token을 사용해서 호출하는데, 해당 Access Token 을 발급받았을 경우 어디에 저장을 할까?
UserDefaults 나 다른 방법을 이용하는 경우에는, 암호화 과정이 거쳐지지 않아서 좋지 않다
이럴 경우 KeyChain을 활용한다
키체인은 사용자의 Mac, 앱, 서버 및 웹 사이트 계정과 암호 및 신용 카드 번호 또는 은행계좌 PIN 번호와 같은 중요 정보를 암호화하여 안전하게 저장한다
Securely store small chunks of data on behalf of the user
The keychain services API helps you solve this problem by giving your app a mechanism to store small bits of user data in an encrypted database called a keychain. When you securely remember the password for them, you free the user to choose a complicated one.
키 체인은 애플 계열의 운영체제에서 동작하는 다양한 응용 프로그램에서 비밀번호나 계정 등 보안이 필요한 요소를 저장하는데 사용되는 암호화된 저장소이다. iOS뿐만 아니라, macOS, tvOS, watchOS 등에서도 모두 제공된다. 사용하는 곳이 생각보다 많아서, iCloud의 로그인 정보가 키 체인을 통해 관리되고 있고, 와이파이의 패스워드도 키 체인에 저장되며, 사파리에서 웹 사이트별 패스워드를 관리할 때에도 키 체인이 사용된다
ref) https://developer.apple.com/documentation/security/keychain_services
샌드박스
외부에서 받은 파일을 바로 실행하지 않고 보호된 영역에서 실행시켜 봄으로써 잘못된 파일과 프로그램이 내부시스템 전체에 악영향을 주는지 확인하는 기술. 이를 확장해서 iOS에서는 애플리케이션 간에 데이터 공유가 불가능하도록 격리된 각자의 샌드박스 공간을 제공하는데, iOS 시스템 자체에는 파일을 함부로 쓸 수 없지만 샌드박스 내에서는 파일 쓰기가 허용된다
-> 망할거면 혼자 망해라 식으 운영 방법
An encoder that stores an object’s data to an archive referenced by keys.
An interface to the user’s defaults database, where you store key-value pairs persistently across launches of your app.
Persist or cache data on a single device, or sync data to multiple devices with CloudKit.
In iOS, apps have access to a single keychain (which logically encompasses the iCloud keychain). This keychain is automatically unlocked when the user unlocks the device then locked when the device is locked. An app can access only its own keychain items, or those shared with a group to which the app belongs. It can't manage the keychain container itself.
In macOS, however, the system supports an arbitrary number of keychains. You typically rely on the user to manage these with the Keychain Access app and work implicitly with the default keychain, much as you would in iOS. Nevertheless, the keychain services API does provide functions that you can use to manipulate keychains directly. For example, you can create and manage a keychain that is private to your app. On the other hand, robust access control mechanisms typically make this unnecessary for anything other than an app trying to replicate the keychain access utility.
But, iOS에서는 모든 앱에서 사용할 수 있는 하나의 키 체인만 사용한다
kSecClassInternetPassword
kSecClassCertificate
kSecClassGenericPassword
등이 있습니다키 체인 아이템을 정의할 때에는 저장할 데이터에 맞는 아이템 클래스를 선택해야 한다. 각 아이템 클래스는 저장값의 특성에 따라 서로 다른 어트리뷰트를 제공하기 때문에...
예를 들자면)
kSecClassGenericPassword
라는 아이템 클래스를 통해서 인증 토큰을 저장하려고 하는데, 여기에는 핵심 어트리뷰트가 kSecAttrAccount / kSecAttrService
가 있다
그래서 키 체인은 이 두개의 어트리뷰트를 메인 키로 하여 저장된 비밀번호를 식별한다.
상수의 의미로 표현되는것 (변하지 않는 값) https://green1229.tistory.com/56
Core Foundation 등의 Core Framework 헤더파일들을 보면, 헝가리언 네이밍 규칙을 따른 흔적들을 제법 볼 수 있다. 일단 'k' 는 헝가리언 네이밍에 따라 사용된 걸로 보인다. Constants 의 'c' 는 이미 헝가리안에서 'char' 의 'c' 로 예약이 되어 있는 상황이니 중복을 피하기 위해 동일한 발음기호인 'k' 를 사용한 것으로 추측된다. Core Foundation 의 역사를 고려하면 헝가리언 네이밍을 따른것이 어느정도 이해가 된다.
https://metalkin.tistory.com/20
CoreFoundation
앞에서 말했듯이, KeyChain은 파일 시스템에 저장된 데이터베이스와 크게 다를 것이 없는데, 그래서 데이터베이스의 핵심인 CRUD에 크게 벗어나지 않는다. 그러니깐, 이것에 대응되는 메소드가 쓰인다는 것이겠지??
위 메소드들은 모두 C스타일로 코딩되어 있으며, 키 체인 쿼리
라고 불리는 CFDictionary 타입의 데이터 집합을 인자값으로 받아 사용합니다. 데이터베이스로 치자면 테이블과 키 값, 저장할 내용 등이 모두 어우러진 SQL문에 해당하는 셈이다. 우리는 저장할 데이터, 아이템 클래스, 서비스명 등을 키 체인 쿼리에 정의한 다음, 목적에 맞는 함수를 호출하면 원하는 CRUD 작업을 처리하게 됩니다.
import Foundation
import Security
let keyChainQuery: NSDictionary = [
kSecClass: <아이템 클래스>,
kSecAttrService: <서비스 아이디>,
kSecAttrAccount: <사용자 계정>,
kSecValueData: <저장할 값>
]
//기존에 저장된 값 삭제해주기
SecItemDelete(keyChainQuery)
//새로운 값 추가
SecItemAdd(keyChainQuery, nil)