summaryrefslogtreecommitdiffstats
path: root/browser/components/backup/resources/PlacesBackupResource.sys.mjs
diff options
context:
space:
mode:
Diffstat (limited to 'browser/components/backup/resources/PlacesBackupResource.sys.mjs')
-rw-r--r--browser/components/backup/resources/PlacesBackupResource.sys.mjs69
1 files changed, 54 insertions, 15 deletions
diff --git a/browser/components/backup/resources/PlacesBackupResource.sys.mjs b/browser/components/backup/resources/PlacesBackupResource.sys.mjs
index 1955406f51..3a9433e67c 100644
--- a/browser/components/backup/resources/PlacesBackupResource.sys.mjs
+++ b/browser/components/backup/resources/PlacesBackupResource.sys.mjs
@@ -10,7 +10,6 @@ const lazy = {};
ChromeUtils.defineESModuleGetters(lazy, {
BookmarkJSONUtils: "resource://gre/modules/BookmarkJSONUtils.sys.mjs",
PrivateBrowsingUtils: "resource://gre/modules/PrivateBrowsingUtils.sys.mjs",
- Sqlite: "resource://gre/modules/Sqlite.sys.mjs",
});
XPCOMUtils.defineLazyPreferenceGetter(
@@ -26,6 +25,8 @@ XPCOMUtils.defineLazyPreferenceGetter(
false
);
+const BOOKMARKS_BACKUP_FILENAME = "bookmarks.jsonlz4";
+
/**
* Class representing Places database related files within a user profile.
*/
@@ -38,8 +39,11 @@ export class PlacesBackupResource extends BackupResource {
return false;
}
+ static get priority() {
+ return 1;
+ }
+
async backup(stagingPath, profilePath = PathUtils.profileDir) {
- const sqliteDatabases = ["places.sqlite", "favicons.sqlite"];
let canBackupHistory =
!lazy.PrivateBrowsingUtils.permanentPrivateBrowsing &&
!lazy.isSanitizeOnShutdownEnabled &&
@@ -52,7 +56,7 @@ export class PlacesBackupResource extends BackupResource {
if (!canBackupHistory) {
let bookmarksBackupFile = PathUtils.join(
stagingPath,
- "bookmarks.jsonlz4"
+ BOOKMARKS_BACKUP_FILENAME
);
await lazy.BookmarkJSONUtils.exportToFile(bookmarksBackupFile, {
compress: true,
@@ -60,25 +64,60 @@ export class PlacesBackupResource extends BackupResource {
return { bookmarksOnly: true };
}
- for (let fileName of sqliteDatabases) {
- let sourcePath = PathUtils.join(profilePath, fileName);
- let destPath = PathUtils.join(stagingPath, fileName);
- let connection;
+ // These are copied in parallel because they're attached[1], and we don't
+ // want them to get out of sync with one another.
+ //
+ // [1]: https://www.sqlite.org/lang_attach.html
+ await Promise.all([
+ BackupResource.copySqliteDatabases(profilePath, stagingPath, [
+ "places.sqlite",
+ ]),
+ BackupResource.copySqliteDatabases(profilePath, stagingPath, [
+ "favicons.sqlite",
+ ]),
+ ]);
+
+ return null;
+ }
- try {
- connection = await lazy.Sqlite.openConnection({
- path: sourcePath,
- readOnly: true,
- });
+ async recover(manifestEntry, recoveryPath, destProfilePath) {
+ if (!manifestEntry) {
+ const simpleCopyFiles = ["places.sqlite", "favicons.sqlite"];
+ await BackupResource.copyFiles(
+ recoveryPath,
+ destProfilePath,
+ simpleCopyFiles
+ );
+ } else {
+ const { bookmarksOnly } = manifestEntry;
- await connection.backup(destPath);
- } finally {
- await connection.close();
+ /**
+ * If the recovery file only has bookmarks backed up, pass the file path to postRecovery()
+ * so that we can import all bookmarks into the new profile once it's been launched and restored.
+ */
+ if (bookmarksOnly) {
+ let bookmarksBackupPath = PathUtils.join(
+ recoveryPath,
+ BOOKMARKS_BACKUP_FILENAME
+ );
+ return { bookmarksBackupPath };
}
}
+
return null;
}
+ async postRecovery(postRecoveryEntry) {
+ if (postRecoveryEntry?.bookmarksBackupPath) {
+ await lazy.BookmarkJSONUtils.importFromFile(
+ postRecoveryEntry.bookmarksBackupPath,
+ {
+ replace: true,
+ }
+ );
+ }
+ }
+
async measure(profilePath = PathUtils.profileDir) {
let placesDBPath = PathUtils.join(profilePath, "places.sqlite");
let faviconsDBPath = PathUtils.join(profilePath, "favicons.sqlite");