best data persistance for NSObject subclass - ios

I'm fairly new to iOS development, so I need some advise.
I'm working on a project (creating a character sheet app for an upcoming table top RPG), and I seem to have put the cart a bit before the horse.
I've already created a subclass of NSObject called characterClass that holds everything I need for a single instance of the character sheet. It also has methods to calculate derived information. I have 2 more classes storing abilities, and have them in NSArrays in the characterClass. Now that it's working, I need to work on data persistance, and storing/retrieving multiple characters.
I'm thinking, of using Core Data, creating a separate entity that matches my characterClass, and having a characterClass init method that pulls the data out of Core Data and puts it into the current instance of characterClass. That seems a bit obtuse to me, (implementing a class separate from the entity) but maybe it's a good way to do it.
I would eventually like to set up dropbox syncing for this information, so whatever I do I would like to have compatible with that. (Core Data with XML files as the backend?)
What would be the best method for something like this?

Rather than just pull the data out of Core Data and use it to create your character class, you could just tweak your character class so that it is an NSManagedObject subclass. That way you are storing your objects directly in Core Data

Related

What's the simplest way to encode a chosen 'root' Core Data entity together with all of its relationships?

I use Core Data within my iOS 7 app to handle the editing and creation of entities. The entities have relationships between them, which all have inverses (as Apple advises).
For the sake of this question, let's pick any one of these interrelated entities and call it the Root entity: the thing that I want to encode with; the thing that logically lives on the 'top' of the hierarchy. I will call this the 'object graph'.
The question is:
What's the easiest way of encoding and decoding such an object graph to and from NSData?
The reason I want to do this is that I'd like my Core Data object graph to be persisted onto a cloud service, without the need of writing my own NSIncrementalStore subclass (it's a bit involved...!).
AutoCoding together with HRCoder almost looks like it could do the job, but I've experimented with this combination and it doesn't quite work with NSManagedObjects at the time of writing.
Still, I'm seeking alternatives. There can't only be one way to do this, surely.
It doesn't have to be JSON, but it'd be nice. Binary would be fine.
It seems to me you do not need to subclass NSIncrementalStore. You can create records and save them to your store with a plain vanilla store created via addPersistentStoreWithType:... with a NSPersistentStoreCoordinator.
The straight-forward way is to handle the incoming JSON by simply taking the data and copying it to the properties of your NSManagedObject subclasses, like this:
object.title = jsonDictionary[#"title"];
object.numericAttribute = [jsonDictionary[#"numericAttribute] integerValue];
If you take care about naming the attribute and entity names exactly the same you can maybe use some shortcuts using KVC, like
[object setValue:jsonDictionary[key] forKey:key];
I once did the above for a large legacy project where it was not feasible to repeat the old attribute names, so I used a custom property list (plist) to match around 800 attribute names.

JSONModel with MagicalRecord

MagicalRecord is a nice library to manage coredata.In my application I have to processes json from web service for managing Json we are using JSONModel. Now the problem is I have to use two separate class to manage magical record and jsonModel.
Is there any way by which I can combine these two?
Thanks in Advance.
What I personally do is to add to all my JSONModel instances a method called:
-(id)mergeWithContext:
Whenever I get a JSON object from the web, JSONModel parses it for me and converts the data to what I need, then if I want to save it to CoreData I just call mergeWithContext: and pass the current context to it.
The further in my mergeWithContext: method I just create a new entity matching the current JSONModel object and copy over all values. (I actually also check whether an entity with the model's ID already exists in CoreData - then I update it, otherwise I create a new instance).
Not too difficult and you get a fair amount of flexibility if you need to add some custom behaviour when the data is saved.
mergeWithContext: returns of course the entity itself, so I can work with it further if I need to.

How can I have multiple copies of an object that are identical update while instantiated as separate objects in different view controllers?

I'm trying to have multiple copies of a single product objects in different view controllers (i.e. you have a product in a shopping list and when you search queries web-service and returns searched products). There is a symbol on search tableviewCell if that product is in the shopping list.
I thought of two ways to do this:
Have an array in a singleton class that caches the products in a NSMutableDictionary by their id numbers and every time a products is created it check to see if there is one in its place. If so it just uses the product already there. I can have a setting in the product that states if it is on the shopping list or not.
Use core data. I tried to implement it but not sure how I can exactly do this. I was thinking of using core data so that when i update a product object it is also updated in other parts of the app using NSFetchedResultsController.
What is "standard practice" for this situation?
Let me know what you think and how you would approach this. Thanks!
You can use singleton pattern for your data manager class, which will hold your data in an array of Models (For e.g.: Product)
If you use singleton data manager (for e.g.: ProductManager) then your data (for e.g.: Product entities) would be persistent for all your class files in application life cycle mode.
Here you can find more information:
Objective C Singleton Class
http://www.galloway.me.uk/tutorials/singleton-classes/
Hope this is what you are looking for.
if the shopping list doesnt need to be written to disk, option 1 is fine. if it does need to be written to disk, you can use core data.. or use sqlite, or NSArchiver. there are a few ways of storing data.

About the Core Data base design

I'm devellopping an IOS app for one month and I feel like I'm ready to create the data base. So as I've learn at school, I took my pencil and start to create my data base design.
Then I start to read the core data guides, in fact I've already used core data but it was in smaller projects. So I read about the Managed Object and they seems to always fit exactly the model object (MVC) of the applications.
So this is my question. Does I have to write the Managed Objects as an sqlLite data base shema (with split tables etc...) and start to write some methods to construct my model objects from thoses tables ? OR should I write the managed object exaclty as the Model objects ? They will be reconstructed much easier but won't it be less efficient?
To ask it in an other way: do the core data base shema should looks like an sqlLit data base with split tables or should it looks like as a set of my Model Objects?
I hope my question is clear.
Thank you,
Alexandre
If you want to use core data, you should not, in any way interact with the SQLite database. The exact way core data stores the objects should be opaque to you.
There is nothing to stop you writing the database layer yourself. You can make and interact with an SQLite database directly and do everything yourself.
General advice is that core data has been around a long time and any issues you encounter making objects and keeping them in sync across threads, caching and speed of access have already been encountered and fixed by the core data team. Save yourself some work, Stand on the shoulders of giants and use Core Data.
Just because you have tagged your question with iOS, one of the best things you can do, is to forget about traditional model relationship techniques you have previously used in relational database (especially the one used with web applications), and structure your NSManagedObject graph depending also on the use you are doing in your UI.
This is especially true when you have something like UITableView. For example, if you are showing only title and description in a table cell, and then you have detail view with all the data, it has perfect sense to model your graph like this:
EntityMain {
NSString *title,
NSString *desc,
// other that may be useful, such as a state...ecc
toOne relationship --> EntityDesc
}
EntityDesc {
NSString *prop1,
NSString *prop2,
......
....
NSString *prop 20
}
Where EntityMain is retrieved, say, by a NSFetchedResultsController, while in the detail view you can retrieve the whole object. In this case you are not fetching more than necessary, and performance will benefit.
This will also help you in case you want to have a separated NSManagedObjectContext for detail editing.

Save an existing Model to a CoreData DB

I'm learning Core Data and I understand all the examples for creating a brand-new object, assigning values and saving it to the managedContext (insertNewObjectForEntityForName).
However, what if I've already created an object elsewhere (model Category)? In this case I'd want to just assign the current Context to this Model, and then save it.
What is the command/approach to take an in-memory Model, and then assign to a context so it can be saved?
If you want to use Core Data to manage your data, you'll need to:
create an appropriate model description (.xcdatamodeld file)
modify your model class(es) so that they inherit from NSManagedObject
set the "Class" for each entity in your model description to one of your NSManagedObject subclasses
add code to your app to create and manage the Core Data stack, fetch data, etc.
This is all very do-able, but I wouldn't recommend that you attempt it until you have a solid understanding of Core Data and your reasons for adopting it in your project. The lack of clarity in your question may indicate that you're not quite there yet; you might benefit from working on a small project that uses Core Data from the start.
If all you want to do is to save your data, you should know that Core Data is not the only way to do that. A much simpler approach to saving your data would be to adopt the NSCoding protocol in your data model and then use a NSKeyedArchiver to store your data. Get the full story from the Archives and Serializations Programming Guide. There are other ways to do it as well, but NSKeyedArchiver is a good place to start.
You can only save NSManagedObjects (and their subclasses) to CoreData. NSManagesObject can not be created except in the context of an NSManagedObjectContext.
So, what you're saying is confusing. Do you have a non-CoreData model object?

Resources