Realm Blog

Realm Java 3.1: 객체 알림, 백업 복구, 역 관계

이 버전에서 읽고 작성된 Realm 파일은 이전 버전의 Realm에서 열리지 않습니다. 기존의 파일은 열릴 때 자동으로 업그레이드됩니다. 기존 앱에 업데이트를 배포할 때 주의하세요!

4월 5일 3.1 버전의 Realm Java를 출시하였습니다. 이 버전은 동기화된 Realm에 대한 향상된 백업 복구, 모든 객체에 대한 정밀한 알림, 역 관계에 대한 초기 지원을 포함합니다. 자세한 내용을 읽어보세요.

정밀한 객체 알림

Realm Java 3.0에서 정밀한 컬렉션 알림을 소개했습니다. 3.1에서는 단일 객체 알림을 RealmObjectChangeListener 인터페이스와 ObjectChangeSet 클래스를 사용하여 확장합니다.

Person p = realm.where(Person.class).findFirst();
p.addChangeListener(new RealmObjectChangeListener<Person>() {
   @Override
   public void onChange(Person person, ObjectChangeSet changeSet) {
       if (changeSet.isDeleted()) {
           hide(); // Object was deleted
       } else {
           // Use information about which fields changed to only update part of the UI
           if (changeSet.isFieldChanged("name")) {
               updateName(person.getName());
           }
       }
   }
});

이전 배포에서 단일 객체 알림은 많은 경우 잘못된 알림이었습니다. 심지어 어떤 데이터도 변경되지 않았을 때도 호출되었죠. 이런 문제는 3.1 버전에서 수정되었고 이제 단일 객체 알림을 사용할 때는 정밀한 알림이든 아니든 객체가 수정되었을 때만 호출됩니다.

백업 복구 향상

서버가 다운되었을 때를 대비해서 복구 계획이 필요합니다. 이런 이유로 Realm 모바일 플랫폼이 데이터 백업 기능을 몇 달 전부터 제공했습니다. 정상적인 상황에서 Realm의 동기화 엔진은 어떤 명령을 받아 동작하며 Realm 오브젝트 서버가 새로운 명령들을 받으면 사용자의 로컬 로그가 지워집니다. 이런 방식이 사용자 앱의 디스크 사용량을 적게 하고 Realm을 번개⚡️같이 빠르게 합니다.

게다가 Realm은 오프라인 우선 데이터베이스이기 때문에 Realm 오브젝트 서버가 어떤 이유로 동작하지 않아도 로컬 데이터는 사용 가능합니다.

하지만 서버가 데이터를 백업받은 데이터로 복원한다면 클라이언트들은 세션 에러 핸들러를 통해 “client reset” (클라이언트 리셋) 에러를 받게 됩니다. 로컬 Realm을 일반적으로 사용하듯 계속 사용할 수 있지만, 이후의 변경이나 마지막 백업 이후의 변경들은 잃게 됩니다.

한번 “client reset” 에러를 받게 되면 사용자에게 이 상황을 알리고 Realm의 사용을 멈추게 하고 서버가 마지막으로 백업한 버전의 Realm을 다시 내려받을 수 있습니다. ClientResetRequiredError 클래스는 Realm의 이전 지역 버전으로 수동으로 정리할 수 있는지 정보와 방법을 담고 있습니다.

client reset 에러를 곧 처리하지 않는 것도 한 가지 선택입니다. 이런 경우 앱이 다음번에 수행될 때 이전의 지역 버전 Realm은 삭제되고 서버가 마지막으로 백업한 버전으로 첫 접근에 다시 내려받습니다.

final SyncConfiguration config = new SyncConfiguration.Builder(user , url)
       .errorHandler(new SyncSession.ErrorHandler() {
           @Override
           public void onError(SyncSession session, ObjectServerError error) {
               if (error.getErrorCode() == ErrorCode.CLIENT_RESET) {
                   ClientResetRequiredError err = (ClientResetRequiredError) error;
                   closeRealm();
                   err.executeClientReset(); // Manually do the reset
                   err.getBackupFile(); // Reference to backed up file
               } else {
                   // Handle other errors
               }
           }
       })
       .build();

역 관계 (베타)

Realm에서 객체 간의 관계는 양방향입니다. 이 말은 Person이 그의 Dog로 관계를 맺고 있다면 Realm은 자동으로 다른 방향의 관계를 만들어 유지한다는 것입니다.

이 역 관계는 일반적으로 모델 클래스에서는 숨겨져 있습니다. 하지만 우리는 @LinkingObjects 어노테이션을 제공하여 역 관계를 명시적으로 따라갈 수 있게 합니다.

역 관계를 만들기 위한 절차는 다음과 같습니다.

RealmResults 필드를 부모 객체의 일반 형으로 추가합니다. 필드는 파이널이어야 합니다. Realm은 관리되는(managed) 객체의 이 값을 자동으로 채웁니다. 관리되지 않는 (Un-managed) 객체에 역 관계를 지원하지 않습니다. 부모 객체에서 이 모델 클래스를 가리키는 필드의 이름을 넣은 @LinkingObjects 어노테이션을 추가하여 역 관계를 정의합니다.

다음에 예제가 있습니다.

public class Person extends RealmObject {
   public String name;
   public int age;
   public Dog dog;
}  

public class Dog extends RealmObject {
   public String name;

   @LinkingObjects("dog")
   public final RealmResults<Person> owners = null;
}

// 역 관계를 사용합니다
Dog dog = realm.where(Dog.class).findFirst();
dog.owners.size(); // 주인의 수를 가져옵니다
dog.owners.first(); // 강아지 첫번째 주인의 레퍼런스를 가져옵니다

다음 배포에 역 관계를 통해 질의가 가능해지면 역 관계는 진정한 힘을 얻게 될 것입니다.

질의 구현이 완료되지 않았기 때문에 @LinkingObjects 어노테이션에 @Beta를 붙여두었습니다. 이 기능에 대한 어떤 피드백도 환영합니다.

파일 포맷 향상

3.1에서 내부 Realm 파일 포맷을 변경합니다. 예전 Realm 파일은 열 때 자동으로 업그레이드됩니다. 이 작업이 완료되면 예전 버전의 Realm에서 더 읽을 수 없습니다.

변경 내역에서 전체 변경을 확인하세요.


읽어주셔서 감사합니다. 이제 Realm을 사용해서 멋진 앱을 만들어 보세요! 언제나 Stack Overflow, GitHub, Facebook page에서 우리를 만날 수 있습니다!


Realm Team

Realm의 미션은 더 나은 앱을 빠르게 개발할 수 있도록 돕는 것입니다. 이를 위해 저희는 개발자들이 실시간 협업, 가상 현실, 라이브 데이터 동기화, 오프라인 경험, 메시징 등 정교하고 강력한 기능을 쉽게 개발할 수 있도록 하는 개발 도구와 플랫폼을 제공하고 있습니다.

저희는 모바일 인터넷이 수많은 사용자와 보다 많은 디바이스가 속한 개방형 네트워크와 이들 간의 실시간 상호 작용으로 진화할 것이라고 믿으며, 개발자가 이같은 방향으로 발전할 수 있도록 돕기 위해 저희 제품들을 개발하고 있습니다.

이런 개발 뉴스를 더 만나보세요