In short: Yes. It's possible, if I understand what you're talking about. Is it easy? No F'ing way. I just got done implementing core data and it was a real bitch. Most of the tutorials and examples floating out there don't do much good in explaining WTF is going on ... they just show you how to get it working, not how to get it working for what YOU want to do with it.
I wound up buying the eBook on the iPhone SDK from Pragmatic Bookshelf. It's got a chapter on Core Data. While it didn't go into much detail on relationships, it was a good start.
I've got a many-to-many relationship between two object models. I wound up creating a third object model to act as an intermediary ... it does one-to-many to my main objects, and thus in the end I've got a many-to-many relationship.
The real bitch for me was that I had to build in the Core Data implementation in stages. First I implemented one object model, and got it populated with a property list. Then, I'd start implementing the middle object model (keeping it ignorant of either of the two main models) ... get it populated with dummy data, just to make sure I had it working. Then I created the relationship from it to the first one, which broke my persistent store without telling me why it was failing. Then once I had that relationship working and populating, I went over to the third model and built it up by itself and populating with it's property list. Then I connected it over to the middle object model ... then magically it all works.
Apple's documentation on Core Data is a f*ing joke. I'm serious. Totally worthless.
The most powerful thing out of all of this is the predicates. But they also are the hardest to wrap your head around. No one has much GOOD documentation on how you should use them to get your crap together.
Quote:
Originally Posted by cation007
Hi,
I am trying to save and retrieve a hierarchy of objects. I know its not easy to do it with sqlite3.
Is it possible to do this with Core Data ? can I save all the objects and retrieve them, modify them save them back to file using core data?
You're bang on. I thought it was me being thick struggling to make sense of using core data. All I wanted to learn was how to maintain persistent data. I got caught up in the move to OS 3 and was advised to use core data. Sounded simple until I tried it. I've still not found any spot on resource yet for walking through a meaningful real world app that I could use. If anyone finds something that was a real help please let me know. Until then I'll be trying to make sense of it. Regards.
You're bang on. I thought it was me being thick struggling to make sense of using core data. .
You need to work thru the Apple tutorial and build the locations project. I started with photolocations as the basis for my application, once I undertood the data model I started changing and adding entities. After that it got to be really easy.
Of course I use sql on the job a lot, and am no stranger to data modeling. The tools built into xcode are probably medium scale as far as modeling tools go but they get the job done.
Once you understand core data you begin to wonder why it was so painful to learn.
Start with the apple tutorials
Then Read the getting started on core data doc
The conference sample in the pragmatic book is good, but some things don't work quite right on it.
Thanks for the heads up on the samples. I'm getting thru the tutorials and samples, but trying to understand everything at first read got me bogged down. I can now push on with your tips knowing it got easy for you.
Thanks for the heads up on the samples. I'm getting thru the tutorials and samples, but trying to understand everything at first read got me bogged down. I can now push on with your tips knowing it got easy for you.
No problem, here's a couple more.
Start with the project from the locations tutorial. There are three samples..
locations, photolocations and taggedlocations.
Taggedlocations is a nice one to start on.
Click on the model to bring up the modeler.
now Try adding an entity
Tagged locations has a single location, photolocations has two entities, An event and a photo, there is a 1 to 1 relationship here.
I would suggest adding a catagory entity, again make it 1 to 1, as every event should be tied to a single category for simplicity. I suppose you could make it 1 to many if you want. ie.. multiple categories for each event.
Click the plus sign under entitiy to add the new entity, now add some fields, make sure you define a relationship on the event (ie. category) between the event and the category.
Now rename all the current entity class or save it somewhere, now generate the new model. A new event class and a category class will be generated. Copy any custom stuff thats in your saved entity class to the new class.
Its best when first learining to let the modeler generate the code, later after you get a hang of it, you can add the class attributes yourshelf.
Now very important, assuming you are working in the simulator go to
yourUser/applications/iphoneSimulator/somelongstring/documents and remove the existing sqllite file.
Now build and test the project.
Play with it, add more entities, more relationships etc.
Read about fetched results sets in the programming docs, and try using that... its really cool.
Great help. I'm happy using the modeler to add entities, attributes, relationships etc (ps thanks for tip on the gotcha when using simulator), I need to go back over the basics. I'm looking to load a tableview with summary record data from a persistent store and then on row selection show another view with all record data with ability to edit, save and create new. I have most of the jigsaw pieces now, your sample suggestions may be the instructions and big picture I need. Your help most appreciated. I'll let you know when the penny drops and I can run downhill for a change!
Could anybody please help me figure out how to add a text note field to apples PhotoLocations sample. Or if you can point me to an article that would help. I have no experiance with SQL and have tried to figure it out but no luck so far. Any help would be apreciated. I would like to be able to type a note into a field just above the picture and below the gps location that would be saved to the sql database. I have added a text field that I can edit but it does not save it because I am not sure how to add it to the database.
Could anybody please help me figure out how to add a text note field to apples PhotoLocations sample. Or if you can point me to an article that would help. I have no experiance with SQL and have tried to figure it out but no luck so far. Any help would be apreciated. I would like to be able to type a note into a field just above the picture and below the gps location that would be saved to the sql database. I have added a text field that I can edit but it does not save it because I am not sure how to add it to the database.
Thanks again,
Mark
go into the modeler , add a an attribute to the photo locations entity. save the model. Make sure the new attribute has been added to the .h header file for the locations entity.
go into the modeler , add a an attribute to the photo locations entity. save the model. Make sure the new attribute has been added to the .h header file for the locations entity.
Thanks I tried that earlier and it didn't work. This time I changed the name of my project so it made a new copy of the app on my iPhone then it worked. So I guess you need to delete the old database when you add to it.
Thanks I tried that earlier and it didn't work. This time I changed the name of my project so it made a new copy of the app on my iPhone then it worked. So I guess you need to delete the old database when you add to it.
Sorry, should of mentioned that, but I did early in this thread. Either delete the database or simply rename the reference to it.
When I first started playing with core data I had the same problem you think they would make a point to document that better.
The sqlite database is usually in the documents folder.
Sorry, should of mentioned that, but I did early in this thread. Either delete the database or simply rename the reference to it.
When I first started playing with core data I had the same problem you think they would make a point to document that better.
The sqlite database is usually in the documents folder.
Do you know how to create a blank database based on an xcdatamodel? The template in XCode has the logic if the database doesn't exist, you copy a blank one from the application bundle. I just don't know if it's just a place-holder document of .sqlite file-type or is it a real db file based on the model schema. Any help?
Thanks.
Do you know how to create a blank database based on an xcdatamodel? The template in XCode has the logic if the database doesn't exist, you copy a blank one from the application bundle. I just don't know if it's just a place-holder document of .sqlite file-type or is it a real db file based on the model schema. Any help?
Thanks.
Well you would need to either delete the one created in the docs directory or give the database a new name and redeploy to the device.
Well you would need to either delete the one created in the docs directory or give the database a new name and redeploy to the device.
Hmmm... The reason I am asking is that when I run the app in the simulator, the database file does not exist yet in the documents folder. So as per the template, a blank db is copied from the applications bundle to the documents folder.
This blank db had to be created somehow. And that's my question: How do you initially create a blank database based on your xcdatamodel schema?
Hmmm... The reason I am asking is that when I run the app in the simulator, the database file does not exist yet in the documents folder. So as per the template, a blank db is copied from the applications bundle to the documents folder.
This blank db had to be created somehow. And that's my question: How do you initially create a blank database based on your xcdatamodel schema?
I assume you've figured this out by now, but if you use the Xcode templates to build a Navigation- or Window-based app, Xcode will create an empty DB for you using the name "<yourappname>.sqlite" if it doesn't already exist. The template doesn't copy anything from your app bundle, unless...
...you want to. If you want to copy over a prefilled database, you can do that in the persistentStoreCoordinator getter in your appDelegate file. Assuming you've created a fully fleshed out Core Data app that has data in it and have run it on the iPhone simulator:
Close the app
Look for your app in one of the folders in ~/Library/Application\ Support/iPhoneSimulator/User/Applications
You'll see a lot of folders with UUIDs for names. If your app was the last one run, you can sort the folders by Date Modified to find yours.
Once you find the right folder, look in the Documents folder and you'll see your .sqlite database. Drag it into your project anywhere (I stick mine in the Resources group normally.)
Now in the appDelegate file, replace the persistentStoreCoordinator getter with the following:
Code:
- (NSPersistentStoreCoordinator *) persistentStoreCoordinator
{
if (persistentStoreCoordinator != nil)
{
return persistentStoreCoordinator;
}
NSString *storePath = [[self applicationDocumentsDirectory] stringByAppendingPathComponent:ksDatabaseFilename];
#if defined(USE_DEMO_DATABASE)
// if we're testing, use a pre-built sample database.
NSFileManager *fileManager = [NSFileManager defaultManager];
// If the expected store doesn't exist, copy the default store.
if ( ! [fileManager fileExistsAtPath:storePath])
{
NSString *defaultStorePath = [[NSBundle mainBundle] pathForResource:@"Travellers" ofType:@"sqlite"];
if ( defaultStorePath )
{
[fileManager copyItemAtPath:defaultStorePath toPath:storePath error:NULL];
}
}
#endif
NSURL *storeUrl = [NSURL fileURLWithPath:storePath];
NSError *error;
persistentStoreCoordinator = [[NSPersistentStoreCoordinator alloc] initWithManagedObjectModel: [self managedObjectModel]];
if ( ! [persistentStoreCoordinator addPersistentStoreWithType:NSSQLiteStoreType configuration:nil URL:storeUrl options:nil error:&error])
{
// Handle error
}
return persistentStoreCoordinator;
}
Obviously, #define USE_DEMO_DATABASE somewhere to use the copy function.
Now your app has a pre-cooked Core Data object context.