Sao lưu dữ liệu người dùng bằng tính năng Tự động sao lưu

Tự động sao lưu cho ứng dụng tự động sao lưu dữ liệu của người dùng từ các ứng dụng dành cho và chạy trên Android 6.0 (API cấp 23) trở lên. Android lưu giữ dữ liệu ứng dụng bằng cách tải dữ liệu đó lên Google Drive của người dùng — nơi dữ liệu được bảo vệ bằng thông tin đăng nhập Tài khoản Google của người dùng. Tính năng sao lưu được mã hoá hai đầu trên các thiết bị chạy Android 9 trở lên sử dụng mã PIN, hình mở khoá hoặc mật khẩu của thiết bị. Giới hạn 25 MB dữ liệu cho mỗi người dùng ứng dụng của bạn. Bạn sẽ không phải trả phí cho việc lưu dữ liệu sao lưu. Ứng dụng của bạn có thể tuỳ chỉnh quy trình sao lưu hoặc chọn không sao lưu bằng cách tắt tính năng sao lưu.

Để biết tổng quan về các tuỳ chọn sao lưu của Android và hướng dẫn về dữ liệu bạn cần sao lưu và khôi phục, hãy xem tổng quan về sao lưu dữ liệu.

Tệp được sao lưu

Theo mặc định, tính năng Tự động sao lưu bao gồm các tệp trong hầu hết các thư mục mà hệ thống gán cho ứng dụng của bạn:

Tính năng Tự động sao lưu loại trừ các tệp trong các thư mục được trả về bởi getCacheDir(), getCodeCacheDir(), và getNoBackupFilesDir(). Những tệp được lưu tại các vị trí này chỉ cần tạm thời và có chủ ý được loại khỏi các hoạt động sao lưu.

Bạn có thể định cấu hình ứng dụng để bao gồm và loại trừ các tệp cụ thể. Để biết thêm thông tin về vấn đề này, hãy xem mục bao gồm và loại trừ tệp.

Vị trí sao lưu

Dữ liệu sao lưu được lưu trữ trong một thư mục riêng trong tài khoản Google Drive của người dùng, giới hạn là 25 MB trên mỗi ứng dụng. Dữ liệu đã lưu không được tính vào hạn mức cá nhân của người dùng trên Google Drive. Chỉ có bản sao lưu gần đây nhất được lưu trữ. Khi thực hiện sao lưu, bản sao lưu trước đó (nếu có) sẽ bị xoá. Người dùng hoặc các ứng dụng khác trên thiết bị không thể đọc dữ liệu sao lưu.

Người dùng có thể xem danh sách các ứng dụng đã được sao lưu trong ứng dụng Android Google Drive. Trên thiết bị chạy Android, người dùng có thể tìm thấy danh sách này trong ngăn điều hướng của ứng dụng Drive trong phần Cài đặt > Sao lưu và đặt lại.

Bản sao lưu từ mỗi lần thiết lập thiết bị trong thời gian hoạt động được lưu trữ trong các tập dữ liệu riêng biệt, như thể hiện trong các ví dụ sau:

  • Nếu người dùng sở hữu hai thiết bị, thì tập dữ liệu sao lưu sẽ tồn tại cho mỗi thiết bị.

  • Nếu người dùng đặt lại thiết bị về trạng thái ban đầu và sau đó thiết lập thiết bị đó với cùng một tài khoản, thì bản sao lưu sẽ được lưu trữ trong một tập dữ liệu mới. Các tập dữ liệu lỗi thời sẽ tự động bị xoá sau một khoảng thời gian không hoạt động.

Lịch biểu sao lưu

Hoạt động sao lưu tự động diễn ra khi đáp ứng tất cả các điều kiện sau đây:

  • Người dùng đã bật tính năng sao lưu trên thiết bị. Trong Android 9, chế độ cài đặt này nằm trong phần Cài đặt > Hệ thống > Sao lưu.
  • Đã ít nhất 24 giờ trôi qua kể từ lần sao lưu gần đây nhất.
  • Thiết bị ở trạng thái rảnh.
  • Thiết bị được kết nối với mạng Wi-Fi (nếu người dùng thiết bị chưa chọn thực hiện sao lưu dữ liệu di động).

Trong thực tế, những điều kiện này xảy ra gần như mỗi đêm nhưng thiết bị có thể không bao giờ sao lưu được (ví dụ: nếu thiết bị chưa từng kết nối với mạng). Để tiết kiệm băng thông mạng, quá trình tải lên chỉ diễn ra nếu dữ liệu ứng dụng đã thay đổi.

