import OSLog
extension FileProviderEnumerator {
- static func fullRecursiveScan(ncAccount: NextcloudAccount, ncKit: NextcloudKit, scanChangesOnly: Bool, completionHandler: @escaping(_ metadatas: [NextcloudItemMetadataTable], _ newMetadatas: [NextcloudItemMetadataTable], _ updatedMetadatas: [NextcloudItemMetadataTable], _ deletedMetadatas: [NextcloudItemMetadataTable], _ error: NKError?) -> Void) {
+ func fullRecursiveScan(ncAccount: NextcloudAccount, ncKit: NextcloudKit, scanChangesOnly: Bool, completionHandler: @escaping(_ metadatas: [NextcloudItemMetadataTable], _ newMetadatas: [NextcloudItemMetadataTable], _ updatedMetadatas: [NextcloudItemMetadataTable], _ deletedMetadatas: [NextcloudItemMetadataTable], _ error: NKError?) -> Void) {
let rootContainerDirectoryMetadata = NextcloudItemMetadataTable()
rootContainerDirectoryMetadata.directory = true
let dispatchQueue = DispatchQueue(label: "recursiveChangeEnumerationQueue", qos: .background)
dispatchQueue.async {
- let results = scanRecursively(rootContainerDirectoryMetadata, ncAccount: ncAccount, ncKit: ncKit, scanChangesOnly: scanChangesOnly)
+ let results = self.scanRecursively(rootContainerDirectoryMetadata, ncAccount: ncAccount, ncKit: ncKit, scanChangesOnly: scanChangesOnly)
// Run a check to ensure files deleted in one location are not updated in another (e.g. when moved)
// The recursive scan provides us with updated/deleted metadatas only on a folder by folder basis;
}
}
- private static func scanRecursively(_ directoryMetadata: NextcloudItemMetadataTable, ncAccount: NextcloudAccount, ncKit: NextcloudKit, scanChangesOnly: Bool) -> (metadatas: [NextcloudItemMetadataTable], newMetadatas: [NextcloudItemMetadataTable], updatedMetadatas: [NextcloudItemMetadataTable], deletedMetadatas: [NextcloudItemMetadataTable], error: NKError?) {
+ private func scanRecursively(_ directoryMetadata: NextcloudItemMetadataTable, ncAccount: NextcloudAccount, ncKit: NextcloudKit, scanChangesOnly: Bool) -> (metadatas: [NextcloudItemMetadataTable], newMetadatas: [NextcloudItemMetadataTable], updatedMetadatas: [NextcloudItemMetadataTable], deletedMetadatas: [NextcloudItemMetadataTable], error: NKError?) {
+
+ if self.isInvalidated {
+ return ([], [], [], [], nil)
+ }
assert(directoryMetadata.directory, "Can only recursively scan a directory.")
let ncAccount: NextcloudAccount
let ncKit: NextcloudKit
var serverUrl: String = ""
+ var isInvalidated = false
private static func isSystemIdentifier(_ identifier: NSFileProviderItemIdentifier) -> Bool {
return identifier == .rootContainer ||
}
func invalidate() {
- // TODO: perform invalidation of server connection if necessary
+ self.isInvalidated = true
}
// MARK: - Protocol methods
if enumeratedItemIdentifier == .workingSet {
Logger.enumeration.debug("Enumerating changes in working set for user: \(self.ncAccount.ncKitAccount, privacy: OSLogPrivacy.auto(mask: .hash))")
- FileProviderEnumerator.fullRecursiveScan(ncAccount: self.ncAccount, ncKit: self.ncKit, scanChangesOnly: true) { _, newMetadatas, updatedMetadatas, deletedMetadatas, error in
+ fullRecursiveScan(ncAccount: self.ncAccount, ncKit: self.ncKit, scanChangesOnly: true) { _, newMetadatas, updatedMetadatas, deletedMetadatas, error in
+
+ if self.isInvalidated {
+ Logger.enumeration.info("Enumerator invalidated during working set change scan. For user: \(self.ncAccount.ncKitAccount, privacy: OSLogPrivacy.auto(mask: .hash))")
+ observer.finishEnumeratingWithError(NSFileProviderError(.cannotSynchronize))
+ return
+ }
guard error == nil else {
Logger.enumeration.info("Finished recursive change enumeration of working set for user: \(self.ncAccount.ncKitAccount, privacy: OSLogPrivacy.auto(mask: .hash)) with error: \(error!.errorDescription, privacy: .public)")
observer.finishEnumeratingWithError(error!.toFileProviderError())
- return;
+ return
}
Logger.enumeration.info("Finished recursive change enumeration of working set for user: \(self.ncAccount.ncKitAccount, privacy: OSLogPrivacy.auto(mask: .hash)). Enumerating items.")