Различные конфигурации области, появляющиеся в приложении Swift

#ios #swift #realm #realm-mobile-platform

#iOS #swift #область #realm-мобильная платформа

Вопрос:

Swift 3, Xcode 8, RealmSwift 2.0.2, Realm Object Server 1.0

В моем делегате приложений у меня есть функция, которая настраивает конфигурацию моей области для подключения к настроенному мной удаленному серверу синхронизации. Я просто использую тестовую учетную запись для аутентификации, пока не смогу освоить основы работы с синхронизацией. 1.1.1.1 это не мой настоящий IP-адрес. 😉

 let username = "test"
let password = "test"

let address = "http://1.1.1.1:9080"
let syncAddress = "realm://1.1.1.1:9080/~/myapp"

SyncUser.authenticate(with: Credential.usernamePassword(username: username, password: password, actions: []), server: URL(string: address)!, onCompletion: { user, error in
    guard let user = user else {
      fatalError(String(describing: error))
    }

    // Open Realm
    Realm.Configuration.defaultConfiguration = Realm.Configuration(
      syncConfiguration: (user, URL(string: syncAddress)!)
    )
 })
  

Кажется, это работает нормально. Я вижу, что данные отображаются на моем сервере, и я не получаю ошибок. Я предполагаю, что установка конфигурации области здесь означает, что все экземпляры Realm() будут использовать эту конфигурацию.

Затем я устанавливаю realm объект как свойство класса в двух отдельных контроллерах представления:

 class TableViewControllerA: UITableViewController{
  let realm = try! Realm()
  override func viewDidLoad() {
    // CORRECT: Prints "nil" as it should for a remotely synced Realm instance
    print(realm.configuration.fileURL)
  }
}
  

… и еще один в другом файле:

 class ViewControllerB: UIViewController{
  let realm = try! Realm()
  override func viewDidLoad() {
    // WRONG: Prints the path to the local realm file in the Simulator
    print(realm.configuration.fileURL) 
  }
}
  

Как отмечено в комментариях к коду выше, два экземпляра realm отличаются. На некоторых из моих контроллеров просмотра я могу сохранять объекты на сервере и видеть, как они отображаются на моем устройстве. На других контроллерах представления я не вижу никаких данных, потому что он использует неправильную базу данных области.

Могу ли я с уверенностью ожидать, что конфигурация области будет сохраняться во всем моем приложении? Нужно ли мне делать что-то еще, чтобы использовать ту же конфигурацию?

Комментарии:

1. Дважды проверьте, что ваш контроллер представления не создается до того, как вы установили конфигурацию по умолчанию.

2. Я устанавливаю конфигурацию по умолчанию в своем делегате приложения. Разве я не гарантирую, что это произойдет первым?

3. Опубликованный вами код показывает, что вы устанавливаете конфигурацию по умолчанию в обратном вызове, который вызывается асинхронно после аутентификации пользователя.

4. Ах, хороший улов — условие гонки! Но я предполагаю, что конфигурация должна быть в этой асинхронной функции, поскольку мне нужна user для настройки конфигурации.

5. @bdash Если вы хотите опубликовать свой ответ об асинхронной функции в качестве ответа, я отмечу его как принятый. Это была проблема. Большое вам спасибо!

Ответ №1:

Вы устанавливаете конфигурацию по умолчанию в обработчике завершения аутентификации. Этот обратный вызов вызывается асинхронно после аутентификации пользователя. Если экземпляр одного из ваших подклассов контроллера представления создается до выполнения обратного вызова, открываемая область будет использовать конфигурацию по умолчанию по умолчанию до любых изменений, которые вы вносите в обработчик завершения аутентификации.

Комментарии:

1. Как бы вам лучше всего избежать этой ситуации?

2. Я избежал этого, заблокировав остальную часть своего пользовательского интерфейса с помощью экрана аутентификации пользователя. Как только пользователь входит в систему, я программно загружаю другую раскадровку.

3. Забавно — именно то, что я сделал — было интересно, использовал ли кто-нибудь семафор или использовал какой-либо другой метод, чтобы дождаться завершения обработчика завершения. Спасибо!