title: Creating a network listener accessible to a whole iOS application
body: <p>I'm developing an iOS app with Firebase. My root view controller is a <code>UITabBarController</code>.</p>
  
  <p>All of the controllers within said TabBar need to listen to a <code>User</code> document in Firebase's Firestore, but creating a listener in each one doesn't seem to be the most efficient way to do it.</p>
  
  <p>I'm aware I could create the listener in a <code>CustomTabBarController</code> like so:</p>
  
  <pre><code>import UIKit
  import FirebaseFirestore
  
  class CustomTabBarController: UITabBarController {
  
      var userListener: ListenerRegistration?
      var user: User? // User is a custom class
  
      override func viewDidAppear(_ animated: Bool) {
          let userID = UserDefaults.standard.value(forKey: "id") as! String
  
          userListener = Firestore.firestore().document("users/\(userID)").addSnapshotListener { (document, error) in
              if let document = document {
                  self.user = User(firebaseDocument: document)
              } else {
                  // handle error!
              }
          }
      }
  
      override func viewDidDisappear(_ animated: Bool) {
          if let listener = userListener {
              listener.remove()
          }
      }
  
  }
  </code></pre>
  
  <p>and then access that <code>user</code> property from all <code>ChildViewController</code>'s like so:</p>
  
  <pre><code>class ChildViewController: UIViewController {
  
      var user: User?
  
      override func viewDidLoad() {
          super.viewDidLoad()
  
          let customTabBarController = tabBarController as! CustomTabBarController
          self.user = customTabBarController.user
      }
  }
  </code></pre>
  
  <p>I find two problems with this approach:</p>
  
  <ol>
  <li>The <code>user</code> property in <code>ChildViewController</code> will not update, as it is only set in the <code>viewDidLoad</code> method.</li>
  <li>I don't think <code>CustomTabBarController</code> is the place to handle the listener failure. Different <code>ChildViewController</code>'s will have different ways to deal with it.</li>
  </ol>
  
  <p><strong>Questions:</strong> What are my options to create a listener capable of updating any <code>UIVIewController</code>'s that need its result? Am I on the right path here or maybe I can use the <code>AppDelegate</code> or even a Singleton to achieve this.</p>
  
  <p>Thanks!</p>