From fdb21cd1fb6c56771e79b0c33bbfd10420ada35e Mon Sep 17 00:00:00 2001 From: Shadowfacts Date: Wed, 5 May 2021 17:51:11 -0400 Subject: [PATCH] Add Refresh Poll option --- .../MastodonCachePersistentStore.swift | 23 ++++++++++--------- Tusker/Screens/Utilities/Previewing.swift | 16 ++++++++++++- 2 files changed, 27 insertions(+), 12 deletions(-) diff --git a/Tusker/CoreData/MastodonCachePersistentStore.swift b/Tusker/CoreData/MastodonCachePersistentStore.swift index d25881a892..3ff5237baf 100644 --- a/Tusker/CoreData/MastodonCachePersistentStore.swift +++ b/Tusker/CoreData/MastodonCachePersistentStore.swift @@ -65,15 +65,15 @@ class MastodonCachePersistentStore: NSPersistentContainer { } @discardableResult - private func upsert(status: Status, incrementReferenceCount: Bool) -> StatusMO { - if let statusMO = self.status(for: status.id, in: self.backgroundContext) { + private func upsert(status: Status, incrementReferenceCount: Bool, context: NSManagedObjectContext) -> StatusMO { + if let statusMO = self.status(for: status.id, in: context) { statusMO.updateFrom(apiStatus: status, container: self) if incrementReferenceCount { statusMO.incrementReferenceCount() } return statusMO } else { - let statusMO = StatusMO(apiStatus: status, container: self, context: self.backgroundContext) + let statusMO = StatusMO(apiStatus: status, container: self, context: context) if incrementReferenceCount { statusMO.incrementReferenceCount() } @@ -81,11 +81,12 @@ class MastodonCachePersistentStore: NSPersistentContainer { } } - func addOrUpdate(status: Status, incrementReferenceCount: Bool, completion: ((StatusMO) -> Void)? = nil) { - backgroundContext.perform { - let statusMO = self.upsert(status: status, incrementReferenceCount: incrementReferenceCount) - if self.backgroundContext.hasChanges { - try! self.backgroundContext.save() + func addOrUpdate(status: Status, incrementReferenceCount: Bool, context: NSManagedObjectContext? = nil, completion: ((StatusMO) -> Void)? = nil) { + let context = context ?? backgroundContext + context.perform { + let statusMO = self.upsert(status: status, incrementReferenceCount: incrementReferenceCount, context: context) + if context.hasChanges { + try! context.save() } completion?(statusMO) self.statusSubject.send(status.id) @@ -94,7 +95,7 @@ class MastodonCachePersistentStore: NSPersistentContainer { func addAll(statuses: [Status], completion: (() -> Void)? = nil) { backgroundContext.perform { - statuses.forEach { self.upsert(status: $0, incrementReferenceCount: true) } + statuses.forEach { self.upsert(status: $0, incrementReferenceCount: true, context: self.backgroundContext) } if self.backgroundContext.hasChanges { try! self.backgroundContext.save() } @@ -194,7 +195,7 @@ class MastodonCachePersistentStore: NSPersistentContainer { // filter out mentions, otherwise we would double increment the reference count of those accounts // since the status has the same account as the notification let accounts = notifications.filter { $0.kind != .mention }.map { $0.account } - statuses.forEach { self.upsert(status: $0, incrementReferenceCount: true) } + statuses.forEach { self.upsert(status: $0, incrementReferenceCount: true, context: self.backgroundContext) } accounts.forEach { self.upsert(account: $0, incrementReferenceCount: true) } if self.backgroundContext.hasChanges { try! self.backgroundContext.save() @@ -214,7 +215,7 @@ class MastodonCachePersistentStore: NSPersistentContainer { accounts.forEach { self.upsert(account: $0, incrementReferenceCount: true) } updatedAccounts.append(contentsOf: accounts.map { $0.id }) }, { (statuses) in - statuses.forEach { self.upsert(status: $0, incrementReferenceCount: true) } + statuses.forEach { self.upsert(status: $0, incrementReferenceCount: true, context: self.backgroundContext) } updatedStatuses.append(contentsOf: statuses.map { $0.id }) }) diff --git a/Tusker/Screens/Utilities/Previewing.swift b/Tusker/Screens/Utilities/Previewing.swift index 9418c84c26..260cc15d5d 100644 --- a/Tusker/Screens/Utilities/Previewing.swift +++ b/Tusker/Screens/Utilities/Previewing.swift @@ -176,7 +176,7 @@ extension MenuPreviewProvider { if mastodonController.account != nil && mastodonController.account.id == status.account.id { let pinned = status.pinned ?? false - actionsSection.append(createAction(identifier: "", title: pinned ? "Unpin" : "Pin", systemImageName: pinned ? "pin.slash" : "pin", handler: { [weak self] (_) in + actionsSection.append(createAction(identifier: "pin", title: pinned ? "Unpin" : "Pin", systemImageName: pinned ? "pin.slash" : "pin", handler: { [weak self] (_) in guard let self = self else { return } let request = (pinned ? Status.unpin : Status.pin)(status.id) self.mastodonController?.run(request, completion: { [weak self] (response) in @@ -188,6 +188,20 @@ extension MenuPreviewProvider { })) } + if status.poll != nil { + actionsSection.insert(createAction(identifier: "refresh", title: "Refresh Poll", systemImageName: "arrow.clockwise", handler: { [weak self] (_) in + guard let mastodonController = self?.mastodonController else { return } + let request = Client.getStatus(id: status.id) + mastodonController.run(request, completion: { (response) in + if case let .success(status, _) = response { + // todo: this shouldn't really use the viewContext, but for some reason saving the + // backgroundContext with the new version of the status isn't updating the viewContext + mastodonController.persistentContainer.addOrUpdate(status: status, incrementReferenceCount: false, context: mastodonController.persistentContainer.viewContext) + } + }) + }), at: 0) + } + var shareSection = [ openInSafariAction(url: status.url!), createAction(identifier: "share", title: "Share...", systemImageName: "square.and.arrow.up", handler: { [weak self, weak sourceView] (_) in