I was puttering around in an attempt to clean up my mess of ruby omnifocus-organisation scripts today1 (using macruby) when I hit a bump:
1 2 3 4 5 6 7 8
#!/usr/bin/env macruby framework "ScriptingBridge" of = SBApplication.applicationWithBundleIdentifier("com.omnigroup.omnifocus").defaultDocument predicate = NSPredicate.predicateWithFormat("completed = YES") of.flattenedTasks.filterUsingPredicate(predicate).each do |task| # More code here... end
Run this, and you get something like the following:
1 2 3 4
2013-04-14 19:43:09.235 macruby[88194:60b] -[SBObject classForCode:]: unrecognized selector sent to instance 0x400189ce0 uncaught Objective-C/C++ exception... 2013-04-14 19:43:09.237 macruby[88194:60b] *** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: '-[SBObject classForCode:]: unrecognized selector sent to instance 0x400189ce0' *** First throw call stack...
This is somewhat annoying, but I’d encountered it before. As far as I can work out, macruby lazily evaluates these sort of filters when they’re needed, and calling
#each on the search doesn’t evaluate it. If I had to guess, I’d say it was a communication breakdown between macruby and cocoa. There is a simple solution, however:
1 2 3
of.flattenedTasks.filterUsingPredicate(predicate).allObjects.get.each do |task| # More code here... end
This effectively gets all the objects for you, like you’d expect.
It’s like gardening, only with less concrete outcome and I can’t really tell my parents anything about it. ↩