如何加速 Cloudkit 'fetchRecordWithID'
How to speed up Cloudkit 'fetchRecordWithID'
我的应用程序在第一次打开时做的第一个操作是在 cloudkit 检查是否有任何信息连接到用户 iCloud 帐户,因为如果有,信息将下载到应用程序。我的问题是,下载信息的方法在通过 wifi 连接时需要大约 13 秒来收集信息,而在使用移动数据时需要超过 45 秒。我一直在寻找优化,发现使用 development
数据库进行模拟时,结果比使用 produciton
数据库进行模拟时更快,所以我可能以错误的方式收集数据,因为有很多生产中的数据多于开发中的数据。
搜索信息的方法如下
CKRecordID *recordID = [[CKRecordID alloc] initWithRecordName: userKey];
[_publicDatabase fetchRecordWithID:recordID completionHandler:^(CKRecord * _Nullable record, NSError * _Nullable error) {
if (error) {
NSLog(@"Error in fethcing from user db %@", error);
completion(error);
} else {
NSLog(@"User found in db");
NSString *name = record[@"Name"];
CKAsset *file = record[@"Image"];
NSString *url = file.fileURL.absoluteString;
NSMutableArray<NSString*> *codes = record[@"Groups"];
NSArray * paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString * basePath = ([paths count] > 0) ? [paths objectAtIndex:0] : nil;
NSData * binaryImageData = [NSData dataWithContentsOfURL:[file fileURL]];
[binaryImageData writeToFile:[basePath stringByAppendingPathComponent:@"profilePicture.png"] atomically:YES];
completion(nil);
}
}];
云端的信息基本就是姓名,头像,群号
有什么方法可以加快从 cloudkit 中获取数据的速度?因为我不认为通过移动数据获取此数据需要超过 45 秒是正常的,所以这没有意义。
你应该使用 CKFetchRecordsOperation class 而不是 CKDatabase 提供的 fetch 函数。
原因是CKFetchRecordsOperation
继承自Operation
class,允许更复杂和扩展的性能配置。
这是您的代码修改以使用上面提到的 class。
let fetchOperation: CKFetchRecordsOperation = CKFetchRecordsOperation(recordIDs: [ userKey ])
// Fetch only desired keys
fetchOperation.desiredKeys = [ "Name", "Image", "Groups" ]
// Performance tips
operation.qualityOfService = .userInitiated
fetchOperation.perRecordCompletionBlock = { (record: CKRecord?, recordID: CKRecordID?, error: Error) -> (Void) in
guard let record = record else
{
print("There's no record in this fetch operations")
if let error = error
{
print("err @ \(#function) -> \(error.localizedDescription)")
}
return
}
Dispatch.async.main
{
// Save your image here...
}
}
_publicDatabase.add(fetchOperation)
这里有一些提示...
- 只获取您需要的那些字段。使用 dediredKeys 属性
- 设置操作的优先级。想想这是后台操作,还是用户现在需要响应。更多信息请见 qualityOfService 属性
- 当您保存图片时,请在主队列以及用户响应中进行保存。
PS:我现在注意到您的代码是 Objective-C,我的示例是 Swift,抱歉。
我的应用程序在第一次打开时做的第一个操作是在 cloudkit 检查是否有任何信息连接到用户 iCloud 帐户,因为如果有,信息将下载到应用程序。我的问题是,下载信息的方法在通过 wifi 连接时需要大约 13 秒来收集信息,而在使用移动数据时需要超过 45 秒。我一直在寻找优化,发现使用 development
数据库进行模拟时,结果比使用 produciton
数据库进行模拟时更快,所以我可能以错误的方式收集数据,因为有很多生产中的数据多于开发中的数据。
搜索信息的方法如下
CKRecordID *recordID = [[CKRecordID alloc] initWithRecordName: userKey];
[_publicDatabase fetchRecordWithID:recordID completionHandler:^(CKRecord * _Nullable record, NSError * _Nullable error) {
if (error) {
NSLog(@"Error in fethcing from user db %@", error);
completion(error);
} else {
NSLog(@"User found in db");
NSString *name = record[@"Name"];
CKAsset *file = record[@"Image"];
NSString *url = file.fileURL.absoluteString;
NSMutableArray<NSString*> *codes = record[@"Groups"];
NSArray * paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString * basePath = ([paths count] > 0) ? [paths objectAtIndex:0] : nil;
NSData * binaryImageData = [NSData dataWithContentsOfURL:[file fileURL]];
[binaryImageData writeToFile:[basePath stringByAppendingPathComponent:@"profilePicture.png"] atomically:YES];
completion(nil);
}
}];
云端的信息基本就是姓名,头像,群号
有什么方法可以加快从 cloudkit 中获取数据的速度?因为我不认为通过移动数据获取此数据需要超过 45 秒是正常的,所以这没有意义。
你应该使用 CKFetchRecordsOperation class 而不是 CKDatabase 提供的 fetch 函数。
原因是CKFetchRecordsOperation
继承自Operation
class,允许更复杂和扩展的性能配置。
这是您的代码修改以使用上面提到的 class。
let fetchOperation: CKFetchRecordsOperation = CKFetchRecordsOperation(recordIDs: [ userKey ])
// Fetch only desired keys
fetchOperation.desiredKeys = [ "Name", "Image", "Groups" ]
// Performance tips
operation.qualityOfService = .userInitiated
fetchOperation.perRecordCompletionBlock = { (record: CKRecord?, recordID: CKRecordID?, error: Error) -> (Void) in
guard let record = record else
{
print("There's no record in this fetch operations")
if let error = error
{
print("err @ \(#function) -> \(error.localizedDescription)")
}
return
}
Dispatch.async.main
{
// Save your image here...
}
}
_publicDatabase.add(fetchOperation)
这里有一些提示...
- 只获取您需要的那些字段。使用 dediredKeys 属性
- 设置操作的优先级。想想这是后台操作,还是用户现在需要响应。更多信息请见 qualityOfService 属性
- 当您保存图片时,请在主队列以及用户响应中进行保存。
PS:我现在注意到您的代码是 Objective-C,我的示例是 Swift,抱歉。