Parse iOS uygulamanızı Firebase'e taşıyın

Ayrıştırıcı olarak başka bir Arka Uç arayan Hizmet çözümü olan Firebase, iOS uygulamanız için ideal seçim olabilir.

Bu kılavuzda, belirli hizmetleri uygulamanıza nasıl entegre edeceğiniz açıklanmaktadır. Örneğin, temel Firebase kurulumu talimatları için iOS+ Kurulumu'na bakın rehberini inceleyin.

Google Analytics

Google Analytics, uygulama kullanımı hakkında bilgi sağlayan ücretsiz bir uygulama ölçüm çözümüdür ve en iyi uygulamaları paylaşacağız. Analytics, Firebase özellikleriyle entegre olarak size sınırsız erişim sunar kullanarak tanımlayabileceğiniz 500'e kadar farklı etkinlik için rapor oluşturabilirsiniz.

Daha fazla bilgi edinmek için Google Analytics belgeye bakın.

Önerilen Taşıma Stratejisi

Farklı analiz sağlayıcıları kullanmak, her türlü analiz için Google Analytics Uygulamanıza ekleyerek etkili etkinliklerden ve kullanıcı özelliklerinden Analytics; ilk açılış, uygulama güncelleme, cihaz modeli ve yaş gibi bilgileri otomatik olarak toplar.

Özel etkinlikler ve kullanıcı özellikleri için, Etkinlikleri ve mülkleri günlüğe kaydetmek için hem Analytics'i hem de Google Analytics'yi ayrıştırarak ve yeni çözümü kademeli olarak kullanıma sunacaktır.

Kod Karşılaştırması

Analizi Ayrıştırma

// Start collecting data
[PFAnalytics trackAppOpenedWithLaunchOptions:launchOptions];

NSDictionary *dimensions = @{
  // Define ranges to bucket data points into meaningful segments
  @"priceRange": @"1000-1500",
  // Did the user filter the query?
  @"source": @"craigslist",
  // Do searches happen more often on weekdays or weekends?
  @"dayType": @"weekday"
};
// Send the dimensions to Parse along with the 'search' event
[PFAnalytics trackEvent:@"search" dimensions:dimensions];

Google Analytics

// Obtain the AppMeasurement instance and start collecting data
[FIRApp configure];

// Send the event with your params
[FIRAnalytics logEventWithName:@"search" parameters:@{
  // Define ranges to bucket data points into meaningful segments
  @"priceRange": @"1000-1500",
  // Did the user filter the query?
  @"source": @"craigslist",
  // Do searches happen more often on weekdays or weekends?
  @"dayType": @"weekday"
}];

Firebase Realtime Database

Firebase Realtime Database, bulutta barındırılan bir NoSQL veritabanıdır. Veriler JSON biçiminde depolanır ve otomatik olarak senkronize edilir.

Daha fazla bilgi edinmek için Firebase Realtime Database belgeye bakın.

Verileri Ayrıştırma Verileriyle Farklar

Nesneler

Ayrıştırma'da, anahtar/değer çiftleri içeren bir PFObject veya bunun bir alt sınıfını saklarsınız. JSON uyumlu veri var. Veriler şemasız olduğundan hangi anahtarların her PFObject için geçerlidir.

Tüm Firebase Realtime Database verileri JSON nesneleri olarak depolanır ve PFObject; tek yapmanız gereken bu işlem için karşılık gelen türlerin kullanılabilir JSON türlerine bakalım.

Aşağıda, bir oyunun rekorlarını nasıl kaydedebileceğinize dair bir örnek verilmiştir.

Ayrıştır
PFObject *gameScore = [PFObject objectWithClassName:@"GameScore"];
gameScore[@"score"] = @1337;
gameScore[@"playerName"] = @"Sean Plott";
gameScore[@"cheatMode"] = @NO;
[gameScore saveInBackgroundWithBlock:^(BOOL succeeded, NSError *error) {
  if (succeeded) {
    // The object has been saved.
  } else {
    // There was a problem, check error.description
  }
}];
Firebase
// Create a reference to the database
FIRDatabaseReference *ref = [[FIRDatabase database] reference];
NSString *key = [[ref child:@"scores"] childByAutoId].key;
NSDictionary *score = @{@"score": @1337,
                        @"playerName": @"Sean Plott",
                        @"cheatMode": @NO};
