iOS 개발/Swift
[Swift] appDelegate 참조 안전하게 하기
스닥
2021. 11. 10. 20:48
우리는 종종 App delegate에서 선언된 instance들을 사용해야 할 때가 있다.
보통은 다음과 같이 강제추출을 사용하게 된다.
UIApplication.shared.delegate as! AppDelegate
하지만, 우리의 두뇌에서 괜찮다고 외쳐도 강제추출을 쓰는 것은 좋지 않다.
(사바사 상바상 이라고는 하지만, 멘토님께 쓰지 않는 습관을 들이는게 좋다고 배웠다.)
설명은 다음의 persistentContainer를 가져오는 예시를 통해서 하겠다.
App Delegate 에는 persistentContainer가 다음과 같이 선언되어 있을 것이다.
import UIKit
import CoreData
@main
class AppDelegate: UIResponder, UIApplicationDelegate {
............
lazy var persistentContainer: NSPersistentContainer = {
let container = NSPersistentContainer(name: "Canvas")
container.loadPersistentStores(completionHandler: { (storeDescription, error) in
if let error = error as NSError? {
fatalError("Unresolved error \(error), \(error.userInfo)")
}
})
return container
}()
............
}
여기 있는 persistentContainer를 다른 view나 controller, 혹은 object에서 어떻게 사용할 수 있을까?
보통은 다음과 같이 사용한다.
private let pContatiner = (UIApplication.shared.delegate as! AppDelegate).persistentContainer
하지만 pContainer를 미리 만들어놓고,
Class의 init이나, Controller의 viewDidLoad 같은 곳에서 가져오는 방식으로 강제추출을 피할 수 있다.
Class의 경우
class handleCoreData {
private var pContainer: NSPersistentContainer?
init() {
if let appDelegate = UIApplication.shared.delegate as? AppDelegate {
pContainer = appDelegate.persistentContainer
}
}
}
Controller의 경우
class ViewController: UIViewController {
private var pContainer: NSPersistentContainer?
override func viewDidLoad() {
super.viewDidLoad()
if let appDelegate = UIApplication.shared.delegate as? AppDelegate {
pContainer = appDelegate.persistentContainer
}
}
}