Skip to content

android: Exclude all data from backup#2160

Merged
gnprice merged 1 commit intozulip:mainfrom
gnprice:pr-backup
Feb 27, 2026
Merged

android: Exclude all data from backup#2160
gnprice merged 1 commit intozulip:mainfrom
gnprice:pr-backup

Conversation

@gnprice
Copy link
Copy Markdown
Member

@gnprice gnprice commented Feb 18, 2026

Fixes part of #2158, namely for Android.

Android (like iOS) has a feature automatically back up apps' data into the cloud, and a related feature to transfer data directly from one device to another (typically when first setting up a new device).

These features have some value when it comes to Zulip, but not a lot: the great bulk of the app's data comes from the user's Zulip server(s) anyway. And conversely, there is some data that shouldn't be backed up, because it shouldn't be duplicated off the device.

Right now, that describes the user's API keys: it's convenient not to have to log in again, but also potentially a security risk depending on how the backup is managed.

With the new "devices" and "push keys" APIs being introduced for end-to-end encrypted push notifications #1764, this will become a bigger issue:

  • If a new device restores a backup from an old device that's still online, then the two real devices will compete over what the push key and push token should be for the "device" object.

  • If a backup includes push keys, then it makes the security of the end-to-end encryption dependent on the security of the backup.

So just disable the backup feature entirely. We have a followup issue #2159 to track selectively re-enabling it where appropriate.

Upstream Android docs:
https://developer.android.com/identity/data/backup
https://developer.android.com/identity/data/autobackup#EnablingAutoBackup

@gnprice gnprice added the maintainer review PR ready for review by Zulip maintainers label Feb 18, 2026
@gnprice
Copy link
Copy Markdown
Member Author

gnprice commented Feb 18, 2026

@rajveermalviya would you pick up this PR from here, and also the rest of #2158 (i.e. the iOS side)?

I believe the only thing this PR needs is manual testing. See the issue's discussion of testing.

The easiest way to test is probably this Android Studio feature, new a few months ago:
https://developer.android.com/studio/releases/past-releases/as-narwhal-3-feature-drop-release-notes#test-backup-restore

There's also a pair of recipes documented here:
https://developer.android.com/identity/data/testingbackup
which are probably still easier than the fully manual way would be.

@rajveermalviya
Copy link
Copy Markdown
Member

I pushed a revision to fix the deprecation lint error, it updates AndroidManifest.xml and also adds related config files for:

@rajveermalviya
Copy link
Copy Markdown
Member

This should be ready for review now, @gnprice PTAL.

@gnprice
Copy link
Copy Markdown
Member Author

gnprice commented Feb 26, 2026

FTR here's the lint error that the previous revision was getting:

  /home/runner/work/zulip-flutter/zulip-flutter/android/app/src/main/AndroidManifest.xml:11: Error: The attribute android:allowBackup is deprecated from Android 12 and higher and may be removed in future versions. Consider adding the attribute android:dataExtractionRules specifying an @xml resource which configures cloud backups and device transfers on Android 12 and higher. [DataExtractionRules]
          android:allowBackup="false"
                               ~~~~~
  
     Explanation for issues of type "DataExtractionRules":
     Before Android 12, the attributes android:allowBackup and
     android:fullBackupContent were used to configure all forms of backup,
     including cloud backups, device-to-device transfers and adb backup.
  
     In Android 12 and higher, these attributes have been deprecated and will
     only apply to cloud backups. You should instead use the attribute
     android:dataExtractionRules, specifying an @xml resource that configures
     which files to back up, for cloud backups and for device-to-device
     transfers, separately. If your minSdkVersion supports older versions,
     you'll still want to specify an android:fullBackupContent resource if the
     default behavior is not right for your app.
  
     https://developer.android.com/about/versions/12/backup-restore#xml-changes
     https://goo.gle/DataExtractionRules

@rajveermalviya
Copy link
Copy Markdown
Member

rajveermalviya commented Feb 26, 2026

To confirm that backup/restore is actually disabled. I used the Android Studio's backup and restore features as documented here:

Basically to test the clean state (with backups enabled) on main:

  1. Run the app, have some state in the DB (like logged in to an account in some realm).
  2. While the app is running, in the Android Studio's menu bar: Run > Backup App Data.
  3. It will show a dialog, in that kept it to Device-to-Device backup type, gave it a path to store the backup file.
  4. And then to try to restore it, first uninstall the app, and then do a clean install via following commands:
$ adb uninstall com.zulipmobile
$ flutter build apk --debug && flutter install --debug
  1. Then restore the backup file via Android Studio: Run > Restore App Data > [Select the backup file].

Then I followed the steps 4 and 5, with the backup disabled. Confirming that the app created the DB from scratch.

–––

Just as a sanity check, I also tested the attributes one-by-one (android:dataExtractionRules, android:fullBackupContent and android:allowBackup="false") to confirm that all those attributes work correctly even as a standalone.

Fixes part of zulip#2158, namely for Android.

Android (like iOS) has a feature automatically back up apps' data
into the cloud, and a related feature to transfer data directly from
one device to another (typically when first setting up a new device).

These features have some value when it comes to Zulip, but not a lot:
the great bulk of the app's data comes from the user's Zulip
server(s) anyway.  And conversely, there is some data that shouldn't
be backed up, because it shouldn't be duplicated off the device.

Right now, that describes the user's API keys: it's convenient not to
have to log in again, but also potentially a security risk depending
on how the backup is managed.

With the new "devices" and "push keys" APIs being introduced for
end-to-end encrypted push notifications zulip#1764, this will become a
bigger issue:

  * If a new device restores a backup from an old device that's still
    online, then the two real devices will compete over what the push
    key and push token should be for the "device" object.

  * If a backup includes push keys, then it makes the security of the
    end-to-end encryption dependent on the security of the backup.

So just disable the backup feature entirely.  We have a followup
issue zulip#2159 to track selectively re-enabling it where appropriate.

Upstream Android docs:
  https://developer.android.com/identity/data/backup
  https://developer.android.com/identity/data/autobackup#EnablingAutoBackup

Co-authored-by: Rajesh Malviya <rmalviya@zulip.com>
@gnprice gnprice marked this pull request as ready for review February 27, 2026 02:06
@gnprice
Copy link
Copy Markdown
Member Author

gnprice commented Feb 27, 2026

Thanks for the testing and revision!

I added some comments to explain our reasoning; merging.

@gnprice gnprice merged commit 6bc975d into zulip:main Feb 27, 2026
2 checks passed
@gnprice gnprice deleted the pr-backup branch February 27, 2026 06:59
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

maintainer review PR ready for review by Zulip maintainers

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants