From bce40f328850f41da5265f7a69e4d8d976b7e9e2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C5=82=20Buczek?= Date: Fri, 7 Dec 2018 17:19:02 +0100 Subject: [PATCH] Fix #593: Bookmark order migration (#602) --- Client/Application/Migration.swift | 5 +++++ Data/models/Bookmark.swift | 34 ++++++++++++++++++++++++++++++ 2 files changed, 39 insertions(+) diff --git a/Client/Application/Migration.swift b/Client/Application/Migration.swift index 0e5b7720906..4861a265525 100644 --- a/Client/Application/Migration.swift +++ b/Client/Application/Migration.swift @@ -97,9 +97,14 @@ extension Preferences { // This needs to be translated to our new preference. Preferences.General.isFirstLaunch.value = Preferences.DAU.lastLaunchInfo.value == nil + // Core Data + // Migrate the shield overrides migrateShieldOverrides() + Bookmark.migrateOrder(forFavorites: true) + Bookmark.migrateOrder(forFavorites: false) + Preferences.Migration.completed.value = true } diff --git a/Data/models/Bookmark.swift b/Data/models/Bookmark.swift index 95b8c232c34..7f4bd0fc2e5 100644 --- a/Data/models/Bookmark.swift +++ b/Data/models/Bookmark.swift @@ -309,6 +309,40 @@ public final class Bookmark: NSManagedObject, WebsitePresentable, Syncable, CRUD DataController.save(context: frc.managedObjectContext) } + /// Takes all Bookmarks and Favorites from 1.6 and sets correct order for them. + /// 1.6 had few bugs with reordering which we want to avoid, in particular non-reordered bookmarks on 1.6 + /// all have order set to 0 which makes sorting confusing. + /// In migration we take all bookmarks using the same sorting method as on 1.6 and add a proper `order` + /// attribute to them. The goal is to have all bookmarks with a proper unique order number set. + public class func migrateOrder(parentFolder: Bookmark? = nil, + forFavorites: Bool, + context: NSManagedObjectContext = DataController.newBackgroundContext()) { + + let predicate = forFavorites ? + NSPredicate(format: "isFavorite == true") : allBookmarksOfAGivenLevelPredicate(parent: parentFolder) + + let orderSort = NSSortDescriptor(key: #keyPath(Bookmark.order), ascending: true) + let folderSort = NSSortDescriptor(key: #keyPath(Bookmark.isFolder), ascending: false) + let createdSort = NSSortDescriptor(key: #keyPath(Bookmark.created), ascending: true) + + let sort = [orderSort, folderSort, createdSort] + + guard let allBookmarks = all(where: predicate, sortDescriptors: sort, context: context), + !allBookmarks.isEmpty else { + return + } + + for (i, bookmark) in allBookmarks.enumerated() { + bookmark.order = Int16(i) + // Calling this method recursively to get ordering for nested bookmarks + if !forFavorites && bookmark.isFolder { + migrateOrder(parentFolder: bookmark, forFavorites: forFavorites, context: context) + } + } + + DataController.save(context: context) + } + // TODO: Migration syncUUIDS still needs to be solved // Should only ever be used for migration from old db // Always uses worker context