Trong quá trình Tự động sao lưu, hệ thống sẽ tắt ứng dụng để đảm bảo rằng ứng dụng không còn ghi vào hệ thống tệp nữa. Theo mặc định, hệ thống sao lưu bỏ qua các ứng dụng đang chạy ở chế độ nền trước vì người dùng sẽ nhận thấy các ứng dụng của họ đang tắt. Bạn có thể ghi đè hành vi mặc định bằng cách đặt thuộc tính android;backupInForeground thành true (đúng).

Để đơn giản hoá quá trình kiểm thử, Android bao gồm các công cụ cho phép bạn tạo bản sao lưu thủ công cho ứng dụng của mình. Để biết thêm thông tin, hãy xem Kiểm thử bản sao lưu và khôi phục.

Khôi phục lịch biểu

Dữ liệu được khôi phục mỗi khi ứng dụng được cài đặt, từ Cửa hàng Play, trong quá trình thiết lập thiết bị (khi hệ thống cài đặt các ứng dụng đã cài đặt trước đó) hoặc từ khi chạy cài đặt adb. Thao tác khôi phục diễn ra sau khi APK được cài đặt, nhưng trước khi ứng dụng có sẵn cho người dùng khởi chạy.

Trong trình hướng dẫn thiết lập thiết bị ban đầu, người dùng nhìn thấy danh sách các tập dữ liệu sao lưu hiện có và được hỏi xem tập dữ liệu nào cần khôi phục dữ liệu. Bất kỳ tập dữ liệu sao lưu nào được chọn sẽ trở thành tập dữ liệu cấp trên cho thiết bị. Thiết bị có thể khôi phục từ bản sao lưu riêng hoặc từ tập dữ liệu cấp trên. Thiết bị ưu tiên sao lưu riêng nếu có sẵn các bản sao lưu từ cả hai nguồn. Nếu người dùng không thực hiện trình hướng dẫn thiết lập thiết bị, thì thiết bị chỉ có thể khôi phục từ bản sao lưu riêng.

Để đơn giản hoá quá trình kiểm thử, Android có những công cụ cho phép bạn bắt đầu khôi phục ứng dụng theo cách thủ công. Để biết thêm thông tin, hãy xem Kiểm thử bản sao lưu và khôi phục.

Bật và tắt tính năng sao lưu

Các ứng dụng dành cho Android 6.0 (API cấp 23) trở lên sẽ tự động bật tính năng Tự động sao lưu. Trong tệp kê khai ứng dụng của bạn, hãy đặt giá trị boolean android:allowBackup để bật hoặc tắt tính năng sao lưu. Giá trị mặc định là true. Nhưng để làm rõ ý định của mình, bạn nên đặt thuộc tính rõ ràng trong tệp kê khai như thể hiện dưới đây:

<manifest ... >
    ...
    <application android:allowBackup="true" ... >
        ...
    </application>
</manifest>

Bạn có thể tắt tính năng sao lưu bằng cách đặt android:allowBackup thành false. Bạn có thể muốn thực hiện việc này nếu ứng dụng của bạn có thể tạo lại trạng thái thông qua một số cơ chế khác hoặc nếu ứng dụng xử lý thông tin nhạy cảm mà Android không nên sao lưu.

Bao gồm và loại trừ tệp

Theo mặc định, hệ thống sao lưu hầu hết tất cả dữ liệu ứng dụng. Để biết thêm thông tin, hãy xem Các tệp đã sao lưu. Phần này cho bạn biết cách xác định các quy tắc XML tuỳ chỉnh để kiểm soát nội dung được sao lưu. Nếu ứng dụng của bạn dành cho Android 12 (API cấp 31) trở lên, bạn phải chỉ định một bộ quy tắc sao lưu XML bổ sung để hỗ trợ các thay đổi đối với việc khôi phục bản sao lưu được giới thiệu cho các thiết bị chạy Android 12 trở lên.

Kiểm soát việc sao lưu trên Android 11 trở xuống

Thực hiện theo các bước trong phần này để bao gồm hoặc loại trừ những tệp được sao lưu trên các thiết bị chạy Android 11 (API cấp 30) trở xuống.

  1. Trong AndroidManifest.xml, hãy thêm thuộc tính android:fullBackupContent vào phần tử <application>. Thuộc tính này trỏ đến một tệp XML chứa các quy tắc sao lưu. Ví dụ:

    <application ...
     android:fullBackupContent="@xml/backup_rules">
    </application>
    
  2. Tạo tệp XML có tên là @xml/backup_rules trong thư mục res/xml/. Bên trong tệp, hãy thêm các quy tắc có phần tử <include><exclude>. Mẫu sau đây sao lưu tất cả các tuỳ chọn chung, ngoại trừ device.xml:

    <?xml version="1.0" encoding="utf-8"?>
    <full-backup-content>
     <include domain="sharedpref" path="."/>
     <exclude domain="sharedpref" path="device.xml"/>
    </full-backup-content>
    

