seguridad restaurar phone how google descargar copia android android-6.0-marshmallow android-backup-service

restaurar - ¿Cómo se prueba el comportamiento de la copia de seguridad completa de Android 6.0?



how to backup android phone to pc (2)

Después de haber discutido y probado varios escenarios (consulte los comentarios debajo de la pregunta), decidí combinar y escribir esos resultados en una respuesta. En realidad, esto no resuelve realmente el problema presentado, pero responderá a la pregunta "¿Cómo utiliza con éxito las herramientas de línea de comandos (o cualquier otra cosa) para probar el comportamiento de copia de seguridad y restauración de Android 6.0?" Lo hará en forma de una guía paso a paso que describe lo que funcionó para mí y cómo superé los diversos inconvenientes que conté en el camino.

Aquí va. Si aún no ha realizado la capacitación sobre " Configuración de copia de seguridad automática para aplicaciones ", le sugiero que lo haga primero. Documenta la función de copia de seguridad automática y ya hace un trabajo muy decente de documentar los distintos pasos.

Empecemos por el principio: ¡necesitamos una aplicación para probar! Al igual que CommonsWare, simplemente usé Android Studio para crear un nuevo proyecto con una actividad vacía . Asegúrese de configurar la API 23 como SDK de destino. Abra la MainActivity generada MainActivity y agregue algo de código en onCreate() para conservar un valor en las preferencias compartidas (o simplemente copie el fragmento de código de la pregunta):

PreferenceManager .getDefaultSharedPreferences(this) .edit() .putBoolean("foo", true) .apply();

Construye, implementa y ejecuta la aplicación. Esto debe hacer que foo persista, y se creará un archivo xml en el disco. Confirme esto con:

adb shell run-as <package_name> ls -al shared_prefs

El paquete de mi aplicación de prueba es com.example.mh.backuptest (que es lo que com.example.mh.backuptest en los comandos de ejemplo de aquí en adelante), por lo que mi comando es:

adb shell run-as com.example.mh.backuptest ls -al shared_prefs

Debería ver una sola línea de salida que enumera todos los archivos en la carpeta shared_prefs , que debe ser solo uno:

com.example.mh.backuptest_preferences.xml

Esto significa que el archivo de preferencias se creó correctamente y se escribió foo en él. Si lo desea, puede inspeccionar el contenido del archivo para confirmar esto.

Ahora, volviendo a las pruebas de copia de seguridad automática. En primer lugar, asegúrese de que está habilitado para realizar copias de seguridad automáticas de la aplicación. En su dispositivo Android 6.0, vaya a:

Settings > Backup & reset > Back up my data > On

Después de eso, active el registro detallado para el transporte de copia de seguridad y el analizador xml de copia de seguridad para que podamos ver lo que sucede:

adb shell setprop log.tag.GmsBackupTransport VERBOSE adb shell setprop log.tag.BackupXmlParserLogging VERBOSE

Luego, inicialice el administrador de respaldo:

adb shell bmgr run

Esto debería generar un poco de salida en logcat. Deberías ver al menos algo similar a esto:

D/AndroidRuntime: Calling main entry com.android.commands.bmgr.Bmgr V/BackupManagerService: Scheduling immediate backup pass V/BackupManagerService: Running a backup pass V/BackupManagerService: clearing pending backups V/PerformBackupTask: Beginning backup of 1 targets D/PerformBackupTask: invokeAgentForBackup on @pm@ I/BackupRestoreController: Getting widget state for user: 0 D/PerformBackupTask: starting key/value backup of BackupRequest{pkg=com.google.android.googlequicksearchbox} D/BackupManagerService: awaiting agent for ApplicationInfo{9f9289c com.google.android.googlequicksearchbox} D/BackupManagerService: agentConnected pkg=com.google.android.googlequicksearchbox agent=android.os.BinderProxy@dcdbafd I/BackupManagerService: got agent android.app.IBackupAgent$Stub$Proxy@c3fe3f2 D/PerformBackupTask: invokeAgentForBackup on com.google.android.googlequicksearchbox D/BackupHelperDispatcher: handling existing helper ''L'' com.android.launcher3.LauncherBackupHelper@7e2dcc3 V/LauncherBackupHelper: lastBackupTime = 1448612678367 W/LauncherBackupHelper: empty intent on application favorite: 223 I/BackupRestoreController: Getting widget state for user: 0 V/GmsBackupTransport: starting new backup session V/GmsBackupTransport: starting performBackup for com.google.android.googlequicksearchbox V/GmsBackupTransport: performBackup done for com.google.android.googlequicksearchbox V/GmsBackupTransport: sending request: 101667 bytes I/GmsBackupTransport: Http Response Code : 200 V/GmsBackupTransport: backup finished for com.google.android.googlequicksearchbox I/BackupManagerService: Backup pass finished.

No te preocupes si tu salida contiene mucho más. Intencionalmente quité las líneas que no son relevantes para la copia de seguridad. Solo pegué en la salida para cuando se realiza una copia de seguridad de una sola aplicación; Probablemente verá muchas más entradas la primera vez que ejecute este comando.

Si en cambio ves algo en la línea de:

GmsBackupTransport: Scotty transfer exception. null PFTBT : Error -1002 backing up com.example.mh.backuptest

O:

GmsBackupTransport: Rejecting full data backup. user has not seen up to date legal text

