CKQueryOperation queryCompletionBlock 返回一个 nil 游标

Posted

技术标签:

【中文标题】CKQueryOperation queryCompletionBlock 返回一个 nil 游标【英文标题】:CKQueryOperation queryCompletionBlock return a nil cursor 【发布时间】:2020-04-19 14:51:38 【问题描述】:

我正在使用 CKQueryOperation 获取 CloudKit 数据库。出于某种原因,每次按下获取按钮时,我第一次得到一个零光标。第二次获取并获取数据时,一切都很好。当我检查 recordFetchedBlock 时,它确实会得到结果并附加它们,但最后数组是空的。我不明白为什么会这样。我想立即显示结果,因为它们已被提取。我认为问题出在 nil 光标上,但我愿意接受其他建议。这是我的代码:

public class CloudKitDatabase 

static let shared = CloudKitDatabase()

var records = [CKRecord]()

let publicData = CKContainer.default().publicCloudDatabase

init() 
    self.fetchRecords()


func fetchRecords() 

    let predicate = NSPredicate(value: true)
    let query = CKQuery(recordType: "OECD", predicate: predicate)

    let queryOperation = CKQueryOperation(query: query)

    queryOperation.recordFetchedBlock = 
        record in
        self.records.append(record)


    

    queryOperation.queryCompletionBlock =  cursor, error in
        DispatchQueue.main.async 
            if error != nil 
                print(error.debugDescription)
             else 
                if cursor != nil 
                    self.queryServer(cursor!)
                 else 
                    print("CURSOR IS NIL")
                
            
        

    
    self.publicData.add(queryOperation)



func queryServer(_ cursor: CKQueryOperation.Cursor) 
    let queryOperation = CKQueryOperation(cursor: cursor)

    queryOperation.recordFetchedBlock = 
        record in
        self.records.append(record)

    

    queryOperation.queryCompletionBlock =  cursor, error in
        DispatchQueue.main.async 
            if error != nil 
                print(error.debugDescription)
             else 
                if cursor != nil 
                    self.queryServer(cursor!)
                 else 
                    print("CURSOR IS NIL")
                
            
        
    
    self.publicData.add(queryOperation)


调试区域告诉我: 光标为零 而 CloudKitDatabase.shared.records.isEmpty 为真

【问题讨论】:

【参考方案1】:

首先在第一个查询中尝试一些配置;

   let queryOperation = CKQueryOperation(query: query)
   queryOperation.queuePriority = .veryHigh
   queryOperation.resultsLimit = 99 // built in limit is 400  

接下来,不要在调度中进行游标调用并包含您的完成;

queryOperation.queryCompletionBlock =
 cursor, error in

        if error != nil 
            print(error.debugDescription)
         else 
            if cursor != nil 
                self.queryServer(cursor!)
             else 
                print("CURSOR IS NIL")
                completion(nil)
            
        

和;

queryOperation.queryCompletionBlock = 
 cursor, error in

        if error != nil 
            print(error.debugDescription)
         else 
            if cursor != nil 
                self.queryServer(cursor!)
             else 
                print("CURSOR IS NIL")
                completion(nil)
            
        


也不要忘记在 fetchRecords 开始时清空您的记录数组,否则连续调用将在数组中获得相同的记录。

【讨论】:

以上是关于CKQueryOperation queryCompletionBlock 返回一个 nil 游标的主要内容,如果未能解决你的问题,请参考以下文章

使用 CKQueryOperation 和 CKReference 获取大集合

CKQueryOperation 处理大批量

CloudKit:删除记录的 CKQueryOperation

CloudKit - 具有依赖关系的 CKQueryOperation

CKQueryOperation queryCompletionBlock 返回一个 nil 游标

CKQueryOperation resultLimit max 和 request count