Xác định các điều kiện thiết bị cần có để sao lưu

Nếu ứng dụng của bạn lưu thông tin nhạy cảm trên thiết bị, bạn có thể chỉ định những điều kiện mà dữ liệu của ứng dụng được đưa vào bản sao lưu của người dùng. Bạn có thể thêm các điều kiện sau vào Android 9 (API cấp 28) trở lên:

Nếu đã nâng cấp các thiết bị phát triển lên Android 9, bạn cần tắt rồi bật lại tính năng sao lưu dữ liệu sau khi nâng cấp. Điều này là do Android chỉ mã hoá bản sao lưu bằng mã bí mật phía máy khách sau khi thông báo cho người dùng trong phần Cài đặt hoặc Trình hướng dẫn thiết lập.

Để khai báo các điều kiện đưa vào, hãy đặt thuộc tính requireFlags thành giá trị mong muốn hoặc các giá trị trong các phần tử <include> trong bộ quy tắc sao lưu của bạn:

backup_rules.xml

<?xml version="1.0" encoding="utf-8"?>
<full-backup-content>
    <!-- App data isn't included in user's backup
         unless client-side encryption is enabled. -->
    <include domain="file" path="."
             requireFlags="clientSideEncryption" />
</full-backup-content>

Nếu ứng dụng của bạn triển khai hệ thống sao lưu khoá-giá trị, hoặc nếu bạn tự triển khai BackupAgent, bạn cũng có thể áp dụng các yêu cầu có điều kiện này vào logic sao lưu của mình bằng cách thực hiện so sánh bitwise giữa bộ cờ truyền tải của đối tượng BackupDataOutput và bộ cờ FLAG_CLIENT_SIDE_ENCRYPTION_ENABLED hoặc FLAG_DEVICE_TO_DEVICE_TRANSFER của tác nhân sao lưu tuỳ chỉnh.

Đoạn mã sau đây cho thấy ví dụ về cách sử dụng phương thức này:

Kotlin

class CustomBackupAgent : BackupAgent() {
    override fun onBackup(oldState: ParcelFileDescriptor?,
            data: BackupDataOutput?, newState: ParcelFileDescriptor?) {
        if (data != null) {
            if ((data.transportFlags and
                    FLAG_CLIENT_SIDE_ENCRYPTION_ENABLED) != 0) {
                // Client-side backup encryption is enabled.
            }

            if ((data.transportFlags and FLAG_DEVICE_TO_DEVICE_TRANSFER) != 0) {
                // Local device-to-device transfer is enabled.
            }
        }
    }

    // Implementation of onRestore() here.
}

Java

public class CustomBackupAgent extends BackupAgent {
    @Override
    public void onBackup(ParcelFileDescriptor oldState, BackupDataOutput data,
            ParcelFileDescriptor newState) throws IOException {
        if ((data.getTransportFlags() &
                FLAG_CLIENT_SIDE_ENCRYPTION_ENABLED) != 0) {
            // Client-side backup encryption is enabled.
        }

        if ((data.getTransportFlags() &
                FLAG_DEVICE_TO_DEVICE_TRANSFER) != 0) {
            // Local device-to-device transfer is enabled.
        }
    }

    // Implementation of onRestore() here.
}

Kiểm soát việc sao lưu trên Android 12 trở lên

Nếu ứng dụng của bạn dành cho Android 12 (API cấp 31) trở lên, hãy thực hiện theo các bước trong phần này để bao gồm hoặc loại trừ các tệp được sao lưu trên các thiết bị đang chạy Android 12 trở lên.

  1. Trong AndroidManifest.xml, hãy thêm thuộc tính android:dataExtractionRules vào phần tử <application>. Thuộc tính này trỏ đến một tệp XML chứa các quy tắc sao lưu. Ví dụ:

    <application ...
     android:dataExtractionRules="backup_rules.xml">
    </application>
    
  2. Tạo tệp XML có tên là backup_rules.xml trong thư mục res/xml/. Bên trong tệp, hãy thêm các quy tắc có phần tử <include><exclude>. Mẫu sau đây sao lưu tất cả các tuỳ chọn chung, ngoại trừ device.xml:

    <?xml version="1.0" encoding="utf-8"?>
    <data-extraction-rules>
     <cloud-backup [disableIfNoEncryptionCapabilities="true|false"]>
       <include domain="sharedpref" path="."/>
       <exclude domain="sharedpref" path="device.xml"/>
     </cloud-backup>
    </data-extraction-rules>
    

