We just pushed a Realm Objective-C update to this website and to CocoaPods. Here’s what’s new!
LLDB Support Script
Our Xcode Plugin now comes with a LLDB script which adds support for inspecting persisted RLMObjects, RLMResults and RLMArrays objects in Xcode’s UI, rather than just displaying every property as nil
or 0
:
N.B.: The script currently only supports Objective-C. Swift support is in progress and should be ready by the next release.
invalidate
We’ve added an invalidate
method to RLMRealm to make it possible to close long-running (implicit) read transactions, which is useful when doing a large number of writes in parallel.
In order to give you a consistent view of your data, Realm only updates the active version accessed between iterations of the run loop. This means that if you read some data from the Realm and then block the thread on a long-running operation while writing to the Realm on other threads, the version is never updated and Realm has to hold on to intermediate versions of the data which you may not actually need, resulting in the file size growing steadily. (This extra space would eventually be reused by future writes, or could be compacted — for example by calling writeCopyToPath:
.) Instead, calling invalidate
tells Realm that you no longer need any of the objects you’ve read from the Realm so far, and frees us of tracking intermediate versions of those objects.
For example, in the following code, without the call to invalidate
, Realm would have to make a copy of the object modified in each write transaction, since it can’t know that the older version won’t be used after the dispatch_group_wait
.
- (void)doWork {
RLMRealm *realm = [RLMRealm defaultRealm];
dispatch_group_t g = dispatch_group_create();
dispatch_queue_t q = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
// Read some data from the Realm on the current thread
RLMResults *objects = [ExampleObject objectsWhere:@"boolProperty = NO"];
NSUInteger startCount = [objects count];
// Tell Realm that we're done with all of the data we read on this thread
// Accessing `objects` after this will throw an exception
[realm invalidate];
// Mutate some objects on other threads
for (NSUInteger i = 0; i < 100; ++i) {
dispatch_group_async(g, q, ^{
RLMRealm *realm = [RLMRealm defaultRealm];
[realm beginWriteTransaction];
ExampleObject *obj = [[ExampleObject objectsWhere:@"boolProperty = NO"]
firstObject];
obj.boolProperty = YES;
[realm commitWriteTransaction];
});
}
// Wait for the background work to complete
dispatch_group_wait(g, DISPATCH_TIME_FOREVER);
// Will be startCount - 100 (assuming startCount > 100)
// Would be equal to startCount without the call to invalidate since the
// Realm would be pinned to the same version for the duration of this method
NSUInteger endCount = [[ExampleObject objectsWhere:@"boolProperty = YES"] count];
}
N.B.: calling invalidate
will cause all RLMObjects and RLMResults read from this RLMRealm to be invalidated, meaning you will have to fetch them again if you need to access or edit them.
Automatic Rollback on RLMRealm Deallocation
Deallocating an RLMRealm instance in a write transaction lacking an explicit commit/cancel will now be automatically cancelled instead of committed. A message will be logged whenever this happens. Areas where this occurs should be rectified so that all write transactions be explicitly closed (either by calling commitWriteTransaction
or cancelWriteTransaction
).
New Features
- BEGINSWITH, ENDSWITH, CONTAINS, and case-insensitive comparisons are now supported when querying array properties (e.g.
[Person objectsWhere:@"ANY dog.name CONTAINS 'a'"]
to fetch all people who have a dog whose name contains an ‘a’). - RLMRealm now has a method
writeCopyToPath:
which writes a compacted copy of the Realm’s data to the given file path. - The location of the default Realm can now be set by calling
+[RLMRealm setDefaultRealmPath:]
. This can be used to make unit tests use a different Realm file from your application code (while still being able to use the convenience methods for the default Realm), or just if you want the Realm file in a different place.
Performance Improvements
- Reading values from RLMResults and RLMArray has been significantly sped up: fast enumeration takes about 30% less time, and
objectAtIndex:
,firstObject
andlastObject
take about half as long. - Calling
firstObject
andlastObject
on a newly created RLMResults no longer results in the query being run twice.
Bug Fixes
- We’ve fixed two crashes: one which would occasionally occur when performing write transactions on a large number of threads at once, and one when opening multiple Realm files at once which have different column orderings (due to rearranging properties).
- The schema version for newly created Realm files is now set to the correct value rather than always being 0.
- Failing to supply a migration block when one is required now gives a much less confusing error message.
Thanks for reading. Now go forth and build amazing apps with Realm! As always, we’re around on the mailing list, StackOverflow, GitHub, and twitter.
Receive news and updates from Realm straight to your inbox