Asegúrese de que ha optado por hacer copias de seguridad automáticas de la aplicación (ver arriba) Si lo ha hecho y sigue viendo estos mensajes, lo que también sucedió para mí, intente cambiar la configuración varias veces y reiniciar el dispositivo. ¿Todavía no tienes suerte? He estado allí ... Retire la cuenta de Google del dispositivo, reinicie, vuelva a agregarla y opte de nuevo. Otros han reported que un restablecimiento de fábrica también funciona, pero eso me parece un poco exagerado. :)

Si llegaste tan lejos, ¡es hora de asegurarte de que se respalde nuestra aplicación de prueba! Para forzar una copia de seguridad, ejecute:

adb shell bmgr fullbackup com.example.mh.backuptest

Esto matará su aplicación si aún se está ejecutando, no se preocupe, eso es normal. Debería ver bastante salida del transporte de copia de seguridad:

D/AndroidRuntime: Calling main entry com.android.commands.bmgr.Bmgr D/BackupManagerService: fullTransportBackup() I/PFTBT: Initiating full-data transport backup of com.example.mh.backuptest V/GmsBackupTransport: create full backup for : com.example.mh.backuptest V/GmsBackupTransport: Start scotty uploading. D/BackupManagerService: Binding to full backup agent : com.example.mh.backuptest I/ActivityManager: Start proc 22032:com.example.mh.backuptest/u0a491 for backup android/FullBackupAgent D/BackupManagerService: awaiting agent for ApplicationInfo{dd359cd com.example.mh.backuptest} V/GmsBackupTransport: [READ] V/GmsBackupTransport: [READ] wait for avaible data. BackupManagerService: agentConnected pkg=com.example.mh.backuptest agent=android.os.BinderProxy@9e7e282 I/BackupManagerService: got agent android.app.IBackupAgent$Stub$Proxy@14b3d93 V/BackupXmlParserLogging: android:fullBackupContent - "true" I/BackupRestoreController: Getting widget state for user: 0 I/file_backup_helper: Name: apps/com.example.mh.backuptest/_manifest V/GmsBackupTransport: [PUSH] Push 512 bytes into pipe. V/GmsBackupTransport: [PUSH] signal data available. V/GmsBackupTransport: [PUSH] Wait for data been processed. V/GmsBackupTransport: [READ] Read 256 bytes data. V/GmsBackupTransport: [READ] V/GmsBackupTransport: [READ] Read 256 bytes data. V/GmsBackupTransport: [READ] signal data processed. V/GmsBackupTransport: [READ] V/GmsBackupTransport: [READ] wait for avaible data. V/GmsBackupTransport: [PUSH] Push 2048 bytes into pipe. V/GmsBackupTransport: [PUSH] signal data available. V/GmsBackupTransport: [PUSH] Wait for data been processed. V/GmsBackupTransport: [READ] Read 256 bytes data. V/GmsBackupTransport: [READ] V/GmsBackupTransport: [READ] Read 256 bytes data. V/GmsBackupTransport: [READ] V/GmsBackupTransport: [READ] Read 256 bytes data. V/GmsBackupTransport: [READ] V/GmsBackupTransport: [READ] Read 256 bytes data. V/GmsBackupTransport: [READ] V/GmsBackupTransport: [READ] Read 256 bytes data. V/GmsBackupTransport: [READ] V/GmsBackupTransport: [READ] Read 256 bytes data. V/GmsBackupTransport: [READ] V/GmsBackupTransport: [READ] Read 256 bytes data. V/GmsBackupTransport: [READ] V/GmsBackupTransport: [READ] Read 256 bytes data. V/GmsBackupTransport: [READ] signal data processed. V/GmsBackupTransport: [READ] V/GmsBackupTransport: [READ] wait for avaible data. D/BackupManagerService: Calling doFullBackup() on com.example.mh.backuptest I/file_backup_helper: Name: apps/com.example.mh.backuptest/sp/com.example.mh.backuptest_preferences.xml V/GmsBackupTransport: [PUSH] Push 512 bytes into pipe. V/GmsBackupTransport: [PUSH] signal data available. V/GmsBackupTransport: [PUSH] Wait for data been processed. V/GmsBackupTransport: [READ] Read 256 bytes data. V/GmsBackupTransport: [READ] V/GmsBackupTransport: [READ] Read 256 bytes data. V/GmsBackupTransport: [READ] signal data processed. V/GmsBackupTransport: [READ] V/GmsBackupTransport: [READ] wait for avaible data. V/GmsBackupTransport: [PUSH] Push 512 bytes into pipe. V/GmsBackupTransport: [PUSH] signal data available. V/GmsBackupTransport: [PUSH] Wait for data been processed. V/GmsBackupTransport: [READ] Read 256 bytes data. V/GmsBackupTransport: [READ] V/GmsBackupTransport: [READ] Read 256 bytes data. V/GmsBackupTransport: [READ] signal data processed. V/GmsBackupTransport: [READ] V/GmsBackupTransport: [READ] wait for avaible data. V/GmsBackupTransport: [FINISH] signal no more data. I/Process: Sending signal. PID: 22032 SIG: 9 I/ActivityManager: Process com.example.mh.backuptest (pid 22032) has died V/GmsBackupTransport: Scotty response: res=200 raw=3584 up=1047 I/PFTBT: Transport suggested backoff=0 I/PFTBT: Full backup completed. D/BackupManagerService: Done with full transport backup.

Con nuestra aplicación de prueba respaldada, veamos si de hecho también restaura los datos. Primero, eliminemos el archivo de preferencias que creó nuestra aplicación de prueba y que forma parte de la copia de seguridad automática predeterminada:

adb shell run-as com.example.mh.backuptest rm shared_prefs/com.example.mh.backuptest_preferences.xml

Confirme que el archivo ya no está allí:

adb shell run-as com.example.mh.backuptest ls -al shared_prefs