Cú pháp cấu hình XML

Cú pháp XML cho tệp cấu hình sẽ thay đổi tuỳ thuộc vào phiên bản Android mà ứng dụng của bạn dành cho và chạy trên:

Android 11 trở xuống

Hãy sử dụng cú pháp XML sau cho tệp cấu hình kiểm soát quá trình sao lưu cho các thiết bị đang chạy Android 11 trở xuống.

<full-backup-content>
    <include domain=["file" | "database" | "sharedpref" | "external" |
                     "root"] path="string"
    requireFlags=["clientSideEncryption" | "deviceToDeviceTransfer"] />
    <exclude domain=["file" | "database" | "sharedpref" | "external" |
                     "root"] path="string" />
</full-backup-content>

Android 12 trở lên

Nếu ứng dụng của bạn dành cho Android 12 (API cấp độ 31) trở lên, hãy sử dụng cú pháp XML sau đây cho tệp cấu hình kiểm soát quá trình sao lưu cho các thiết bị chạy Android 12 trở lên.

<data-extraction-rules>
  <cloud-backup [disableIfNoEncryptionCapabilities="true|false"]>
    ...
    <include domain=["file" | "database" | "sharedpref" | "external" |
                        "root"] path="string"/>
    ...
    <exclude domain=["file" | "database" | "sharedpref" | "external" |
                        "root"] path="string"/>
    ...
  </cloud-backup>
  <device-transfer>
    ...
    <include domain=["file" | "database" | "sharedpref" | "external" |
                        "root"] path="string"/>
    ...
    <exclude domain=["file" | "database" | "sharedpref" | "external" |
                        "root"] path="string"/>
    ...
  </device-transfer>
</data-extraction-rules>

Mỗi phần của cấu hình (<cloud-backup>, <device-transfer>) chứa các quy tắc chỉ áp dụng cho loại chuyển dữ liệu cụ thể đó. Ví dụ: việc phân tách này cho phép bạn loại trừ một tệp hoặc thư mục khỏi bản sao lưu trên Google Drive trong khi vẫn chuyển dữ liệu trong quá trình chuyển từ thiết bị này sang thiết bị khác (D2D). Tính năng này có thể hữu ích nếu bạn có các tệp quá lớn nên không thể sao lưu vào đám mây. Tuy nhiên, bạn có thể chuyển các tệp này giữa các thiết bị mà không gặp vấn đề nào.

Nếu không có quy tắc nào cho một chế độ sao lưu cụ thể, chẳng hạn như nếu phần <device-transfer> bị thiếu, thì chế độ đó sẽ được bật hoàn toàn cho tất cả nội dung ngoại trừ thư mục no-backupcache, như mô tả trong Các tệp được sao lưu.

Ứng dụng của bạn có thể đặt cờ disableIfNoEncryptionCapabilities trong phần <cloud-backup> để đảm bảo rằng quá trình sao lưu chỉ xảy ra nếu có thể mã hoá được, chẳng hạn như khi người dùng có màn hình khoá. Khi đặt hạn chế này, bản sao lưu sẽ không được gửi tới đám mây nếu thiết bị của người dùng không thể hỗ trợ mã hoá. Tuy nhiên, do quá trình chuyển D2D không được gửi đến máy chủ, nên những bản sao lưu đó sẽ tiếp tục hoạt động ngay cả trên những thiết bị không hỗ trợ tính năng mã hoá.

Cú pháp để bao gồm và loại trừ các phần tử

Trong các thẻ <full-backup-content>, <cloud-backup><device-transfer> (tuỳ thuộc vào phiên bản Android của thiết bị và targetSDKVersion của ứng dụng), bạn có thể xác định các phần tử <include><exclude>:

<include>

Chỉ định một tệp hoặc thư mục cần sao lưu. Theo mặc định, tính năng Tự động sao lưu bao gồm hầu hết các tệp ứng dụng. Nếu bạn chỉ định một phần tử <include> thì theo mặc định, hệ thống sẽ không bao gồm bất kỳ tệp nào và chỉ sao lưu các tệp được chỉ định. Để bao gồm nhiều tệp, hãy sử dụng nhiều phần tử <include>.

Trên Android 11 trở xuống, phần tử này cũng có thể chứa thuộc tính requireFlags. Phần mô tả cách xác định các yêu cầu có điều kiện để sao lưu sẽ thảo luận chi tiết hơn về thuộc tính đó.

