Improve logic of setting duplicate as current

Back currentProfileId with an internal variable that allows for
more control over navigation.

Can drop pendingProfiles hack.
This commit is contained in:
Davide De Rosa 2022-05-04 09:41:10 +02:00
parent b68fb21652
commit 7ec6ccda6c
1 changed files with 20 additions and 24 deletions

View File

@ -55,15 +55,25 @@ public class ProfileManager: ObservableObject {
} }
} }
@Published public var currentProfileId: UUID? { @Published private var internalCurrentProfileId: UUID? {
willSet { willSet {
pp_log.debug("Setting current profile: \(newValue?.uuidString ?? "nil")") pp_log.debug("Setting current profile: \(newValue?.uuidString ?? "nil")")
}
}
public var currentProfileId: UUID? {
get {
internalCurrentProfileId
}
set {
guard let id = newValue else { guard let id = newValue else {
internalCurrentProfileId = nil
return return
} }
guard let profile = liveProfile(withId: id) else { guard let profile = liveProfile(withId: id) else {
return return
} }
internalCurrentProfileId = id
setCurrentProfile(profile) setCurrentProfile(profile)
} }
} }
@ -72,8 +82,6 @@ public class ProfileManager: ObservableObject {
public let didCreateProfile = PassthroughSubject<Profile, Never>() public let didCreateProfile = PassthroughSubject<Profile, Never>()
private var pendingProfiles: [UUID: Profile] = [:]
private var cancellables: Set<AnyCancellable> = [] private var cancellables: Set<AnyCancellable> = []
public init( public init(
@ -177,10 +185,6 @@ extension ProfileManager {
pp_log.debug("Profile \(currentProfile.value.logDescription) found in memory (current profile)") pp_log.debug("Profile \(currentProfile.value.logDescription) found in memory (current profile)")
return currentProfile.value return currentProfile.value
} }
if let pending = pendingProfiles[id] {
pp_log.debug("Profile \(pending.logDescription) found in memory (pending profile)")
return pending
}
guard let profile = strategy.profile(withId: id) else { guard let profile = strategy.profile(withId: id) else {
assertionFailure("Profile in headers yet not found in persistent store") assertionFailure("Profile in headers yet not found in persistent store")
@ -253,23 +257,15 @@ extension ProfileManager {
.withNewId() .withNewId()
.renamedUniquely(withLastUpdate: false) .renamedUniquely(withLastUpdate: false)
//
// XXX: we want to batch save the duplicate together with the former current
// profile, which is done in setCurrentProfile(). however, setting
// currentProfileId (for navigation), requires the profile ID to exist in
// the persistent store when looked up via liveProfile(withId:)
//
// the pendingProfiles workaround allows setting currentProfileId to a
// profile that has not been persisted yet
//
if setAsCurrent { if setAsCurrent {
pendingProfiles[copy.id] = copy
// iOS 14 goes crazy when changing binding of a presented NavigationLink
if #available(iOS 15, *) { if #available(iOS 15, *) {
currentProfileId = copy.id internalCurrentProfileId = copy.id
} else {
setCurrentProfile(copy)
} }
pendingProfiles.removeValue(forKey: copy.id)
// autosaves copy if non-existing in persistent store
setCurrentProfile(copy)
} else { } else {
strategy.saveProfile(copy) strategy.saveProfile(copy)
} }
@ -303,15 +299,15 @@ extension ProfileManager {
// means that carelessly calling .saveProfiles() may trigger an unnecessary // means that carelessly calling .saveProfiles() may trigger an unnecessary
// willUpdateProfiles() and a potential animation in subscribers (e.g. OrganizerView) // willUpdateProfiles() and a potential animation in subscribers (e.g. OrganizerView)
// //
// current profile, when set on launch, is never fetched from pendingProfiles, so we take // current profile, when set on launch, is always existing, so we take care
// care of checking that to avoid an undesired save // checking that to avoid an undesired save
// //
var profilesToSave: [Profile] = [] var profilesToSave: [Profile] = []
if isExistingProfile(withId: currentProfile.value.id) { if isExistingProfile(withId: currentProfile.value.id) {
pp_log.info("Defer saving of former current profile \(currentProfile.value.logDescription)") pp_log.info("Defer saving of former current profile \(currentProfile.value.logDescription)")
profilesToSave.append(currentProfile.value) profilesToSave.append(currentProfile.value)
} }
if let _ = pendingProfiles[profile.id] { if !isExistingProfile(withId: profile.id) {
pp_log.info("Defer saving of transient current profile \(profile.logDescription)") pp_log.info("Defer saving of transient current profile \(profile.logDescription)")
profilesToSave.append(profile) profilesToSave.append(profile)
} }