[key setValue:score withCompletionBlock:^(NSError *error,  FIRDatabaseReference *ref) {
  if (error) {
    // The object has been saved.
  } else {
    // There was a problem, check error.description
  }
}];
Daha fazla bilgi için Apple platformlarında Veri Okuma ve Yazma kılavuzu.

Veriler Arasındaki İlişkiler

PFObject, başka bir PFObject ile ilişkili olabilir: herhangi bir başka nesneleri değer olarak kullanabilir.

Firebase Realtime Database'da ilişkiler, farklı dillerdeki düz veri yapıları kullanılarak daha iyi ifade verileri ayrı yollara bölmek ve böylece ayrı görüşmelerde etkili bir şekilde indirilebilmelerini sağlamak.

Aşağıda, bir Google Etiket Yöneticisi'ndeki yayınlar arasındaki ilişkiyi ve yazarları.

Ayrıştır
// Create the author
PFObject *myAuthor = [PFObject objectWithClassName:@"Author"];
myAuthor[@"name"] = @"Grace Hopper";
myAuthor[@"birthDate"] = @"December 9, 1906";
myAuthor[@"nickname"] = @"Amazing Grace";

// Create the post
PFObject *myPost = [PFObject objectWithClassName:@"Post"];
myPost[@"title"] = @"Announcing COBOL, a New Programming Language";

// Add a relation between the Post and the Author
myPost[@"parent"] = myAuthor;

// This will save both myAuthor and myPost
[myPost saveInBackground];
Firebase
// Create a reference to the database
FIRDatabaseReference *ref = [[FIRDatabase database] reference];

// Create the author
NSString *myAuthorKey = @"ghopper";
NSDictionary *author = @{@"name": @"Grace Hopper",
                         @"birthDate": @"December 9, 1906",
                         @"nickname": @"Amazing Grace"};
// Save the author
[[ref child:myAuthorKey] setValue:author]

// Create and save the post
NSString *key = [[ref child:@"posts"] childByAutoId].key;
NSDictionary *post = @{@"author": myAuthorKey,
                       @"title": @"Announcing COBOL, a New Programming Language"};
[key setValue:post]

Sonuç, aşağıdaki veri düzenidir.

{
  // Info about the authors
  "authors": {
    "ghopper": {
      "name": "Grace Hopper",
      "date_of_birth": "December 9, 1906",
      "nickname": "Amazing Grace"
    },
    ...
  },
  // Info about the posts: the "author" fields contains the key for the author
  "posts": {
    "-JRHTHaIs-jNPLXOQivY": {
      "author": "ghopper",
      "title": "Announcing COBOL, a New Programming Language"
    }
    ...
  }
}
Daha fazla bilgi için Veritabanınızı Yapılandırma rehberini inceleyin.

Verileri Okuma

Ayrıştırma'da, verileri belirli bir Parse nesnesinin kimliğini kullanarak veya PFQuery kullanarak sorgu yürütebilirsiniz.

Firebase'de, verileri bir veritabanı referansına eşzamansız işleyici ekleyerek alırsınız. İlgili içeriği oluşturmak için kullanılan işleyici, verilerin ilk durumu için bir kez ve veriler değiştiğinde tekrar tetiklenir. bu nedenle verilerin değişip değişmediğini belirlemek için herhangi bir kod eklemeniz gerekmez.

Aşağıda, skor tablosuna göre, oyun türüne göre belirli bir oyuncu için "Nesneler" bölümünde sunulan örneğe bakın.

Ayrıştır
PFQuery *query = [PFQuery queryWithClassName:@"GameScore"];
[query whereKey:@"playerName" equalTo:@"Dan Stemkoski"];
[query findObjectsInBackgroundWithBlock:^(NSArray *objects, NSError *error) {
  if (!error) {
    for (PFObject *score in objects) {
      NSString *gameScore = score[@"score"];
      NSLog(@"Retrieved: %@", gameScore);
    }
  } else {
    // Log details of the failure
    NSLog(@"Error: %@ %@", error, [error userInfo]);
  }
}];
Firebase
// Create a reference to the database
FIRDatabaseReference *ref = [[FIRDatabase database] reference];

// This type of listener is not one time, and you need to cancel it to stop
// receiving updates.
[[[[ref child:@"scores"] queryOrderedByChild:@"playerName"] queryEqualToValue:@"Dan Stemkoski"]
    observeEventType:FIRDataEventTypeChildAdded withBlock:^(FIRDataSnapshot *snapshot) {
  // This will fire for each matching child node.
  NSDictionary *score = snapshot.value;
  NSString gameScore = score[@"score"];
  NSLog(@"Retrieved: %@", gameScore);
}];
Mevcut etkinlik işleyici türleri hakkında daha fazla bilgi Verilerin nasıl sıralanacağı ve filtreleneceği konusunda, Apple platformlarında Veri Okuma ve Yazma rehberini inceleyin.

Önerilen Taşıma Stratejisi

Verilerinizi Yeniden Değerlendirme

Firebase Realtime Database, tüm bağlı cihazlarda verileri milisaniyeler içinde senkronize edecek şekilde optimize edilmiştir ve ortaya çıkan veri yapısı, Parse çekirdek verilerinden farklıdır. Bu, Taşıma işleminizin ilk adımı, aşağıdakiler de dahil olmak üzere verileriniz için gereken değişiklikleri göz önünde bulundurmaktır:

  • Parse nesnelerinizin Firebase verileriyle nasıl eşleşmesi gerekir?
  • Üst-alt ilişkileriniz varsa verilerinizi farklı yollar arasında nasıl böleceğiniz ve ayrı görüşmelerde verilebilir şekilde indirilebilir.

Verilerinizi Taşıma

Firebase'de verilerinizi nasıl yapılandıracağınıza karar verdikten sonra, Bu süre boyunca uygulamanızın her iki veritabanına da yazması gerekir. Seçenekleriniz şunlardır:

Arka Plan Senkronizasyonu

Bu senaryoda uygulamanın iki sürümü bulunmaktadır: Parse kullanan eski sürüm ve yeni sürüm veya Firebase için Google Analytics'i kullanın. İki veritabanı arasındaki senkronizasyonlar Parse Cloud Code (Ayrıştırma) tarafından işlenir Firebase'e aktarma) sayesinde, kodunuz Firebase'deki değişiklikleri dinler ve bu değişiklikleri Parse ile senkronize eder. Yeni sürümü kullanmaya başlamadan önce şunları yapmanız gerekir:

  • Mevcut Ayrıştırma Verilerinizi yeni Firebase yapısına dönüştürün ve Firebase Realtime Database
  • Firebase REST API kullanan Ayrıştırma Cloud Code işlevlerini Eski istemciler tarafından Ayrıştırma Verilerinde Firebase Realtime Database değişiklik yapıldı.
  • Firebase'deki değişiklikleri dinleyen ve bunları Parse'a senkronize eden bir kod yazıp dağıtın

Bu senaryo, eski ve yeni kodun sorunsuz bir şekilde birbirinden ayrılmasını sağlar ve müşterileri basit tutar. İlgili içeriği oluşturmak için kullanılan Bu senaryonun en zorlayıcıları, ilk dışa aktarım sırasında büyük veri kümelerini ele almak ve çift yönlü senkronizasyon, sonsuz yineleme oluşturmaz.

Çift Yazma

Bu senaryoda, uygulamanın hem Firebase hem de Parse kullanan yeni bir sürümünü yazmak için Eski istemciler tarafından yapılan değişiklikleri Parse Verilerinden Firebase Realtime Database Uygulamanın salt Parse sürümünden yeterli sayıda kullanıcı geçiş yaptığında çift yazılan sürümden Ayrıştırma kodunu kaldırabilirsiniz.

Bu senaryo, herhangi bir sunucu tarafı kodu gerektirmez. Dezavantajları ise ve uygulamanızın boyutunun her iki SDK'nın kullanımı tarafından artırılacağını da hatırlatmak isteriz.

Firebase Authentication

Firebase Authentication, şifreleri ve popüler birleşik kimlik sağlayıcılarını kullanarak kullanıcıların kimliğini doğrulayabilir Google, Facebook ve Twitter gibi. Ayrıca kullanıcı arayüzü kitaplıkları sayesinde uygulamanızda eksiksiz bir kimlik doğrulama deneyimi sunmak ve sürdürmek için gereken yatırım tüm platformlarda kullanılabilir.

Daha fazla bilgi edinmek için Firebase Authentication belgeye bakın.

Parse Auth ile Farklar