Si el comando se ejecuta sin ningún resultado, significa que no había archivos en la carpeta shared_prefs y que eliminó las preferencias con éxito.

Ahora, active una restauración para nuestra aplicación de prueba:

adb shell bmgr restore com.example.mh.backuptest

Una vez más, el transporte de copia de seguridad generará bastante salida:

V/BackupManagerService: beginRestoreSession: pkg=com.example.mh.backuptest transport=null V/RestoreSession: restorePackage pkg=com.example.mh.backuptest obs=android.app.backup.IRestoreObserver$Stub$Proxy@23829fa V/RestoreSession: restorePackage pkg=com.example.mh.backuptest token=31eda3bdfd5fddb7 D/BackupManagerService: MSG_RUN_RESTORE observer=android.app.backup.IRestoreObserver$Stub$Proxy@23829fa V/GmsBackupTransport: New restore session, 2 apps V/GmsBackupTransport: sending request: 471 bytes I/GmsBackupTransport: Http Response Code : 200 V/GmsBackupTransport: @pm@: 109 keys I/GmsBackupTransport: Current restore package : PackageInfo{195d280 @pm@} V/GmsBackupTransport: A key/value pairs restore D/BackupManagerService: initiateOneRestore packageName=@pm@ I/GmsBackupTransport: Current restore package : PackageInfo{1edd0b9 com.example.mh.backuptest} V/GmsBackupTransport: A full restore : https://www.googleapis.com/drive/v2/files/XXXXXXXXXXXXXXXXXXXXXXXXXXXX?alt=media&sources=ANDROID_BACKUP I/BackupManagerService: Next restore package: RestoreDescription{com.example.mh.backuptest : STREAM} V/GmsBackupTransport: Read first chunk for com.example.mh.backuptest V/GmsBackupTransport: Create http connection for com.example.mh.backuptest I/GmsBackupTransport: Drive download http response status : 200 V/GmsBackupTransport: ContentLength is 3584 V/GmsBackupTransport: Downloaded: 808 / 3584 bytes V/GmsBackupTransport: Read 808 Bytes V/GmsBackupTransport: Read next chunk for com.example.mh.backuptest V/GmsBackupTransport: Downloaded: 2197 / 3584 bytes V/GmsBackupTransport: Read 1389 Bytes I/RestoreEngine: Sig + version match; taking data V/GmsBackupTransport: Read next chunk for com.example.mh.backuptest V/GmsBackupTransport: Downloaded: 3584 / 3584 bytes V/GmsBackupTransport: Read 1387 Bytes V/GmsBackupTransport: Read next chunk for com.example.mh.backuptest V/GmsBackupTransport: Read -1 Bytes D/RestoreEngine: Need to launch agent for com.example.mh.backuptest D/RestoreEngine: Clearing app data preparatory to full restore I/ActivityManager: Force stopping com.example.mh.backuptest appid=10491 user=0: clear data V/GmsBackupTransport: Reach end of http content -- NO MORE DATA D/PackageBroadcastService: Received broadcast action=android.intent.action.PACKAGE_DATA_CLEARED and uri=com.example.mh.backuptest D/AccountUtils: Clearing selected account for com.example.mh.backuptest I/LocationSettingsChecker: Removing dialog suppression flag for package com.example.mh.backuptest I/Icing: doRemovePackageData com.example.mh.backuptest I/ActivityManager: Start proc 22708:com.example.mh.backuptest/u0a491 for backup android/FullBackupAgent D/BackupManagerService: awaiting agent for ApplicationInfo{dd359cd com.example.mh.backuptest} D/BackupManagerService: agentConnected pkg=com.example.mh.backuptest agent=android.os.BinderProxy@7875d75 I/BackupManagerService: got agent android.app.IBackupAgent$Stub$Proxy@9aa10a D/VoldConnector: SND -> {14 volume mkdirs /storage/emulated/0/Android/data/com.example.mh.backuptest/files/} D/VoldConnector: RCV <- {200 14 Command succeeded} V/BackupXmlParserLogging: android:fullBackupContent - "true" V/BackupManagerService: No more packages; finishing restore V/GmsBackupTransport: restore finished D/RestoreSession: endRestoreSession I/BackupRestoreController: restoreFinished for 0 I/BackupManagerService: Restore complete.

Si todo se ve como arriba, verifiquemos si nuestro archivo de preferencias está donde debería estar:

adb shell run-as com.example.mh.backuptest ls -al shared_prefs

La salida debe ser lo que vio la primera vez que ejecutó el comando (en las primeras etapas de esta historia bastante larga). Si es así, es hora de felicitaciones! ¡Has logrado hacer una copia de seguridad exitosa y restaurar tu aplicación usando la Copia de seguridad automática de Google para aplicaciones!

¿Contento? ¡Entonces hagamos una prueba más! Desinstala la aplicación:

adb uninstall com.example.mh.backuptest

Aunque veamos ''Éxito'', confirme que se ha ido:

adb shell run-as com.example.mh.backuptest

Rendimiento esperado:

run-as: Package ''com.example.mh.backuptest'' is unknown

Ahora, instale la aplicación de nuevo (pero no la inicie ):

adb install backuptest.apk

Echa un vistazo a logcat:

