Shared Instance of NSManagedObject
I have come upon a situation, in the project that I’m working on, where I need a single shared instance of NSManagedObject. I looked around for a common practice and there was none except for some misguiding Q&As on Stack Overflow. There were (are) probably more people than I that need this kind of functionality yet they didn’t publish their solutions. That or I didn’t try hard enough to actually find them. So I decided to whip it up.
I decided to whip up my own solution not only because I was struggling to find an existing one, but also because it was something new and something that I haven’t stumbled upon before.
The setup: let’s say that I have a fictional project which has users and something else that users can add, edit, delete and read. In the app itself I’d like to have a very quick access to default user account. For the sake of clarity: WSAccount entity represents the account entity and it is being wrapped by WSAccount class instances in the code. Since it is supposed to be a shared instance, I started smelling singleton pattern. I do know that singletons are evil. To be honest - I really do my best to actually avoid singletons in my code as hard as I can. I think for the first time in my coding career I was saved by constraints put on framework by its creators. And here’s why.
Since NSManagedObject depends on NSManagedObjectContext. And NSManagedObjectContext is not thread safe, I figured that shared instance should be reinstantiated depending in which context you require it to be. Hence the method name was born:
1 2 3 4 5
It may be weird for you, but I am one of those guys that don’t mind passing existing or new managed object context from one view controller to another. For me fetching the default managed object context from app delegate all the time is really uncomfortable. Including that “AppDelegate.h” in every possible file (it’s just one of those ways when headers cripple your code), doing the casting. Ugh…
For me, passing the managed object context along the application flow seems more… flowy. It also benefits you from actual possibility to have transient managed objects, not worry about failed validations and existing objects (fetched in other MOCs) can be retrieved in a single call!
Now tagging along the implementation, I defined the static variable and assigned it to nil (just like in singleton!!!).
1 2 3 4 5
Now for the actual method implementation - it’s quite simple. There is one extra check to be made before doing the fetching thing. Here’s the code with comments
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42