I\'m trying to download a batch of records from my iCloud public database using CloudKit and the cursor. The code works fine for the first 3 executions, regardless of how t
This could be another approach (already updated to Swift 3).
It does not stops after third iteration, but continues until the end
var queryOp = CKQueryOperation(query: query)
queryOp.recordFetchedBlock = self.fetchedARecord
queryOp.resultsLimit = 5
queryOp.queryCompletionBlock = { [weak self] (cursor : CKQueryCursor?, error : Error?) -> Void in
print("comp block called with \(cursor) \(error)")
if cursor != nil {
let nextOp = CKQueryOperation(cursor: cursor!)
nextOp.recordFetchedBlock = self!.fetchedARecord
nextOp.queryCompletionBlock = queryOp.queryCompletionBlock
nextOp.resultsLimit = queryOp.resultsLimit
//this is VERY important
queryOp = nextOp
self!.publicDB.add(queryOp)
print("added next fetch")
}
}
self.publicDB.add(queryOp)
I successfully use it to retrieve hundreds of records from CloudKit
The way you're defining nextOp inside of your queryCompletionBlock scope is causing a problem after three iterations of that block. If you break the creation of the CKQueryOperation out into its own method your problem goes away.
Here is the code:
func fetchedDetailRecord(record: CKRecord!) -> Void {
println("Retrieved record: \(record)")
}
func createQueryOperation(cursor: CKQueryCursor? = nil) -> CKQueryOperation {
var operation:CKQueryOperation
if (cursor != nil) {
operation = CKQueryOperation(cursor: cursor!)
} else {
operation = CKQueryOperation(query: CKQuery(...))
}
operation.recordFetchedBlock = self.fetchedDetailRecord
operation.resultsLimit = 5
operation.queryCompletionBlock = { [weak self]
(cursor: CKQueryCursor!, error: NSError!) -> Void in
println("comp block called with \(cursor) \(error)")
if error != nil {
println("Error on fetch \(error.userInfo)")
} else {
if cursor != nil {
self!.publicDatabase?.addOperation(self!.createQueryOperation(cursor: cursor))
println("added next fetch")
} else {
self!.fileHandle!.closeFile()
self!.exportProgressIndicator.stopAnimation(self)
}
}
}
return operation
}
func doQuery() {
println("Querying records...")
self.publicDatabase?.addOperation(createQueryOperation())
}