V/BackupManagerService: restoreAtInstall pkg=com.example.mh.backuptest token=3 restoreSet=31eda3bdfd5fddb7 D/BackupManagerService: MSG_RUN_RESTORE observer=null V/GmsBackupTransport: New restore session, 2 apps V/GmsBackupTransport: sending request: 471 bytes I/GmsBackupTransport: Http Response Code : 200 V/GmsBackupTransport: @pm@: 109 keys I/GmsBackupTransport: Current restore package : PackageInfo{2981234 @pm@} V/GmsBackupTransport: A key/value pairs restore D/BackupManagerService: initiateOneRestore packageName=@pm@ I/GmsBackupTransport: Current restore package : PackageInfo{883c85d com.example.mh.backuptest} V/GmsBackupTransport: A full restore : https://www.googleapis.com/drive/v2/files/XXXXXXXXXXXXXXXXXXXXXXXXXXXX?alt=media&sources=ANDROID_BACKUP I/BackupManagerService: Next restore package: RestoreDescription{com.example.mh.backuptest : STREAM} V/GmsBackupTransport: Read first chunk for com.example.mh.backuptest V/GmsBackupTransport: Create http connection for com.example.mh.backuptest I/GmsBackupTransport: Drive download http response status : 200 V/GmsBackupTransport: ContentLength is 3584 V/GmsBackupTransport: Downloaded: 808 / 3584 bytes V/GmsBackupTransport: Read 808 Bytes V/GmsBackupTransport: Read next chunk for com.example.mh.backuptest V/GmsBackupTransport: Downloaded: 2197 / 3584 bytes V/GmsBackupTransport: Read 1389 Bytes I/RestoreEngine: Sig + version match; taking data V/GmsBackupTransport: Read next chunk for com.example.mh.backuptest V/GmsBackupTransport: Downloaded: 3584 / 3584 bytes V/GmsBackupTransport: Read 1387 Bytes V/GmsBackupTransport: Read next chunk for com.example.mh.backuptest V/GmsBackupTransport: Read -1 Bytes D/RestoreEngine: Need to launch agent for com.example.mh.backuptest D/RestoreEngine: Clearing app data preparatory to full restore I/ActivityManager: Force stopping com.example.mh.backuptest appid=10493 user=0: clear data V/GmsBackupTransport: Reach end of http content -- NO MORE DATA D/PackageBroadcastService: Received broadcast action=android.intent.action.PACKAGE_DATA_CLEARED and uri=com.example.mh.backuptest D/AccountUtils: Clearing selected account for com.example.mh.backuptest I/LocationSettingsChecker: Removing dialog suppression flag for package com.example.mh.backuptest I/Icing: doRemovePackageData com.example.mh.backuptest I/ActivityManager: Start proc 31545:com.example.mh.backuptest/u0a493 for backup android/FullBackupAgent D/BackupManagerService: awaiting agent for ApplicationInfo{a84d42d com.example.mh.backuptest} D/BackupManagerService: agentConnected pkg=com.example.mh.backuptest agent=android.os.BinderProxy@b023d62 I/BackupManagerService: got agent android.app.IBackupAgent$Stub$Proxy@a742ef3 D/VoldConnector: SND -> {17 volume mkdirs /storage/emulated/0/Android/data/com.example.mh.backuptest/files/} D/VoldConnector: RCV <- {200 17 Command succeeded} V/BackupXmlParserLogging: android:fullBackupContent - "true" D/BackupManagerService: Restore complete, killing host process of com.example.mh.backuptest V/BackupManagerService: No more packages; finishing restore I/Process: Sending signal. PID: 31545 SIG: 9 V/GmsBackupTransport: restore finished I/BackupRestoreController: restoreFinished for 0 I/BackupManagerService: Restore complete.

¡Eso se ve prometedor! ¿Realmente restauró nuestro archivo de preferencia con copia de seguridad al reinstalar la aplicación?

adb shell run-as com.example.mh.backuptest ls -al shared_prefs

Si ve la salida que debería estar familiarizada a estas alturas, entonces la respuesta es sí.

Notas finales: He probado con éxito los pasos anteriores en varios dispositivos:

  • Emulador de Android 6.0 predeterminado (emulador64-x86) sin servicios de Google Play
  • Genymotion Google Nexus 5X - API 23 - VISTA PREVIA con los servicios de Google Play
  • Nexus 5X (dispositivo físico) con Google Play Services.

Si recuerdo correctamente, sin tener instalado Google Play Services en el dispositivo, el administrador de copias de seguridad no se va a Google Drive (lo que no sería sorprendente), pero sí puede corregirlo.

Fuentes:

TL; DR: ¿Cómo utilizas con éxito las herramientas de línea de comandos (o cualquier otra cosa) para probar el comportamiento de la copia de seguridad y restauración de Android 6.0, ya que no puedo hacer que restauren nada?

Como ya tenía problemas con una aplicación de ejemplo de mi libro que trataba de hacer que esto funcionara, comencé desde cero con el propósito de esta pregunta.

Creé un nuevo proyecto del asistente de nuevo proyecto de Android Studio 1.4.1, aceptando todos los valores predeterminados relevantes, excepto que fui con la plantilla "Actividad vacía" y agregué un 2 al ID de la aplicación y al nombre para mostrar. Luego agregué un poco de código a la actividad para darme algunos datos sobre el almacenamiento interno:

package com.commonsware.myapplication2; import android.os.Bundle; import android.preference.PreferenceManager; import android.support.v7.app.AppCompatActivity; public class MainActivity extends AppCompatActivity { @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); PreferenceManager .getDefaultSharedPreferences(this) .edit() .putBoolean("foo", true) .apply(); } }

adb shell run-as com.commonsware.myapplication2 ... la aplicación y confirmé, usando adb shell run-as com.commonsware.myapplication2 ... que el archivo SharedPreferences existía.

Luego ejecuté adb shell setprop log.tag.BackupXmlParserLogging VERBOSE , según los documentos. No hay problemas obvios.

