Получать уведомления об изменениях файлов в iCloud
Я создаю файл с именем File - 1.jpg
на двух разных устройствах и положить его в контейнер iCloud.
Я не пользуюсь UIDocument
и хотя я пытался его использовать, это не создает конфликта. Вместо этого я вижу, что документы автоматически переименовываются и перемещаются с помощью iCloud.
Поэтому после загрузки тот или иной файл становится File - 2.jpg
, Все это хорошо, но теперь у меня нет ссылки на файл, поэтому я понятия не имею, что...
Есть ли способ получить уведомление на стороне приложения, что файл был переименован / перемещен / удален в iCloud?
2 ответа
В конце концов мне пришлось создать класс, который реализует NSFilePresenter
и укажите на папку контейнера iCloud.
Активные обновления от iCloud могут быть довольно поздними и происходить только тогда, когда iCloud извлекает метаданные.
Кроме того, мне пришлось связать каждый созданный файл с каждым устройством и учетной записью iCloud и сохранить эти данные, в моем случае в CoreData. Это где ubiquityIdentityToken
становится полезным.
Все операции с файлами в контейнере iCloud должны выполняться NSFileCoordinator
,
Для добавления / удаления событий лучше использовать NSMetadataQuery
, NSFileCoordinator
не сообщает о них вообще, но все же полезно определять, когда файлы были перемещены, это то, что метаданные запрашивают как обновления.
Это очень простой шаблон, который можно использовать в качестве отправной точки:
@interface iCloudFileCoordinator () <NSFilePresenter>
@property (nonatomic) NSString *containerID;
@property (nonatomic) NSURL *containerURL;
@property (nonatomic) NSOperationQueue *operationQueue;
@end
@implementation iCloudFileCoordinator
- (instancetype)initWithContainerID:(NSString *)containerID {
self = [super init];
if(!self) {
return nil;
}
self.containerID = containerID;
self.operationQueue = [[NSOperationQueue alloc] init];
self.operationQueue.qualityOfService = NSQualityOfServiceBackground;
[self addFilePresenter];
return self;
}
- (void)dealloc {
[self removeFilePresenter];
}
- (void)addFilePresenter {
[NSFileCoordinator addFilePresenter:self];
}
- (void)removeFilePresenter {
[NSFileCoordinator removeFilePresenter:self];
}
#pragma mark - NSFilePresenter
#pragma mark -
- (NSURL *)presentedItemURL {
NSURL *containerURL = self.containerURL;
if(containerURL) {
return containerURL;
}
NSFileManager *fileManager = [[NSFileManager alloc] init];
containerURL = [fileManager URLForUbiquityContainerIdentifier:self.containerID];
self.containerURL = containerURL;
return containerURL;
}
- (NSOperationQueue *)presentedItemOperationQueue {
return self.operationQueue;
}
- (void)presentedSubitemAtURL:(NSURL *)oldURL didMoveToURL:(NSURL *)newURL {
NSLog(@"Moved file from %@ to %@", oldURL, newURL);
}
/*
... and other bunch of methods that report on sub item changes ...
*/
@end
Используйте CKSubscription:
После инициализации CKSubscription вы можете указать параметры уведомления:
- CKSubscriptionOptionsFiresOnRecordСоздание
- CKSubscriptionOptionsFiresOnRecordУдаление
- CKSubscriptionOptionsFiresOnRecordОбновление
- CKSubscriptionOptionsFiresOnce
Это выглядело полезным для вас тоже:
http://www.raywenderlich.com/83116/beginning-cloudkit-tutorial