<exclude>

Chỉ định một tệp hoặc thư mục cần loại trừ trong quá trình sao lưu. Dưới đây là một số tệp thường bị loại trừ khỏi việc sao lưu:

  • Tệp có mã nhận dạng cụ thể theo thiết bị, do máy chủ cấp hoặc được tạo trên thiết bị. Ví dụ: Giải pháp gửi thông báo qua đám mây của Firebase (FCM) cần tạo mã thông báo đăng ký mỗi khi người dùng cài đặt ứng dụng của bạn trên một thiết bị mới. Nếu mã thông báo đăng ký cũ được khôi phục, ứng dụng có thể hoạt động không như mong muốn.

  • Các tệp liên quan đến việc gỡ lỗi ứng dụng.

  • Các tệp lớn khiến ứng dụng vượt quá hạn mức sao lưu 25 MB.

Mỗi phần tử <include><exclude> phải bao gồm hai thuộc tính sau:

domain

Chỉ định vị trí của tài nguyên. Các giá trị hợp lệ cho thuộc tính này bao gồm như sau:

  • root Thư mục trên hệ thống tệp, nơi lưu trữ tất cả các tệp riêng tư của ứng dụng này.
  • file Thư mục được getFilesDir() trả về.
  • database Thư mục được getDatabasePath() trả về. Cơ sở dữ liệu được tạo bằng SQLiteOpenHelper được lưu trữ ở đây.
  • sharedpref Thư mục lưu trữ SharedPreferences.
  • external Thư mục được getExternalFilesDir() trả về.
path

Chỉ định một tệp hoặc thư mục để bao gồm hoặc loại trừ khỏi bản sao lưu. Xin lưu ý những điều sau:

  • Thuộc tính này không hỗ trợ cú pháp ký tự đại diện hoặc biểu thức chính quy.
  • Bạn có thể tham chiếu thư mục hiện tại sử dụng ./, nhưng không thể tham chiếu thư mục chính .. vì lý do bảo mật.
  • Nếu bạn chỉ định một thư mục, thì quy tắc này sẽ áp dụng cho tất cả các tệp trong thư mục và thư mục con định kỳ.

Triển khai BackupAgent

Các ứng dụng triển khai tính năng Tự động sao lưu không cần phải triển khai BackupAgent. Tuy nhiên, bạn có thể tuỳ ý triển khai một BackupAgent tuỳ chỉnh. Thông thường, có hai lý do để làm điều này:

  • Bạn muốn nhận thông báo về các sự kiện sao lưu, chẳng hạn như onRestoreFinished()onQuotaExceeded(long, long). Các phương thức gọi lại này được thực thi ngay cả khi ứng dụng không chạy.

  • Bạn không thể dễ dàng biểu thị tập hợp các tệp bạn muốn sao lưu bằng các quy tắc XML. Trong một số ít trường hợp, bạn có thể triển khai BackupAgent ghi đè onFullBackup(FullBackupDataOutput) để lưu trữ nội dung mình muốn. Để duy trì cách triển khai mặc định của hệ thống, hãy gọi phương thức tương ứng trên siêu lớp bằng super.onFullBackup().

Nếu bạn triển khai một BackupAgent, theo mặc định, hệ thống dự kiến ứng dụng của bạn sẽ thực hiện sao lưu và khôi phục khoá/giá trị. Thay vào đó, để sử dụng tính năng Tự động sao lưu dựa trên tệp, hãy đặt thuộc tính android:fullBackupOnly thành true trong tệp kê khai của ứng dụng.

Trong quá trình diễn ra hoạt động tự động sao lưu và khôi phục, hệ thống khởi chạy ứng dụng ở chế độ hạn chế để ngăn ứng dụng truy cập vào các tệp có thể gây xung đột đồng thời cho phép ứng dụng thực thi các phương thức gọi lại trong BackupAgent của mình. Ở chế độ hạn chế này, hoạt động chính của ứng dụng không được tự động khởi chạy, Nhà cung cấp nội dung của ứng dụng không được khởi chạy và lớp cơ sở Application được tạo bản sao thay vì bất kỳ lớp con nào được khai báo trong tệp kê khai của ứng dụng.

BackupAgent của bạn phải triển khai các phương thức trừu tượng onBackup()onRestore(), dùng cho hệ thống sao lưu khoá-giá trị. Nếu không muốn thực hiện sao lưu khoá-giá trị, bạn chỉ cần để trống việc triển khai các phương thức đó.

Để biết thêm thông tin, hãy xem Mở rộng BackupAgent.