Luego ejecuté adb shell bmgr run , según los documentos, que generó muchos mensajes de registro pero nada relacionado con mi aplicación, como se esperaba (y tampoco sugirió ningún problema en particular con el motor de respaldo).

Luego ejecuté adb shell bmgr fullbackup com.commonsware.myapplication2 , según los documentos, que generaron:

11-16 15:09:15.246 10372-10372/? D/AndroidRuntime: Calling main entry com.android.commands.bmgr.Bmgr 11-16 15:09:15.248 783-793/? D/BackupManagerService: fullTransportBackup() 11-16 15:09:15.249 783-10419/? I/PFTBT: Initiating full-data transport backup of com.commonsware.myapplication2 11-16 15:09:15.250 1406-1418/? I/GmsBackupTransport: Attempt to do full backup on com.commonsware.myapplication2 11-16 15:09:15.251 783-10419/? I/AccountManagerService: getTypesVisibleToCaller: isPermitted? true 11-16 15:09:15.257 1325-1325/? V/GLSActivity: AuthDelegateWrapperCreated with selected intent: Intent { cmp=com.google.android.gms/.auth.DefaultAuthDelegateService } 11-16 15:09:15.259 783-2127/? I/AccountManagerService: getTypesVisibleToCaller: isPermitted? true 11-16 15:09:15.262 1325-1325/? V/GLSActivity: AuthDelegateWrapperCreated with selected intent: Intent { cmp=com.google.android.gms/.auth.DefaultAuthDelegateService } 11-16 15:09:15.264 1325-1325/? V/GLSActivity: AuthDelegateWrapperCreated with selected intent: Intent { cmp=com.google.android.gms/.auth.DefaultAuthDelegateService } 11-16 15:09:15.284 1406-1418/? V/GmsBackupTransport: create full backup for : com.commonsware.myapplication2 11-16 15:09:15.286 1406-10421/? V/GmsBackupTransport: Start scotty uploading. 11-16 15:09:15.287 783-10422/? D/BackupManagerService: Binding to full backup agent : com.commonsware.myapplication2 11-16 15:09:15.291 783-10422/? D/BackupManagerService: awaiting agent for ApplicationInfo{75f37e2 com.commonsware.myapplication2} 11-16 15:09:15.292 783-1544/? D/BackupManagerService: agentConnected pkg=com.commonsware.myapplication2 agent=android.os.BinderProxy@e073ad3 11-16 15:09:15.293 783-10422/? I/BackupManagerService: got agent android.app.IBackupAgent$Stub$Proxy@f328610 11-16 15:09:15.299 783-1552/? D/VoldConnector: SND -> {8 volume mkdirs /storage/emulated/0/Android/data/com.commonsware.myapplication2/files/} 11-16 15:09:15.302 783-878/? D/VoldConnector: RCV <- {200 8 Command succeeded} 11-16 15:09:15.302 7953-7965/com.commonsware.myapplication2 V/BackupXmlParserLogging: android:fullBackupContent - "true" 11-16 15:09:15.309 783-10422/? I/BackupRestoreController: Getting widget state for user: 0 11-16 15:09:15.312 783-10425/? I/file_backup_helper: Name: apps/com.commonsware.myapplication2/_manifest 11-16 15:09:15.313 783-10425/? D/BackupManagerService: Calling doFullBackup() on com.commonsware.myapplication2 11-16 15:09:15.320 7953-7967/com.commonsware.myapplication2 I/file_backup_helper: Name: apps/com.commonsware.myapplication2/sp/com.commonsware.myapplication2_preferences.xml 11-16 15:09:15.325 7953-7953/com.commonsware.myapplication2 I/Process: Sending signal. PID: 7953 SIG: 9 11-16 15:09:15.337 783-2131/? D/GraphicsStats: Buffer count: 4 11-16 15:09:15.337 783-2131/? I/WindowState: WIN DEATH: Window{d0be7fd u0 com.commonsware.myapplication2/com.commonsware.myapplication2.MainActivity} 11-16 15:09:15.357 783-2124/? I/ActivityManager: Process com.commonsware.myapplication2 (pid 7953) has died 11-16 15:09:15.357 783-2124/? W/ActivityManager: Force removing ActivityRecord{d9c7ab7 u0 com.commonsware.myapplication2/.MainActivity t1146}: app died, no saved state 11-16 15:09:15.374 783-2124/? I/ActivityManager: Config changes=480 {1.0 310mcc?mnc en_US ldltr sw360dp w360dp h568dp 480dpi nrml port finger -keyb/v/h -nav/h s.9} 11-16 15:09:15.414 783-876/? I/InputReader: Reconfiguring input devices. changes=0x00000004 11-16 15:09:15.414 783-876/? I/InputReader: Device reconfigured: id=4, name=''touch_dev'', size 1080x1920, orientation 0, mode 1, display id 0 11-16 15:09:15.441 917-1161/? E/Surface: getSlotFromBufferLocked: unknown buffer: 0x9cfd78f0 11-16 15:09:15.446 783-1649/? W/InputMethodManagerService: Got RemoteException sending setActive(false) notification to pid 7953 uid 10193 11-16 15:09:15.447 1477-1477/? I/Keyboard.Facilitator: onFinishInput() 11-16 15:09:15.513 3287-3287/? W/LocationOracle: Best location was null 11-16 15:09:15.551 3287-10448/? I/MicroRecognitionRnrImpl: Starting detection. 11-16 15:09:15.556 3287-10452/? I/MicrophoneInputStream: mic_starting com.google.android.apps.gsa.speech.audio.aa@5e3e5da 11-16 15:09:15.564 783-801/? I/WindowManager: Screen frozen for +201ms due to Window{48728f7 u0 com.android.systemui.ImageWallpaper} 11-16 15:09:15.566 199-10454/? I/AudioFlinger: AudioFlinger''s thread 0xb2600000 ready to run 11-16 15:09:15.570 3287-10452/? I/MicrophoneInputStream: mic_started com.google.android.apps.gsa.speech.audio.aa@5e3e5da 11-16 15:09:15.579 199-10454/? D/audio_hw_primary: select_devices: out_snd_device(0: none) in_snd_device(61: voice-rec-mic) 11-16 15:09:15.580 199-10454/? D/msm8974_platform: platform_send_audio_calibration: sending audio calibration for snd_device(61) acdb_id(62) 11-16 15:09:15.580 199-10454/? D/: Failed to fetch the lookup information of the device 0000003E 11-16 15:09:15.580 199-10454/? E/ACDB-LOADER: Error: ACDB AudProc vol returned = -19 11-16 15:09:15.580 199-10454/? D/audio_hw_primary: enable_snd_device: snd_device(61: voice-rec-mic) 11-16 15:09:15.583 199-10454/? D/audio_hw_primary: enable_audio_route: apply and update mixer path: audio-record 11-16 15:09:15.641 1406-1593/? D/GCoreFlp: FLP HAL exists but batch size is <= 0. Disabling FLP HAL. 11-16 15:09:15.649 783-2126/? D/WifiService: acquireWifiLockLocked: WifiLock{NlpWifiLock type=2 binder=android.os.BinderProxy@6b83dff} 11-16 15:09:15.651 783-897/? D/wifi: Initialized common fields 10000, 16, 100, 10 11-16 15:09:15.651 783-897/? D/wifi: bucket[0] = 2:3:10000:2 11-16 15:09:15.670 3287-3287/? W/MicroDetectionWorkerImp: Tag [MicroDetectionWorkerImpl] is too long; truncated to [MicroDetectionWorkerImp] 11-16 15:09:15.670 3287-3287/? I/MicroDetectionWorkerImp: onReady 11-16 15:09:15.971 3456-3476/? W/OpenGLRenderer: Incorrectly called buildLayer on View: ShortcutAndWidgetContainer, destroying layer... 11-16 15:09:16.065 1406-10421/? V/GmsBackupTransport: Scotty response: res=200 raw=2560 up=2560 11-16 15:09:16.069 783-10419/? I/PFTBT: Transport suggested backoff=0 11-16 15:09:16.083 783-10419/? I/PFTBT: Full backup completed. 11-16 15:09:16.084 783-793/? D/BackupManagerService: Done with full transport backup.