Ayrıştırma, PFUser adında özel bir kullanıcı sınıfı sağlar. Bu sınıf, otomatik olarak işlenir. Kullanıcı hesabı yönetimi için gereken işlevsellik. PFUser şunun bir alt sınıfıdır: PFObject, yani kullanıcı verilerinin Ayrıştırma Verilerinde bulunduğu ve ek alanları (diğer tüm PFObject gibi) kullanabilirsiniz.

FIRUser, benzersiz kimlik, birincil e-posta adresi, Ayrı bir projenin kullanıcı veritabanında depolanan bir ad ve fotoğraf URL'si; bu özellikler gösterir. FIRUser nesnesine doğrudan başka özellikler ekleyemezsiniz; bunun yerine ek özellikleri Firebase Realtime Database içinde depolayabilirsiniz.

Aşağıda, kullanıcıları nasıl ekleyebileceğiniz ve ek bir telefon numarası alanı nasıl ekleyebileceğinizi gösteren bir örnek verilmiştir.

Ayrıştır
PFUser *user = [PFUser user];
user.username = @"my name";
user.password = @"my pass";
user.email = @"email@example.com";

// other fields can be set just like with PFObject
user[@"phone"] = @"415-392-0202";

[user signUpInBackgroundWithBlock:^(BOOL succeeded, NSError *error) {
  if (!error) {
    // Hooray! Let them use the app now.
  } else {
    // Something went wrong
    NSString *errorString = [error userInfo][@"error"];
  }
}];
Firebase
[[FIRAuth auth] createUserWithEmail:@"email@example.com"
                           password:@"my pass"
                         completion:^(FIRUser *_Nullable user, NSError *_Nullable error) {
  if (!error) {
    FIRDatabaseReference *ref = [[FIRDatabase database] reference];
    [[[[ref child:@"users"] child:user.uid] child:@"phone"] setValue:@"415-392-0202"
  } else {
    // Something went wrong
    NSString *errorString = [error userInfo][@"error"];
  }
}];

Önerilen Taşıma Stratejisi

Hesapları Taşı

Kullanıcı hesaplarını Parse'dan Firebase'e taşımak için kullanıcı veritabanınızı CSV veya CSV dosyası olarak indirin, ardından şu dosyayı kullanarak dosyayı Firebase projenize aktarın: Firebase CLI'ın auth:import komutuna ekleyin.

Öncelikle, Parse konsolundan veya kendi barındırdığınız kullanıcıdan kullanıcı veritabanınızı dışa aktarın Örneğin, Parse konsolundan dışa aktarılan bir JSON dosyası örneğin:

{ // Username/password user
  "bcryptPassword": "$2a$10$OBp2hxB7TaYZgKyTiY48luawlTuYAU6BqzxJfpHoJMdZmjaF4HFh6",
  "email": "user@example.com",
  "username": "testuser",
  "objectId": "abcde1234",
  ...
},
{ // Facebook user
  "authData": {
    "facebook": {
      "access_token": "ABCDEFGHIJKLMNOPQRSTUVWXYZ",
      "expiration_date": "2017-01-02T03:04:05.006Z",
      "id": "1000000000"
    }
  },
  "username": "wXyZ987654321StUv",
  "objectId": "fghij5678",
  ...
}

Ardından, dışa aktarılan dosyayı Firebase'in gerektirdiği biçime dönüştürün KSA. Parse kullanıcılarınızın objectId öğesini Firebase kullanıcılarınızın localId kadarı. Ayrıca, base64 kodlayın: Ayrıştırma işlemindeki bcryptPassword değerleri ve bunları passwordHash içinde kullanın girin. Örneğin:

{
  "users": [
    {
      "localId": "abcde1234",  // Parse objectId
      "email": "user@example.com",
      "displayName": "testuser",
      "passwordHash": "JDJhJDEwJE9CcDJoeEI3VGFZWmdLeVRpWTQ4bHVhd2xUdVlBVTZCcXp4SmZwSG9KTWRabWphRjRIRmg2",
    },
    {
      "localId": "fghij5678",  // Parse objectId
      "displayName": "wXyZ987654321StUv",
      "providerUserInfo": [
        {
          "providerId": "facebook.com",
          "rawId": "1000000000",  // Facebook ID
        }
      ]
    }
  ]
}

Son olarak, dönüştürülen dosyayı Firebase CLI ile içe aktarın ve bcrypt yapın. örneğine bakalım:

firebase auth:import account_file.json --hash-algo=BCRYPT

Kullanıcı Verilerini Taşı

Kullanıcılarınız için ek veriler depoluyorsanız bu verileri Firebase Realtime Database hizmetine taşıyabilirsiniz ve veri taşıma bölümünde açıklanan stratejiler uygulanır. Taşıma işlemini gerçekleştirirseniz hesap taşıma bölümünde açıklanan akışı kullanan hesaplarınızı yönetmek için Firebase hesapları Parse hesaplarınızla aynı kimliklere sahiptir, böylece kolayca taşıma ve yeniden oluşturma kullanıcı kimliği ile anahtarlanan tüm ilişkiler.

Firebase Cloud Messaging

Firebase Cloud Messaging (FCM), güvenli bir şekilde mesajlaşmanıza olanak tanıyan platformlar arası bir mesajlaşma çözümüdür ücretsiz olarak mesaj ve bildirim gönderin. Bildirimler oluşturucu, Mobil uygulama geliştiriciler için hedeflenmiş kullanıcı bildirimlerini etkinleştiren Firebase Cloud Messaging uygulamasında.

Daha fazla bilgi edinmek için Firebase Cloud Messaging dokümana bakın.

Ayrıştırma push bildirimleriyle olan farklılıklar

Bildirimler için kayıtlı bir cihazda yüklü her Ayrıştırma uygulamasının ilişkilendirilmiş bir numarası vardır Installation nesnesi içerir. Installation, PFUser etiketinin bir alt sınıfıdır. Bu nedenle şunları ekleyebilirsiniz: Installation örneklerinize eklemek istediğiniz tüm ek veriler.

Bildirim oluşturucu; uygulama, uygulama sürümü ve cihaz gibi bilgilere dayalı olarak önceden tanımlanmış kullanıcı segmentleri sağlar dili'ne dokunun. Google Analytics etkinliklerini ve özelliklerini kullanarak daha karmaşık kullanıcı segmentleri oluşturabilirsiniz. kullanarak kitle oluşturabilirsiniz. Kitleleri inceleyin yardım rehberine göz atın. Bu hedefleme bilgileri Firebase Realtime Database içinde görünmez.

Önerilen Taşıma Stratejisi

Cihaz Jetonlarını Taşıma

Parse, bildirimler için yüklemeleri hedeflemek amacıyla APNs cihaz jetonlarını kullanırken FCM APN'lerin cihaz jetonlarıyla eşlenen FCM kayıt jetonlarını kullanır. FCM eklemeniz yeterlidir. SDK'yı Apple uygulamanıza eklerseniz otomatik olarak bir FCM jetonu getirir.

Kanallar FCM Konularına Taşınıyor

Bildirim göndermek için Kanalları Ayrıştırma özelliğini kullanıyorsanız FCM konulara taşıyabilirsiniz. modeline sahip olmanız gerekir. Ayrıştırma'dan FCM'ye geçişi gerçekleştirmek için yeni bir sürüm yazabilirsiniz Parse kanallarının aboneliğinden çıkmak için Parse SDK'sını ve abone olmak üzere FCM SDK'sını kullanan uygulamanın ilgili FCM konu.

Örneğin, kullanıcınız "Giants"a aboneyse şöyle bir şey yaparsınız:

PFInstallation *currentInstallation = [PFInstallation currentInstallation];
[currentInstallation removeObject:@"Giants" forKey:@"channels"];
[currentInstallation saveInBackgroundWithBlock:^(BOOL succeeded, NSError *error) {
  if (succeeded) {
    [[FIRMessaging messaging] subscribeToTopic:@"/topics/Giants"];
  } else {
    // Something went wrong unsubscribing
  }
}];

Bu stratejiyi kullanarak hem Parse kanalına hem de ilgili kanala mesaj gönderebilirsiniz FCM konu, hem eski hem de yeni sürümlerin kullanıcılarını destekleme Gmail'den yeterli sayıda kullanıcı Uygulamanın yalnızca ayrıştırılan sürümünü kullanıyorsanız bu sürümü kullanımdan kaldırabilir ve yalnızca FCM uygulamasını kullanarak göndermeye başlayabilirsiniz.

Bkz. FCM konu dokümanı konulu videomuzu izleyin.

Firebase Remote Config

Firebase Remote Config, cihazınızın davranışını ve görünümünü değiştirmenizi sağlayan bir bulut hizmetidir uygulamasını kullanarak kullanıcıların uygulama güncellemesi indirmesini gerektirmez. Remote Config'i kullanırken uygulama içi uygulamanızın davranışını ve görünümünü kontrol eden varsayılan değerlerdir. Daha sonra, Firebase konsolunu kullanarak, tüm uygulama kullanıcıları veya kullanıcı tabanınızın segmentleri için uygulama içi varsayılan değerleri geçersiz kılabilirsiniz.

Firebase Remote Config, test etmek istediğiniz durumlarda, taşıma işlemleriniz sırasında çok yararlı olabilir daha fazla müşteriyi dinamik olarak farklı bir sağlayıcıya aktarabilme olanağı. Örneğin, Uygulamanızın veriler için hem Firebase hem de Parse kullanan bir sürümü varsa hangi istemcilerin Firebase'den okuduğunu belirlemek için rastgele yüzdelik dilim kuralı uygulayın ve yüzdeyi kademeli olarak artırın.

Firebase Remote Config hakkında daha fazla bilgi için bkz. Remote Config giriş.

Ayrıştırma Yapılandırması ile Farklar

Parse yapılandırmasıyla, Parse Config Kontrol Paneli'nde uygulamanıza anahtar/değer çiftleri ekleyebilir, ardından istemcide PFConfig öğesini getir. Oluşturduğunuz her PFConfig örneği get her zaman sabittir. Gelecekte yeni bir PFConfig aldığınızda ağda yer alıyorsa mevcut PFConfig örneklerini değil, yeni bir hesap oluşturun ve currentConfig üzerinden kullanıma sunun.

Firebase Remote Config ile anahtar/değer çiftleri için geçersiz kılabileceğiniz uygulama içi varsayılan ayarlar oluşturursunuz ve uygulamanızın ayarları ile ilgili varyasyonları sağlamak için kurallar ve koşulları kullanabilirsiniz. daha fazla kullanıcıya hitap edin. Firebase Remote Config, bir anahtar/değer çiftlerini uygulamanızda kullanılabilir hale getiren singleton sınıfını kullanın. Başlangıçta singleton geri döner uygulama içi olarak tanımladığınız varsayılan değerler. İstediğiniz zaman sunucudan yeni bir değer grubu alabilirsiniz uygulamanız için en uygun an; getirildikten sonra, yeni kümenin ne zaman etkinleştirileceğini seçebilirsiniz. uygulamanın kullanıma sunulmasını sağlayabilir.

Önerilen Taşıma Stratejisi

Parse yapılandırmanızın anahtar/değer çiftlerini kopyalayarak Firebase Remote Config platformuna geçebilirsiniz ve ardından uygulamanın Firebase Remote Config kullanan yeni bir sürümünü dağıtmanız gerekir.

Hem Parse Config hem de Firebase Remote Config ile deneme yapmak istiyorsanız Yalnızca Parse sürümünden yeterli sayıda kullanıcı geçiş yapana kadar her iki SDK'yı da kullanan yeni bir uygulama sürümü.

Kod Karşılaştırması

Ayrıştır

[PFConfig getConfigInBackgroundWithBlock:^(PFConfig *config, NSError *error) {
  if (!error) {
    NSLog(@"Yay! Config was fetched from the server.");
  } else {
    NSLog(@"Failed to fetch. Using Cached Config.");
    config = [PFConfig currentConfig];
  }

  NSString *welcomeMessage = config[@"welcomeMessage"];
  if (!welcomeMessage) {
    NSLog(@"Falling back to default message.");
    welcomeMessage = @"Welcome!";
  }
}];

Firebase

FIRRemoteConfig remoteConfig = [FIRRemoteConfig remoteConfig];
// Set defaults from a plist file
[remoteConfig setDefaultsFromPlistFileName:@"RemoteConfigDefaults"];

[remoteConfig fetchWithCompletionHandler:^(FIRRemoteConfigFetchStatus status, NSError *error) {
  if (status == FIRRemoteConfigFetchStatusSuccess) {
    NSLog(@"Yay! Config was fetched from the server.");
    // Once the config is successfully fetched it must be activated before newly fetched
    // values are returned.
    [self.remoteConfig activateFetched];
  } else {
    NSLog(@"Failed to fetch. Using last fetched or default.");
  }
}];

// ...

// When this is called, the value of the latest fetched and activated config is returned;
// if there's none, the default value is returned.
NSString welcomeMessage = remoteConfig[@"welcomeMessage"].stringValue;