我经常使用插件(加载的 NSBundles)来封装一些功能。我现在想在我的一个插件中使用 NSMetadataQuery,但遇到了我无法解决的线程问题。
在插件的主类中,我这样设置查询:
NSMetadataQuery *mdQuery = [[NSMetadataQuery alloc] init];
[mdQuery setPredicate:[NSPredicate predicateWithFormat:@"(kMDItemFSName LIKE 'Project *')"]];
[[NSNotificationCenter defaultCenter] addObserver:self
selector:@selector(processQuery:)
name:nil
object:mdQuery];
[mdQuery startQuery];
通知被以下人员捕获:
- (void)processQuery:(NSNotification *)notification
{
NSMetadataQuery *mdQuery = [notification object];
if ([[notification name] isEqualToString:NSMetadataQueryDidStartGatheringNotification]) {
NSLog(@"%@ %@ Query started", [self class], NSStringFromSelector(_cmd));
} else if ([[notification name] isEqualToString:NSMetadataQueryGatheringProgressNotification]) {
NSLog(@"%@ %@ %ld", [self class], NSStringFromSelector(_cmd), (long)[mdQuery resultCount]);
} else if ([[notification name] isEqualToString: NSMetadataQueryDidFinishGatheringNotification]) {
NSUInteger theResultCount = [mdQuery resultCount];
theResultCount = 10; //for now
for (NSUInteger i; i < theResultCount; i++) {
NSLog(@"%@ %@ %ld %@", [self class], NSStringFromSelector(_cmd), (long)i, [mdQuery resultAtIndex:i]);
}
} else {
NSLog(@"%@ %@ NSMetadataQueryDidUpdateNotification: %@", [self class], NSStringFromSelector(_cmd), notification);
}
}
此代码在应用程序中运行良好,但使用插件运行时,只收到 NSMetadataQueryDidStartGatheringNotification ,没有别的。
我发现一两个帖子里有同样问题的人,其中一个(哦通知中的 James Bucanek,你在哪里?)通过调用 CFRunLoopRun(); 解决了他的问题。在 startQuery 和 CFRunLoopStop(CFRunLoopGetCurrent ()) 之后;当查询完成时。一个问题是这样启动的运行循环是同步的,而 NSMetadataQuery 显然是异步的,另一个是在插件中它从未通过 NSMetadataQueryGatheringProgressNotification。然后我尝试给 NSMetadataQuery 自己的线程,但同样,只收到了 NSMetadataQueryDidStartGatheringNotification。我不知道问题是否可以解决,但我真的很想提供一些意见。