Nada parece indicar un error u otra falla en la copia de seguridad.

Luego borré el archivo SharedPreferences manualmente, a través de:

adb shell run-as com.commonsware.myapplication2 rm /data/data/com.commonsware.myapplication2/shared_prefs/com.commonsware.myapplication2_preferences.xml

y confirmó que el archivo SharedPreferences ya no existe.

Luego ejecuté adb shell bmgr restore com.commonsware.myapplication2 , según los documentos. Esto generó otro conjunto de mensajes de registro, con algunos errores aparentes:

11-16 15:13:01.692 10593-10593/? D/AndroidRuntime: Calling main entry com.android.commands.bmgr.Bmgr 11-16 15:13:01.694 783-941/? V/BackupManagerService: beginRestoreSession: pkg=com.commonsware.myapplication2 transport=null 11-16 15:13:01.696 783-794/? V/RestoreSession: restorePackage pkg=com.commonsware.myapplication2 obs=android.app.backup.IRestoreObserver$Stub$Proxy@b011dce 11-16 15:13:01.696 783-794/? V/RestoreSession: restorePackage pkg=com.commonsware.myapplication2 token=3dd6ad03f250d4cb 11-16 15:13:01.696 783-900/? D/BackupManagerService: MSG_RUN_RESTORE observer=android.app.backup.IRestoreObserver$Stub$Proxy@b011dce 11-16 15:13:01.700 783-900/? I/AccountManagerService: getTypesVisibleToCaller: isPermitted? true 11-16 15:13:01.703 1325-1325/? V/GLSActivity: AuthDelegateWrapperCreated with selected intent: Intent { cmp=com.google.android.gms/.auth.DefaultAuthDelegateService } 11-16 15:13:01.705 783-1552/? I/AccountManagerService: getTypesVisibleToCaller: isPermitted? true 11-16 15:13:01.707 1325-1325/? V/GLSActivity: AuthDelegateWrapperCreated with selected intent: Intent { cmp=com.google.android.gms/.auth.DefaultAuthDelegateService } 11-16 15:13:01.708 1325-1325/? V/GLSActivity: AuthDelegateWrapperCreated with selected intent: Intent { cmp=com.google.android.gms/.auth.DefaultAuthDelegateService } 11-16 15:13:01.991 1406-1682/? I/GmsBackupTransport: Http Response Code : 200 11-16 15:13:01.995 1406-1887/? I/GmsBackupTransport: Current restore package : PackageInfo{f7f23bd @pm@} 11-16 15:13:01.996 783-900/? D/BackupManagerService: initiateOneRestore packageName=@pm@ 11-16 15:13:02.008 1406-1417/? I/GmsBackupTransport: Current restore package : PackageInfo{733fdb2 com.commonsware.myapplication2} 11-16 15:13:02.009 783-900/? I/BackupManagerService: Next restore package: RestoreDescription{com.commonsware.myapplication2 : STREAM} 11-16 15:13:02.023 783-10612/? I/AccountManagerService: getTypesVisibleToCaller: isPermitted? true 11-16 15:13:02.213 1406-1418/? I/GmsBackupTransport: Drive download http response status : 401 11-16 15:13:02.282 783-10612/? I/AccountManagerService: getTypesVisibleToCaller: isPermitted? true 11-16 15:13:02.311 783-10612/? I/AccountManagerService: getTypesVisibleToCaller: isPermitted? true 11-16 15:13:02.319 1325-1325/? V/GLSActivity: AuthDelegateWrapperCreated with selected intent: Intent { cmp=com.google.android.gms/.auth.DefaultAuthDelegateService } 11-16 15:13:02.321 783-1552/? I/AccountManagerService: getTypesVisibleToCaller: isPermitted? true 11-16 15:13:02.516 783-884/? D/WifiStateMachine: starting scan for "cw"WPA_PSK with 2427,5180 11-16 15:13:02.517 783-886/? D/ConnectivityService: updateNetworkScore for NetworkAgentInfo [WIFI () - 100] to 60 11-16 15:13:02.517 783-886/? D/ConnectivityService: rematching NetworkAgentInfo [WIFI () - 100] 11-16 15:13:02.695 1406-1418/? I/GmsBackupTransport: Reading next chunk on full restore - IOException 11-16 15:13:09.611 783-10612/? I/AccountManagerService: getTypesVisibleToCaller: isPermitted? true 11-16 15:13:09.808 1406-1418/? I/GmsBackupTransport: Drive download http response status : 401 11-16 15:13:09.834 783-10612/? I/AccountManagerService: getTypesVisibleToCaller: isPermitted? true 11-16 15:13:09.884 783-10612/? I/AccountManagerService: getTypesVisibleToCaller: isPermitted? true 11-16 15:13:09.892 1325-1325/? V/GLSActivity: AuthDelegateWrapperCreated with selected intent: Intent { cmp=com.google.android.gms/.auth.DefaultAuthDelegateService } 11-16 15:13:09.894 783-2126/? I/AccountManagerService: getTypesVisibleToCaller: isPermitted? true 11-16 15:13:09.897 1325-1325/? V/GLSActivity: AuthDelegateWrapperCreated with selected intent: Intent { cmp=com.google.android.gms/.auth.DefaultAuthDelegateService } 11-16 15:13:09.898 1325-1325/? V/GLSActivity: AuthDelegateWrapperCreated with selected intent: Intent { cmp=com.google.android.gms/.auth.DefaultAuthDelegateService } 11-16 15:13:10.110 1406-1418/? I/GmsBackupTransport: Reading next chunk on full restore - IOException 11-16 15:13:10.110 1406-1418/? E/GmsBackupTransport: HTTP reading error: java.io.IOException: Unauthorized full data restore request 11-16 15:13:10.110 1406-1418/? E/GmsBackupTransport: Fail to read full backup data chunk : java.io.IOException: Unauthorized full data restore request 11-16 15:13:10.112 783-10612/? E/StreamFeederThread: Error -1002 streaming restore for com.commonsware.myapplication2 11-16 15:13:10.119 783-10612/? I/ActivityManager: Force stopping com.commonsware.myapplication2 appid=10193 user=0: clear data 11-16 15:13:10.140 783-796/? I/ActivityManager: Start proc 10623:com.android.documentsui/u0a36 for broadcast com.android.documentsui/.PackageReceiver 11-16 15:13:10.174 10623-10623/? W/System: ClassLoader referenced unknown path: /system/app/DocumentsUI/lib/arm 11-16 15:13:10.198 1440-10637/? D/PackageBroadcastService: Received broadcast action=android.intent.action.PACKAGE_DATA_CLEARED and uri=com.commonsware.myapplication2 11-16 15:13:10.198 1440-10637/? D/AccountUtils: Clearing selected account for com.commonsware.myapplication2 11-16 15:13:10.203 1440-10637/? I/LocationSettingsChecker: Removing dialog suppression flag for package com.commonsware.myapplication2 11-16 15:13:10.208 1440-2449/? I/Icing: doRemovePackageData com.commonsware.myapplication2 11-16 15:13:10.232 783-900/? V/BackupManagerService: No more packages; finishing restore 11-16 15:13:10.234 783-900/? I/BackupRestoreController: restoreFinished for 0 11-16 15:13:10.234 783-900/? I/BackupManagerService: Restore complete. 11-16 15:13:10.234 783-793/? D/RestoreSession: endRestoreSession 11-16 15:13:10.234 10593-10593/? D/AndroidRuntime: Shutting down VM 11-16 15:13:10.235 783-900/? V/BackupManagerService: Clearing restore session and halting timeout 11-16 15:13:10.279 783-1544/? I/ActivityManager: Start proc 10661:com.android.externalstorage/u0a6 for content provider com.android.externalstorage/.ExternalStorageProvider 11-16 15:13:10.301 10661-10661/? W/System: ClassLoader referenced unknown path: /system/priv-app/ExternalStorageProvider/lib/arm 11-16 15:13:10.307 10661-10661/? D/ExternalStorage: After updating volumes, found 1 active roots 11-16 15:13:10.336 783-1544/? I/ActivityManager: Start proc 10675:com.android.shell/2000 for content provider com.android.shell/.BugreportStorageProvider 11-16 15:13:10.360 10675-10675/? W/System: ClassLoader referenced unknown path: /system/priv-app/Shell/lib/arm 11-16 15:13:10.371 10623-10636/? D/Documents: Update found 7 roots in 156ms 11-16 15:13:10.377 10623-10674/? D/Documents: Update found 7 roots in 65ms 11-16 15:13:14.635 783-886/? D/ConnectivityService: updateNetworkScore for NetworkAgentInfo [WIFI () - 100] to 56 11-16 15:13:14.635 783-886/? D/ConnectivityService: rematching NetworkAgentInfo [WIFI () - 100] 11-16 15:13:17.617 783-2632/? D/NetlinkSocketObserver: NeighborEvent{elapsedMs=2866928, 192.168.3.1, [000DB9340C50], RTM_NEWNEIGH, NUD_STALE} 11-16 15:13:22.520 783-884/? D/WifiStateMachine: starting scan for "cw"WPA_PSK with 2427,5180 11-16 15:13:23.729 783-886/? D/ConnectivityService: updateNetworkScore for NetworkAgentInfo [WIFI () - 100] to 60 11-16 15:13:23.731 783-886/? D/ConnectivityService: rematching NetworkAgentInfo [WIFI () - 100]

