Create a fetchStatuses method that will optionally create statuses if needed. Callback gets Set<ArticleStatus> — or nil if the app is suspended.

This commit is contained in:
Brent Simmons 2019-12-11 22:28:01 -08:00
parent 507eddd42f
commit 45cdb7bea3
4 changed files with 50 additions and 1 deletions

View File

@ -762,6 +762,17 @@ public final class Account: DisplayNameProvider, UnreadCountProvider, Container,
database.ensureStatuses(articleIDs, defaultRead, statusKey, flag, completionHandler: completionHandler)
}
/// Update statuses  set a key and value. This updates the database, and sends a .StatusesDidChange notification.
func update(statuses: Set<ArticleStatus>, statusKey: ArticleStatus.Key, flag: Bool) {
// TODO: https://github.com/brentsimmons/NetNewsWire/issues/1420
}
/// Fetch statuses for the specified articleIDs. The completionHandler will get nil if the app is suspended.
/// To update the properties in the database, call the update method that takes Set<ArticleStatus> as first parameter.
func fetchStatuses(articleIDs: Set<String>, createIfNeeded: Bool, completionHandler: @escaping (Set<ArticleStatus>?) -> Void) {
database.fetchStatuses(articleIDs: articleIDs, createIfNeeded: createIfNeeded, callback: completionHandler)
}
/// Empty caches that can reasonably be emptied. Call when the app goes in the background, for instance.
func emptyCaches() {
database.emptyCaches()

View File

@ -172,6 +172,10 @@ public final class ArticlesDatabase {
return articlesTable.mark(articles, statusKey, flag)
}
public func fetchStatuses(articleIDs: Set<String>, createIfNeeded: Bool, callback: @escaping (Set<ArticleStatus>?) -> Void) {
articlesTable.fetchStatuses(articleIDs, createIfNeeded, callback)
}
// MARK: - Suspend and Resume (for iOS)
/// Close the database and stop running database calls.

View File

@ -310,7 +310,28 @@ final class ArticlesTable: DatabaseTable {
}
}
}
func fetchStatuses(_ articleIDs: Set<String>, _ createIfNeeded: Bool, _ callback: @escaping (Set<ArticleStatus>?) -> Void) {
guard !queue.isSuspended else {
callback(nil)
return
}
queue.runInTransaction { (database) in
var statusesDictionary = [String: ArticleStatus]()
if createIfNeeded {
statusesDictionary = self.statusesTable.ensureStatusesForArticleIDs(articleIDs, false, database)
}
else {
statusesDictionary = self.statusesTable.existingStatusesForArticleIDs(articleIDs, database)
}
let statuses = Set(statusesDictionary.values)
DispatchQueue.main.async {
callback(statuses)
}
}
}
// MARK: - Unread Counts
func fetchUnreadCounts(_ webFeedIDs: Set<String>, _ completion: @escaping UnreadCountCompletionBlock) {

View File

@ -46,6 +46,19 @@ final class StatusesTable: DatabaseTable {
return statusesDictionary(articleIDs)
}
func existingStatusesForArticleIDs(_ articleIDs: Set<String>, _ database: FMDatabase) -> [String: ArticleStatus] {
// Check cache.
let articleIDsMissingCachedStatus = articleIDsWithNoCachedStatus(articleIDs)
if articleIDsMissingCachedStatus.isEmpty {
return statusesDictionary(articleIDs)
}
// Check database.
fetchAndCacheStatusesForArticleIDs(articleIDsMissingCachedStatus, database)
return statusesDictionary(articleIDs)
}
// MARK: - Marking
@discardableResult