ABOUT ME

-

Today
-
Yesterday
-
Total
-
  • iOS) CoreData - perform 메소드
    iOS 2021. 1. 31. 13:32

    출처: www.kairadiagne.com/2019/01/06/understanding-the-core-data-perform-methods.html 

     

    Understanding the Core Data perform methods

    Core Data is controversial to many developers. Some love it while others think it is too difficult or that it contains too many bugs. Personally I enjoy using Core Data. Out of the box it provides a lot of functionality needed for managing the model layer

    www.kairadiagne.com

    위 링크를 번역한 문서입니다.

     

    Core Data는 많은 개발자들 사이에서 논쟁의 여지가 많다. 누군가는 좋아하지만 다른 누군가는 사용하기 어렵고 버그가 많다고 생각한다.

    Core Data는 별도의 설치 필요 없이 대부분의 app의 모델 계층을 다루는데 필요한 많은 기능들을 제공한다. 또한 애플의 공식적인 지원으로 인해 프로젝트를 다른 서드파티에 의존하지 않아도 된다.

     

    그러나 Core Data를 배우는데 있어서 Learing Curve가 높다고 생각한다. 이번 주의 포스트는 perform(_:)과 performAndWait(_:) api이다.

     

    Core Data in a nutshell 코어 데이터 둘러보기

    Core Data안의 모든 model object는 NSManagedObject의 서브 클래싱이다. 당신은 일반적으로 NSManagedObjectContext를 통해 객체에 접근할 것이다. 이는 scratchpad의 manged object를 CRUD 하고 객체의 변화를 persistent store에 저장하는 기능과 비슷하다.

    Persistent Store은 managed object들이 저장되는 저장소이다. 대부분 persistent store은 SQLite 데이터 베이스이다.

     

    NSManagedObjectContext Concurrency policies 동시성 정책

    Managed Object Context는 시리얼 큐에 묶여있어서 context에 있는 모든 작업이 순서대로 실행되는 것을 보장하므로 데이터의 일관성을 유지한다. 그러므로 중요하게 기억해야 할 것은 'context와 context의 managed object에 접근할 때 항상 자체의 queue에 액세스 해야 한다'는 것이다.. context에 사용되는 queue는 ConcurrencyType에 달려있다.

     

    NSPrivateQueueConcurrencyType의 context는 고유의 backgournd queue를 가지고 있다. 이 타입의 context는 일반적으로 backgourd queue 혹은 private context라고 하는데 예를 들면 대규모 JSON 응답을 persistent store에 import 할 때 main queue를 block 할 수 있다. 

     

    NSMainQueueConcurrencyType의 컨텍스트는 고유의 queue가 없지만 대신 어플리케이션의 main queue와 연결된다. NSpersistentContainer라는 타입의 context를 'view context' 라고 부르고 일반적으로 어플리케이션의 UI에 사용된다.

     

    앞선 내용들이 모두 간단하지 않은가? 그러나 context에 사용되는 queue는 private이다. 그렇다면 어떻게 고유한 queue에서만 context에 접근할 수 있도록 보장하는가? 여기서 perform(_:)과 performAndWait(_:) 메서드가 등장한다. 메서드 내부에서 랩핑된 작업은 context queue에서 실행된다(즉, 메소드를 사용한 블럭안의 작업은 자체의 queue에서 실행된다). Backgourd queue에서는 항상 위의 메소드 중 하나로 wrapping 해야 한다.

    view context는 대부분 main queue에서 UI가 실행되는 동안에 사용자가 직접적으로 접근할 수 있기 때문에 살짝 다르다.

    그러나 만약  main context 또는 background queue안의 main context manged object 접근하고 싶다면 peform(_:) api를 사용하여 작업이 main queue에서 실행되는지 확인해야 한다. 

     

    Perform(_:)

    Perform(:_) 메소드는 비동기 방식이다. 즉 바로 호출하는 쓰레드를 막지 않고 즉시 리턴해준다. 이 메소드를 통해 제출되는 블록은 queue의 context안에서 FIFO(First in First out) 방식으로 실행된다.

     

    Core Data를 사용하는 이점 중 하나는 reactive user interfaces를 작성하는 것에 있어서 유용한 변화 추적이다. perform(_:) 메소드는 사용자가 제출한 블록을 유저 이벤트로 처리하고, 이는 모든 perform 메소드의 블록이 끝날 때마다 모든 변경 내용이 처리되고 관련 notification을 보낸다. 예를 들어 NSFetchedResultsController는 이러한 notification에 대한 응답으로 테이블 뷰를 자동으로 업데이트한다.

     

    마지막으로, perform(_:) 메소드를 통해 통해 제출되는 모든 블록은 autorelease pool로 포장된다.

     

    PerformAndWait(_:)

    performAndWait(_:) 메소드는 queue에 등록된 블록이 실행 완료된 다음 리턴해주는 동기 방식이다. 따라서 쓰레드가 차단된다. performAndWait(_:) 메소드를 통해 등록된 블록은 사용자 이벤트로 처리되지 않는다. 즉, NSFetchedResultController를 사용한다면 processPendingChanges() 호출하여 변경사항을 처리하도록 context에게 직접 전달하거나 save()메소드를 통해 context의 변경 사항을 가져올 수 있다. 또한 autorealease pool에서 블록을 감싸지 않는다.

     

    performAndWait(_:)를 호출하는 것은 reentrant(재진입성)이다. 즉, 다른 perform 블록 내에서 performAndWait(_:)를 호출한다면 인라인으로 실행된다.

     

    결론

    context나 해당 manged object와 상호작용 할 때는 항상 perform 메소드를 통해 올바른 queue에서 실행되게 만들어야한다. view context 와 main queue에서 접근 할때는 예외이다. 이 경우 perform 메소드를 사용할 필요가 없다.

     

    댓글

Designed by Tistory.