El subconjunto preocupante de eso es:

11-16 15:13:10.110 1406-1418/? I/GmsBackupTransport: Reading next chunk on full restore - IOException 11-16 15:13:10.110 1406-1418/? E/GmsBackupTransport: HTTP reading error: java.io.IOException: Unauthorized full data restore request 11-16 15:13:10.110 1406-1418/? E/GmsBackupTransport: Fail to read full backup data chunk : java.io.IOException: Unauthorized full data restore request 11-16 15:13:10.112 783-10612/? E/StreamFeederThread: Error -1002 streaming restore for com.commonsware.myapplication2

Y, efectivamente, el archivo no se restaura. No tengo idea de lo que significa una "Solicitud de restauración de datos completa no autorizada".

Entonces, desinstalé la aplicación (a través de gradle uninstallDebug ) y la instalé de nuevo sin ejecutarla (a través de gradle installDebug ). De acuerdo con la documentación, "Puede probar la restauración automática de su aplicación si desinstala y la vuelve a instalar. Los datos de la aplicación se restauran automáticamente desde la nube una vez que se completa la instalación de la aplicación". Sin embargo, unos minutos después de SharedPreferences instalarlo, el archivo SharedPreferences aún no existe.

Luego volví a ejecutar adb shell bmgr restore com.commonsware.myapplication2 y obtuve un conjunto similar de declaraciones de registro, con el mismo mensaje "Solicitud de restauración de datos completa no autorizada".

