设置NSMetadataQueryDidUpdateNotification以获得简单响应

时间:2013-06-16 03:32:57

标签: xcode cocoa icloud nsmetadataquery

我正在尝试使用OS X应用程序上的NSMetadataQueryDidUpdateNotification启动并运行,以便在我的iCloud ubiquity容器中的文件更新时提醒我。我一直在做很多研究(包括阅读其他Stack答案,如thisthisthisthis),但我仍然没有好吧,似乎。

我有一个从NSDocument子类化的“CloudDocument”对象,它在H中包含了这个代码:

@property (nonatomic, strong) NSMetadataQuery *alertQuery;

这是M文件:

@synthesize alertQuery;

-(id)init {
    self = [super init];
    if (self) {
        if (alertQuery) {
            [alertQuery stopQuery];
        } else {
            alertQuery = [[NSMetadataQuery alloc]init];
        }

        [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(queryDidUpdate:) name:NSMetadataQueryDidUpdateNotification object:nil];
        NSLog(@"Notification created");

        [alertQuery startQuery];
    }
    return self;
}

-(void)queryDidUpdate:(NSNotification *)notification {
    NSLog(@"Something changed!!!");
}

根据我的最佳理解,这应该停止预先存在的查询(如果正在运行),设置通知以更改普遍容器,然后启动查询以便它将从此处监视更改。

除此之外,情况并非如此,因为我在启动日志中获得Notification created但在更改iCloud文档时从未Something changed!!!

谁能告诉我我缺少什么?如果你的超级酱超级棒,你会帮我解决一些代码示例和/或教程吗?

编辑:如果重要/有帮助,我的ubiquity容器中只有一个文件同步。它被称为“注释”,因此我使用以下URL结果访问它:

+(NSURL *)notesURL {
    NSURL *url = [[NSFileManager defaultManager] URLForUbiquityContainerIdentifier:nil];
    return [url URLByAppendingPathComponent:kAllNotes];
}

其中“kAllNotes”设置为#define kAllNotes @"notes"

编辑#2:通过与Daij-Djan的对话,我的代码有了很多更新,所以这是我的更新代码:

@synthesize alertQuery;

-(id)init {
    self = [super init];
    if (self) {
        alertQuery = [[NSMetadataQuery alloc] init];
        if (alertQuery) {
            [alertQuery setSearchScopes:[NSArray arrayWithObject:NSMetadataQueryUbiquitousDocumentsScope]];

            NSString *STEDocFilenameExtension = @"*";
            NSString* filePattern = [NSString stringWithFormat:@"*.%@", STEDocFilenameExtension];
            [alertQuery setPredicate:[NSPredicate predicateWithFormat:@"%K LIKE %@", NSMetadataItemFSNameKey, filePattern]];
        }

        [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(queryDidUpdate:) name:NSMetadataQueryDidFinishGatheringNotification object:nil];
        [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(queryDidUpdate:) name:NSMetadataQueryDidUpdateNotification object:nil];

        NSLog(@"Notification created");

        [alertQuery startQuery];
    }
    return self;
}

-(void)queryDidUpdate:(NSNotification *)notification {
    [alertQuery disableUpdates];

    NSLog(@"Something changed!!!");

    [alertQuery enableUpdates];
}

2 个答案:

答案 0 :(得分:2)

你如何保存你的文件 - 你给它的网址是什么?除非你自己给它一个扩展名,否则不会自动给它 - 所以你的*.*模式永远不会匹配没有扩展名的文件。尝试*作为模式,看看会发生什么。

此外,它有助于记录queryDidUpdate中发生的事情,直到您确切地知道发生了什么:

尝试类似:

-(void)queryDidUpdate:(NSNotification *)notification {
    [alertQuery disableUpdates];

    NSLog(@"Something changed!!!");

    // Look at each element returned by the search
    // - note it returns the entire list each time this method is called, NOT just the changes
    int resultCount = [alertQuery resultCount];
    for (int i = 0; i < resultCount; i++) {
        NSMetadataItem *item = [alertQuery resultAtIndex:i];
        [self logAllCloudStorageKeysForMetadataItem:item];
    }

    [alertQuery enableUpdates];
}

- (void)logAllCloudStorageKeysForMetadataItem:(NSMetadataItem *)item
{
    NSNumber *isUbiquitous = [item valueForAttribute:NSMetadataItemIsUbiquitousKey];
    NSNumber *hasUnresolvedConflicts = [item valueForAttribute:NSMetadataUbiquitousItemHasUnresolvedConflictsKey];
    NSNumber *isDownloaded = [item valueForAttribute:NSMetadataUbiquitousItemIsDownloadedKey];
    NSNumber *isDownloading = [item valueForAttribute:NSMetadataUbiquitousItemIsDownloadingKey];
    NSNumber *isUploaded = [item valueForAttribute:NSMetadataUbiquitousItemIsUploadedKey];
    NSNumber *isUploading = [item valueForAttribute:NSMetadataUbiquitousItemIsUploadingKey];
    NSNumber *percentDownloaded = [item valueForAttribute:NSMetadataUbiquitousItemPercentDownloadedKey];
    NSNumber *percentUploaded = [item valueForAttribute:NSMetadataUbiquitousItemPercentUploadedKey];
    NSURL *url = [item valueForAttribute:NSMetadataItemURLKey];

    BOOL documentExists = [[NSFileManager defaultManager] fileExistsAtPath:[url path]];

    NSLog(@"isUbiquitous:%@ hasUnresolvedConflicts:%@ isDownloaded:%@ isDownloading:%@ isUploaded:%@ isUploading:%@ %%downloaded:%@ %%uploaded:%@ documentExists:%i - %@", isUbiquitous, hasUnresolvedConflicts, isDownloaded, isDownloading, isUploaded, isUploading, percentDownloaded, percentUploaded, documentExists, url);
}

答案 1 :(得分:1)

你永远不会分配你的alertQuery ....

你需要分配的地方,为它启动一个NSMetaDataQuery

例如


NSMetadataQuery* aQuery = [[NSMetadataQuery alloc] init];
if (aQuery) {
    // Search the Documents subdirectory only.
    [aQuery setSearchScopes:[NSArray
                arrayWithObject:NSMetadataQueryUbiquitousDocumentsScope]];

    // Add a predicate for finding the documents.
    NSString* filePattern = [NSString stringWithFormat:@"*"];
    [aQuery setPredicate:[NSPredicate predicateWithFormat:@"%K LIKE %@",
                NSMetadataItemFSNameKey, filePattern]];

   // Register for the metadata query notifications.
   [[NSNotificationCenter defaultCenter] addObserver:self
        selector:@selector(processFiles:)
        name:NSMetadataQueryDidFinishGatheringNotification
        object:nil];
   [[NSNotificationCenter defaultCenter] addObserver:self
        selector:@selector(processFiles:)
        name:NSMetadataQueryDidUpdateNotification
        object:nil];

   // Start the query and let it run.
   [aQuery startQuery];

}

processFiles方法

== your queryDidUpdate

- processFiles(NSNotification*)note {
     [aQuery disableUpdates];

     .....

     [aQuery enableUpdates];
}

注意:禁用并重新启用搜索!

http://developer.apple.com/library/ios/#documentation/General/Conceptual/iCloud101/SearchingforiCloudDocuments/SearchingforiCloudDocuments.html