Birçok kullanıcı yeni bir Android cihazı kurarken kendi kimlik bilgilerini yönetmeye devam eder. Bu manuel işlem zorlayıcı olabilir ve genellikle kötü bir kullanıcı deneyimine neden olur. Google Play hizmetleri tarafından desteklenen bir kitaplık olan Block Store API, kullanıcıların kullanıcı şifrelerini kaydetmeyle ilgili karmaşıklık veya güvenlik riski olmadan kullanıcı kimlik bilgilerini kaydetmeleri için bir yol sağlayarak bu sorunu çözmeye çalışır.
Block Store API, uygulamanızın daha sonra yeni bir cihazda kullanıcıların kimliklerini yeniden doğrulamak için alabileceği verileri depolamasına olanak tanır. Bu sayede, kullanıcılar uygulamanızı yeni cihazda ilk kez başlatırken bir oturum açma ekranı görmeleri gerekmez. Bu sayede, kullanıcılar daha sorunsuz bir deneyim yaşayabilirler.
Blok Mağaza'yı kullanmanın sağladığı avantajlardan bazıları şunlardır:
- Geliştiriciler için şifrelenmiş kimlik bilgisi depolama çözümü. Kimlik bilgileri mümkün olduğunda uçtan uca şifrelenir.
- Kullanıcı adları ve şifreler yerine jetonları kaydedin.
- Oturum açma süreçlerindeki zorlukları ortadan kaldırın.
- Kullanıcıları karmaşık şifreleri yönetme zahmetinden kurtarın.
- Google, kullanıcının kimliğini doğrular.
Başlamadan önce
Uygulamanızı hazırlamak için aşağıdaki adımları tamamlayın.
Uygulamanızı yapılandırma
Proje düzeyindeki build.gradle
dosyanıza Google'ın Maven deposunu hem buildscript
hem de allprojects
bölümlerine ekleyin:
buildscript {
repositories {
google()
mavenCentral()
}
}
allprojects {
repositories {
google()
mavenCentral()
}
}
Google Play Hizmetleri
Block Store API için bağımlılığı, modülünüzün Gradle derleme dosyasına
ekleyin (genellikle app/build.gradle
):
dependencies {
implementation 'com.google.android.gms:play-services-auth-blockstore:16.2.0'
}
İşleyiş şekli
Block Store, geliştiricilerin en fazla 16 baytlık dizileri kaydedip geri yüklemesine olanak tanır. Bu sayede, geçerli kullanıcı oturumuyla ilgili önemli bilgileri kaydedebilir ve bu bilgileri istediğiniz şekilde kaydedebilirsiniz. Bu veriler uçtan uca şifrelenebilir ve Engelleme Mağazası'nı destekleyen altyapı, Yedekle ve Geri Yükle altyapısının üzerine inşa edilmiştir.
Bu kılavuzda, bir kullanıcının jetonunun Mağaza'ya kaydedilmesiyle ilgili kullanım alanları ele alınmaktadır. Aşağıdaki adımlarda Blok Store kullanan bir uygulamanın nasıl çalıştığı açıklanmaktadır:
- Uygulamanızın kimlik doğrulama akışı sırasında veya daha sonra, daha sonra almak üzere kullanıcının kimlik doğrulama jetonunu Mağazada Engelle bölümünde saklayabilirsiniz.
- Jeton yerel olarak depolanır ve mümkün olduğunda uçtan uca şifrelenerek buluta yedeklenebilir.
- Kullanıcı yeni bir cihazda geri yükleme akışı başlattığında veriler aktarılır.
- Kullanıcı geri yükleme sürecinde uygulamanızı geri yüklerse uygulamanız yeni cihazda Blok Store'dan kaydedilen jetonu alabilir.
Jeton kaydediliyor
Bir kullanıcı uygulamanızda oturum açtığında, söz konusu kullanıcının Mağazayı Engellemesi için oluşturduğunuz kimlik doğrulama jetonunu kaydedebilirsiniz. Bu jetonu, giriş başına maksimum 4 KB olan benzersiz bir anahtar çifti değeri kullanarak depolayabilirsiniz.
Jetonu depolamak için StoreBytesData.Builder
örneğinde setBytes()
ve 'setKey(/android/reference/com/google/android/gms/auth/blockstore/StoreBytesData.Builder.html#setKey(java.lang.String)" yöntemini çağırarak kullanıcının kimlik bilgilerini kaynak cihazda depolayın. Jetonu Store Store ile kaydettikten sonra jeton şifrelenir ve cihazda yerel olarak depolanır.
Aşağıdaki örnekte, kimlik doğrulama jetonunun yerel cihaza nasıl kaydedileceği gösterilmektedir:
Java
BlockstoreClient client = Blockstore.getClient(this); byte[] bytes1 = new byte[] { 1, 2, 3, 4 }; // Store one data block. String key1 = "com.example.app.key1"; StoreBytesData storeRequest1 = StoreBytesData.Builder() .setBytes(bytes1) // Call this method to set the key value pair the data should be associated with. .setKeys(Arrays.asList(key1)) .build(); client.storeBytes(storeRequest1) .addOnSuccessListener(result -> Log.d(TAG, "stored " + result + " bytes")) .addOnFailureListener(e -> Log.e(TAG, "Failed to store bytes", e));
Kotlin
val client = Blockstore.getClient(this) val bytes1 = byteArrayOf(1, 2, 3, 4) // Store one data block. val key1 = "com.example.app.key1" val storeRequest1 = StoreBytesData.Builder() .setBytes(bytes1) // Call this method to set the key value with which the data should be associated with. .setKeys(Arrays.asList(key1)) .build() client.storeBytes(storeRequest1) .addOnSuccessListener { result: Int -> Log.d(TAG, "Stored $result bytes") } .addOnFailureListener { e -> Log.e(TAG, "Failed to store bytes", e) }
Varsayılan jetonu kullan
StoreBytes kullanılarak anahtar olmadan kaydedilen veriler varsayılan BlockstoreClient.DEFAULT_BYTES_DATA_KEY anahtarını kullanır.
Java
BlockstoreClient client = Blockstore.getClient(this); // The default key BlockstoreClient.DEFAULT_BYTES_DATA_KEY. byte[] bytes = new byte[] { 9, 10 }; StoreBytesData storeRequest = StoreBytesData.Builder() .setBytes(bytes) .build(); client.storeBytes(storeRequest) .addOnSuccessListener(result -> Log.d(TAG, "stored " + result + " bytes")) .addOnFailureListener(e -> Log.e(TAG, "Failed to store bytes", e));
Kotlin
val client = Blockstore.getClient(this); // the default key BlockstoreClient.DEFAULT_BYTES_DATA_KEY. val bytes = byteArrayOf(1, 2, 3, 4) val storeRequest = StoreBytesData.Builder() .setBytes(bytes) .build(); client.storeBytes(storeRequest) .addOnSuccessListener { result: Int -> Log.d(TAG, "stored $result bytes") } .addOnFailureListener { e -> Log.e(TAG, "Failed to store bytes", e) }
Jeton alınıyor
Daha sonra, kullanıcı yeni bir cihazda geri yükleme akışını tamamladığında Google Play Hizmetleri önce kullanıcıyı doğrular, ardından Mağaza Engelleme verilerinizi alır. Kullanıcı, geri yükleme akışının bir parçası olarak uygulama verilerinizi geri yüklemeyi kabul etmiştir. Bu nedenle, ek izin gerekmez. Kullanıcı uygulamanızı açtığında retrieveBytes()
numaralı telefonu arayarak jetonunuzu Blok Store'dan isteyebilirsiniz.
Alınan jeton, daha sonra kullanıcının yeni cihazda oturumunu açık tutmak için kullanılabilir.
Aşağıdaki örnekte, belirli anahtarlara göre birden fazla jetonun nasıl alınacağı gösterilmektedir.
Java
BlockstoreClient client = Blockstore.getClient(this); // Retrieve data associated with certain keys. String key1 = "com.example.app.key1"; String key2 = "com.example.app.key2"; String key3 = BlockstoreClient.DEFAULT_BYTES_DATA_KEY; // Used to retrieve data stored without a key ListrequestedKeys = Arrays.asList(key1, key2, key3); // Add keys to array RetrieveBytesRequest retrieveRequest = new RetrieveBytesRequest.Builder() .setKeys(requestedKeys) .build(); client.retrieveBytes(retrieveRequest) .addOnSuccessListener( result -> { Map blockstoreDataMap = result.getBlockstoreDataMap(); for (Map.Entry entry : blockstoreDataMap.entrySet()) { Log.d(TAG, String.format( "Retrieved bytes %s associated with key %s.", new String(entry.getValue().getBytes()), entry.getKey())); } }) .addOnFailureListener(e -> Log.e(TAG, "Failed to store bytes", e));
Kotlin
val client = Blockstore.getClient(this) // Retrieve data associated with certain keys. val key1 = "com.example.app.key1" val key2 = "com.example.app.key2" val key3 = BlockstoreClient.DEFAULT_BYTES_DATA_KEY // Used to retrieve data stored without a key val requestedKeys = Arrays.asList(key1, key2, key3) // Add keys to array val retrieveRequest = RetrieveBytesRequest.Builder() .setKeys(requestedKeys) .build() client.retrieveBytes(retrieveRequest) .addOnSuccessListener { result: RetrieveBytesResponse -> val blockstoreDataMap = result.blockstoreDataMap for ((key, value) in blockstoreDataMap) { Log.d(ContentValues.TAG, String.format( "Retrieved bytes %s associated with key %s.", String(value.bytes), key)) } } .addOnFailureListener { e: Exception? -> Log.e(ContentValues.TAG, "Failed to store bytes", e) }
Tüm jetonlar alınıyor.
BlockStore'a kaydedilen tüm jetonların nasıl alınacağını gösteren bir örneği aşağıda bulabilirsiniz.
Java
BlockstoreClient client = Blockstore.getClient(this) // Retrieve all data. RetrieveBytesRequest retrieveRequest = new RetrieveBytesRequest.Builder() .setRetrieveAll(true) .build(); client.retrieveBytes(retrieveRequest) .addOnSuccessListener( result -> { MapblockstoreDataMap = result.getBlockstoreDataMap(); for (Map.Entry entry : blockstoreDataMap.entrySet()) { Log.d(TAG, String.format( "Retrieved bytes %s associated with key %s.", new String(entry.getValue().getBytes()), entry.getKey())); } }) .addOnFailureListener(e -> Log.e(TAG, "Failed to store bytes", e));
Kotlin
val client = Blockstore.getClient(this) val retrieveRequest = RetrieveBytesRequest.Builder() .setRetrieveAll(true) .build() client.retrieveBytes(retrieveRequest) .addOnSuccessListener { result: RetrieveBytesResponse -> val blockstoreDataMap = result.blockstoreDataMap for ((key, value) in blockstoreDataMap) { Log.d(ContentValues.TAG, String.format( "Retrieved bytes %s associated with key %s.", String(value.bytes), key)) } } .addOnFailureListener { e: Exception? -> Log.e(ContentValues.TAG, "Failed to store bytes", e) }
Aşağıda, varsayılan anahtarın nasıl alınacağına dair bir örnek verilmiştir.
Java
BlockStoreClient client = Blockstore.getClient(this); RetrieveBytesRequest retrieveRequest = new RetrieveBytesRequest.Builder() .setKeys(Arrays.asList(BlockstoreClient.DEFAULT_BYTES_DATA_KEY)) .build(); client.retrieveBytes(retrieveRequest);
Kotlin
val client = Blockstore.getClient(this) val retrieveRequest = RetrieveBytesRequest.Builder() .setKeys(Arrays.asList(BlockstoreClient.DEFAULT_BYTES_DATA_KEY)) .build() client.retrieveBytes(retrieveRequest)
Jetonları silme
Jetonların BlockStore'dan silinmesi aşağıdaki nedenlerden dolayı gerekli olabilir:
- Kullanıcı, oturumu kapatma kullanıcı akışını gerçekleştiriyor.
- Jeton iptal edildi veya geçersiz.
Jetonları almaya benzer şekilde, silinmesi gereken bir anahtar dizisi ayarlayarak hangi jetonların silinmesi gerektiğini belirtebilirsiniz.
Aşağıda bazı anahtarları silmeyle ilgili bir örnek verilmiştir.
Java
BlockstoreClient client = Blockstore.getClient(this); // Delete data associated with certain keys. String key1 = "com.example.app.key1"; String key2 = "com.example.app.key2"; String key3 = BlockstoreClient.DEFAULT_BYTES_DATA_KEY; // Used to delete data stored without key ListrequestedKeys = Arrays.asList(key1, key2, key3) // Add keys to array DeleteBytesRequest deleteRequest = new DeleteBytesRequest.Builder() .setKeys(requestedKeys) .build(); client.deleteBytes(deleteRequest)
Kotlin
val client = Blockstore.getClient(this) // Retrieve data associated with certain keys. val key1 = "com.example.app.key1" val key2 = "com.example.app.key2" val key3 = BlockstoreClient.DEFAULT_BYTES_DATA_KEY // Used to retrieve data stored without a key val requestedKeys = Arrays.asList(key1, key2, key3) // Add keys to array val retrieveRequest = DeleteBytesRequest.Builder() .setKeys(requestedKeys) .build() client.deleteBytes(retrieveRequest)
Tüm Jetonları Sil
Aşağıdaki örnekte BlockStore'da kayıtlı olan tüm jetonlar silinecektir:
Java
// Delete all data. DeleteBytesRequest deleteAllRequest = new DeleteBytesRequest.Builder() .setDeleteAll(true) .build(); client.deleteBytes(deleteAllRequest) .addOnSuccessListener(result -> Log.d(TAG, "Any data found and deleted? " + result));
Kotlin
val deleteAllRequest = DeleteBytesRequest.Builder() .setDeleteAll(true) .build() client.deleteBytes(deleteAllRequest) .addOnSuccessListener { result: Boolean -> Log.d(TAG, "Any data found and deleted? $result") }
Uçtan uca şifreleme
Uçtan uca şifrelemenin kullanılabilmesi için cihazın Android 9 veya sonraki bir sürümü çalıştırıyor olması ve kullanıcının cihazı için bir ekran kilidi (PIN, desen veya şifre) ayarlamış olması gerekir. isEndToEndEncryptionAvailable()
numaralı telefonu arayarak cihazda şifrelemenin kullanılabilir olup olmadığını doğrulayabilirsiniz.
Aşağıdaki örnekte, bulut yedekleme sırasında şifrelemenin kullanılıp kullanılamayacağını nasıl doğrulayacağınız gösterilmektedir:
client.isEndToEndEncryptionAvailable()
.addOnSuccessListener { result ->
Log.d(TAG, "Will Block Store cloud backup be end-to-end encrypted? $result")
}
Bulut yedeklemeyi etkinleştir
Bulut yedeklemeyi etkinleştirmek için StoreBytesData
nesnenize setShouldBackupToCloud()
yöntemini ekleyin. setShouldBackupToCloud()
depolama alanı true olarak ayarlandığında, Store'da Engelleme işlemi düzenli olarak yedeklenir ve bayt olarak buluta aktarılır.
Aşağıdaki örnekte, yalnızca bulut yedeği uçtan uca şifrelendiğinde bulut yedeklemesinin nasıl etkinleştirileceği gösterilmektedir:
val client = Blockstore.getClient(this)
val storeBytesDataBuilder = StoreBytesData.Builder()
.setBytes(/* BYTE_ARRAY */)
client.isEndToEndEncryptionAvailable()
.addOnSuccessListener { isE2EEAvailable ->
if (isE2EEAvailable) {
storeBytesDataBuilder.setShouldBackupToCloud(true)
Log.d(TAG, "E2EE is available, enable backing up bytes to the cloud.")
client.storeBytes(storeBytesDataBuilder.build())
.addOnSuccessListener { result ->
Log.d(TAG, "stored: ${result.getBytesStored()}")
}.addOnFailureListener { e ->
Log.e(TAG, “Failed to store bytes”, e)
}
} else {
Log.d(TAG, "E2EE is not available, only store bytes for D2D restore.")
}
}
Nasıl test edilir?
Geri yükleme akışlarını test etmek için geliştirme sırasında aşağıdaki yöntemleri kullanın.
Aynı cihazı kaldırma/yeniden yükleme
Kullanıcı, Yedekleme hizmetlerini etkinleştirirse (Ayarlar > Google > Yedekleme bölümünden kontrol edilebilir), Mağazanın Engelleme verileri, uygulamanın kaldırılması/yeniden yüklenmesi sırasında saklanır.
Aşağıdaki adımları uygulayarak test edebilirsiniz:
- BlockStore API'yi test uygulamanıza entegre edin.
- Verilerinizi depolamak için BlockStore API'yi çağırmak için test uygulamasını kullanın.
- Test uygulamanızı kaldırıp uygulamanızı aynı cihaza yeniden yükleyin.
- Verilerinizi almak amacıyla BlockStore API'yi çağırmak için test uygulamasını kullanın.
- Alınan baytların kaldırma işleminden önce depolananlarla aynı olduğunu doğrulayın.
Cihazdan cihaza
Çoğu durumda, bu işlem için hedef cihazın fabrika ayarlarına sıfırlanması gerekir. Daha sonra Android kablosuz geri yükleme akışını veya Google kablo geri yükleme özelliğini (desteklenen cihazlar için) girebilirsiniz.
Bulutta geri yükleme
- Blockstore API'yi test uygulamanıza entegre edin. Test uygulamasının Play Store'a gönderilmesi gerekir.
- Kaynak cihazda, verilerinizi depolamak için Blockstore API'yi çağırmak için test uygulamasını kullanın.
- O ve sonraki cihazlarda, Engelle mağazası bulut yedeğini manuel olarak tetikleyebilirsiniz: Ayarlar > Google > Yedekleme'ye gidin ve "Şimdi Yedekle" düğmesini tıklayın.
- Store Store bulut yedeklemesinin başarılı olduğunu doğrulamak için şunları yapabilirsiniz:
- Yedekleme tamamlandıktan sonra “CloudSyncBpTkSvc” etiketine sahip günlük satırlarını arayın.
- Şuna benzer satırlar görürsünüz: “......, CloudSyncBpTkSvc: senkronizasyon sonuç: SUCCESS, ..., yüklenen boyut: XXX bayt ...”
- Cloud Storage yedeklemesinden sonra 5 dakikalık bir "dinlenme süresi" vardır. Bu 5 dakika içinde, "Şimdi Yedekle" düğmesini tıkladığınızda başka bir Blok Mağaza bulut yedeği tetiklenmez.
- Store Store bulut yedeklemesinin başarılı olduğunu doğrulamak için şunları yapabilirsiniz:
- Hedef cihazı fabrika ayarlarına sıfırlayın ve buluta geri yükleme sürecinden geçin. Geri yükleme sürecinde test uygulamanızı geri yüklemeyi seçin. Bulut geri yükleme akışları hakkında daha fazla bilgi için Desteklenen bulut geri yükleme akışları başlıklı makaleye bakın.
- Hedef cihazda, verilerinizi almak amacıyla Blockstore API'yi çağırmak için test uygulamasını kullanın.
- Alınan baytların kaynak cihazda depolanan baytlarla aynı olduğunu doğrulayın.
Cihaz Gereksinimleri
Uçtan Uca Şifreleme
- Uçtan Uca şifreleme, Android 9 (API 29) ve sonraki sürümleri çalıştıran cihazlarda desteklenir.
- Uçtan uca şifrelemenin etkinleştirilmesi ve kullanıcı verilerinin doğru bir şekilde şifrelenmesi için cihazda PIN, desen veya şifre içeren bir ekran kilidi ayarlanmış olmalıdır.
Cihazdan Cihaza Geri Yükleme Akışı
Cihazdan cihaza geri yükleme işlemi için bir kaynak cihazınız ve bir hedef cihazınız olması gerekir. Bunlar, verileri aktaran iki cihazdır.
Kaynak cihazlar, yedekleme yapmak için Android 6 (API 23) ve sonraki bir sürümü çalıştırıyor olmalıdır.
Android 9 (API 29) ve sonraki sürümleri çalıştıran cihazları geri yükleyerek bu cihazları hedefleyebilirsiniz.
Cihazdan cihaza geri yükleme akışı hakkında daha fazla bilgiye buradan ulaşabilirsiniz.
Bulutta Yedekleme ve Geri Yükleme Akışı
Bulut yedekleme ve geri yükleme işlemi için bir kaynak cihaz ile bir hedef cihaz gereklidir.
Kaynak cihazlar, yedekleme yapmak için Android 6 (API 23) ve sonraki bir sürümü çalıştırıyor olmalıdır.
Hedef cihazlar, tedarikçilerine bağlı olarak desteklenir. Pixel cihazlar, Android 9 (API 29) sürümünden bu özelliği kullanabilir ve diğer tüm cihazların Android 12 (API 31) veya sonraki bir sürümü çalıştırıyor olması gerekir.