¿Hay pasos en este proceso que me falten o que no estén documentados?

EDITAR : había estado probando en hardware real (un Nexus 6). Según el comentario de MH, probé este procedimiento en un emulador de Android 6.0 (sin Servicios de Juego), y funciona. Eso sugiere que la documentación no está completamente equivocada, aunque todavía plantea la pregunta de por qué no funciona con hardware.


Encontré un error en Android 6.0, donde a veces mataría incluso a un servicio de primer plano fijo para ejecutarlo doFullBackup(), y no lo reiniciaría durante horas. Esto es problemático si su aplicación necesita ejecutarse sin interrupción mientras el teléfono se está cargando (Chroma Doze es un generador de ruido blanco, por lo que a menudo se ejecuta mientras el usuario está dormido):

01-22 03:01:00.303 879 25791 I PFTBT : Initiating full-data transport backup of net.pmarks.chromadoze 01-22 03:01:00.470 879 25793 D BackupManagerService: Binding to full backup agent : net.pmarks.chromadoze 01-22 03:01:00.470 879 25793 D BackupManagerService: awaiting agent for ApplicationInfo{8ab9ee7 net.pmarks.chromadoze} 01-22 03:01:00.482 879 8822 D BackupManagerService: agentConnected pkg=net.pmarks.chromadoze agent=android.os.BinderProxy@3428a8a 01-22 03:01:00.482 879 25793 I BackupManagerService: got agent android.app.IBackupAgent$Stub$Proxy@a4738fb 01-22 03:01:00.525 879 25793 I BackupRestoreController: Getting widget state for user: 0 01-22 03:01:00.527 879 25796 D BackupManagerService: Calling doFullBackup() on net.pmarks.chromadoze 01-22 03:01:00.554 879 8821 I WindowState: WIN DEATH: Window{7b1ddb4 u0 net.pmarks.chromadoze/net.pmarks.chromadoze.ChromaDoze} 01-22 03:01:00.570 879 3721 I ActivityManager: Process net.pmarks.chromadoze (pid 18451) has died 01-22 03:01:00.570 879 3721 W ActivityManager: Scheduling restart of crashed service net.pmarks.chromadoze/.NoiseService in 13305612ms

Esto solo afecta a las aplicaciones con targetSdkVersion 23, pero una vez que haya publicado una aplicación de este tipo, volver a 22es imposible: los usuarios que intenten instalar la próxima versión lo verán (Error -504)en Play Store.

Hay dos soluciones que conozco:

  • Establecer android:allowBackup="false"en su manifiesto para deshabilitar todas las copias de seguridad.
  • Implementar un android:backupAgent, que (eventualmente) desactiva las copias de seguridad completas y utiliza la API de copia de seguridad antigua en su lugar.

Sin embargo, si tiene una targetSdkVersion 23aplicación instalada sin una backupAgent, la adición backupAgentno desactiva las copias de seguridad completas de inmediato; debe reiniciar el dispositivo para eliminarlo de la cola.

Para ver qué aplicaciones recibirán una copia de seguridad completa, puede ejecutar lo siguiente:

$ adb shell dumpsys backup

Y luego busque la Full backup queue:sección.