diff --git a/Frameworks/Account/Account.xcodeproj/project.pbxproj b/Frameworks/Account/Account.xcodeproj/project.pbxproj index 38efd6984..e8c367aeb 100644 --- a/Frameworks/Account/Account.xcodeproj/project.pbxproj +++ b/Frameworks/Account/Account.xcodeproj/project.pbxproj @@ -42,6 +42,7 @@ 5144EA49227B497600D19003 /* FeedbinAPICaller.swift in Sources */ = {isa = PBXBuildFile; fileRef = 5144EA48227B497600D19003 /* FeedbinAPICaller.swift */; }; 5144EA4E227B829A00D19003 /* FeedbinAccountDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = 5144EA4D227B829A00D19003 /* FeedbinAccountDelegate.swift */; }; 514BF5202391B0DB00902FE8 /* SingleArticleFetcher.swift in Sources */ = {isa = PBXBuildFile; fileRef = 514BF51F2391B0DB00902FE8 /* SingleArticleFetcher.swift */; }; + 515000002438682300C1A442 /* CloudKitPublicZone.swift in Sources */ = {isa = PBXBuildFile; fileRef = 5150FFFF2438682300C1A442 /* CloudKitPublicZone.swift */; }; 5150FFFE243823B800C1A442 /* CloudKitError.swift in Sources */ = {isa = PBXBuildFile; fileRef = 5150FFFD243823B800C1A442 /* CloudKitError.swift */; }; 5154367B228EEB28005E1CDF /* FeedbinImportResult.swift in Sources */ = {isa = PBXBuildFile; fileRef = 5154367A228EEB28005E1CDF /* FeedbinImportResult.swift */; }; 515E4EB52324FF8C0057B0E7 /* CredentialsManager.swift in Sources */ = {isa = PBXBuildFile; fileRef = 515E4EB22324FF8C0057B0E7 /* CredentialsManager.swift */; }; @@ -278,6 +279,7 @@ 5144EA4D227B829A00D19003 /* FeedbinAccountDelegate.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = FeedbinAccountDelegate.swift; sourceTree = ""; }; 514BF51F2391B0DB00902FE8 /* SingleArticleFetcher.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SingleArticleFetcher.swift; sourceTree = ""; }; 5150FFFD243823B800C1A442 /* CloudKitError.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = CloudKitError.swift; sourceTree = ""; }; + 5150FFFF2438682300C1A442 /* CloudKitPublicZone.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = CloudKitPublicZone.swift; sourceTree = ""; }; 5154367A228EEB28005E1CDF /* FeedbinImportResult.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = FeedbinImportResult.swift; sourceTree = ""; }; 515E4EB22324FF8C0057B0E7 /* CredentialsManager.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = CredentialsManager.swift; sourceTree = ""; }; 515E4EB32324FF8C0057B0E7 /* URLRequest+RSWeb.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = "URLRequest+RSWeb.swift"; sourceTree = ""; }; @@ -528,6 +530,7 @@ 519E84A72434C5EF00D238B0 /* CloudKitArticlesZone.swift */, 519E84AB2435019100D238B0 /* CloudKitArticlesZoneDelegate.swift */, 5150FFFD243823B800C1A442 /* CloudKitError.swift */, + 5150FFFF2438682300C1A442 /* CloudKitPublicZone.swift */, 51E4DB2D242633ED0091EB5B /* CloudKitZone.swift */, 51C034DE242D65D20014DC71 /* CloudKitZoneResult.swift */, ); @@ -1110,6 +1113,7 @@ 84F73CF1202788D90000BCEF /* ArticleFetcher.swift in Sources */, 841974251F6DDCE4006346C4 /* AccountDelegate.swift in Sources */, 510BD113232C3E9D002692E4 /* WebFeedMetadataFile.swift in Sources */, + 515000002438682300C1A442 /* CloudKitPublicZone.swift in Sources */, 5103A9D92422546800410853 /* CloudKitAccountDelegate.swift in Sources */, 5165D73122837F3400D9D53D /* InitialFeedDownloader.swift in Sources */, 9E784EBE237E890600099B1B /* FeedlyLogoutOperation.swift in Sources */, diff --git a/Frameworks/Account/CloudKit/CloudKitPublicZone.swift b/Frameworks/Account/CloudKit/CloudKitPublicZone.swift new file mode 100644 index 000000000..653ac72d4 --- /dev/null +++ b/Frameworks/Account/CloudKit/CloudKitPublicZone.swift @@ -0,0 +1,58 @@ +// +// CloudKitPublicZone.swift +// Account +// +// Created by Maurice Parker on 4/4/20. +// Copyright © 2020 Ranchero Software, LLC. All rights reserved. +// + +import Foundation +import CloudKit +import os.log + +final class CloudKitPublicZone: CloudKitZone { + + static var zoneID: CKRecordZone.ID { + return CKRecordZone.default().zoneID + } + + var log = OSLog(subsystem: Bundle.main.bundleIdentifier!, category: "CloudKit") + + weak var container: CKContainer? + weak var database: CKDatabase? + var delegate: CloudKitZoneDelegate? + + struct CloudKitWebFeed { + static let recordType = "WebFeed" + struct Fields { + static let url = "url" + static let httpLastModified = "httpLastModified" + static let httpEtag = "httpEtag" + } + } + + struct CloudKitWebFeedCheck { + static let recordType = "UserSubscription" + struct Fields { + static let webFeed = "webFeed" + static let subscriptionID = "oldestPossibleCheckTime" + } + } + + struct CloudKitUserSubscription { + static let recordType = "UserSubscription" + struct Fields { + static let user = "user" + static let webFeed = "webFeed" + static let subscriptionID = "subscriptionID" + } + } + + func subscribe() {} + + func receiveRemoteNotification(userInfo: [AnyHashable : Any], completion: @escaping () -> Void) { + + } + + +} diff --git a/Frameworks/Account/CloudKit/CloudKitZone.swift b/Frameworks/Account/CloudKit/CloudKitZone.swift index fb386713f..20ba10960 100644 --- a/Frameworks/Account/CloudKit/CloudKitZone.swift +++ b/Frameworks/Account/CloudKit/CloudKitZone.swift @@ -34,6 +34,18 @@ protocol CloudKitZone: class { var database: CKDatabase? { get } var delegate: CloudKitZoneDelegate? { get set } + /// Reset the change token used to determine what point in time we are doing changes fetches + func resetChangeToken() + + /// Generates a new CKRecord.ID using a UUID for the record's name + func generateRecordID() -> CKRecord.ID + + /// Subscribe to changes at a zone level + func subscribe() + + /// Process a remove notification + func receiveRemoteNotification(userInfo: [AnyHashable : Any], completion: @escaping () -> Void) + } extension CloudKitZone { @@ -43,12 +55,10 @@ extension CloudKitZone { changeToken = nil } - /// Generates a new CKRecord.ID using a UUID for the record's name func generateRecordID() -> CKRecord.ID { return CKRecord.ID(recordName: UUID().uuidString, zoneID: Self.zoneID) } - /// Subscribe to all changes that happen in this zone func subscribe() { let subscription = CKRecordZoneSubscription(zoneID: Self.zoneID) @@ -72,7 +82,6 @@ extension CloudKitZone { } - /// Fetch and process any changes in the zone since the last time we checked when we get a remote notification. func receiveRemoteNotification(userInfo: [AnyHashable : Any], completion: @escaping () -> Void) { let note = CKRecordZoneNotification(fromRemoteNotificationDictionary: userInfo) guard note?.recordZoneID?.zoneName == Self.zoneID.zoneName else {