|
I am working on another sample application that I am using as a means of teaching me some more things about Cocoa and programming on the Mac in general. I have been particularly fascinated with Core Data, so I started using it again in a new application.
I have a rather unique perspective on persistence tools because I have probably tested and developed in just about every conceivable environment for rapidly creating data-bound desktop applications, including some that called themselves "4GL" and were basically code generators that would inhale a data model and exhale an application. The general feeling I have come away with from tools that make it so that you can write a data-bound desktop application "with no code at all for the low-low price of $19.95!!" is that such tools are crap. They spend so much time insulating you from what is really going on that as soon as you want to do something other than build the "hello world" samples - you're knee deep in crap without a shovel.
This is not the case with Core Data. At first, I was extremely skeptical. I thought to myself, self: this is to easy. This is going to get ugly when I need to make some minor tweaks. So, I went ahead and wrote another sample app and sure enough, I needed to perform a minor tweak.
Problem 1: I created my model. I have two attributes, one is a number (Int32) and the other column is a date column. I created a table view and bound the columns to the attributes in my entity. Everything looked fine. I ran the app. Whenever I tabbed out of a field, I'd get an error showing up in my Console complaining about a data type mismatch. Basically it looked like the table view was sending a string to the bound attribute, and the bound attribute needed an integer or a date.
Solution 1: Thanks to some tips from a knowledgeable resource on Cocoa, I figured out that I could just drag a number formatter into the number cell, and drag a date formatter into the date cell. Problem solved. My thoughts: holy crap that's easy.
Problem 2: I wanted to make it so that whenever I clicked the "+" button that was linked to the "insert:" action, the date on the underlying model object (which is a core data entity) would be today's date. There didn't seem to be any way to do this in the user interface, so I got scared.
Solution 2: It was actually really , really easy. I created a new class that inherited from NSManagedObject called KHWeighInEntity. I then changed the type of my entity from NSManagedObject to KHWeighInEntity. Then, I overrode a single method in this class as follows:
- (void)awakeFromInsert
{
[self setValue:[NSCalendarDate date] forKey:@"weighInDate"];
}
That's it. Done. I didn't have to go through the hoops of building a brand new "wheel", all I had to do was override the part of the wheel that needed tweaking, and I was done. To me, scenarios like this are why inheritance was conceived. Here's the fantastically cool part: I can continue to model and extend my entity in the entity designer, and it won't impact the code I've already written. I don't have to manually add attributes to my new custom class... it's still all extremely seamless.
The more I use Core Data (and, of course, Cocoa), the more I become a huge fan. In short, Core Data is a rare example of a solution that allows you to rapidly build solutions without writing a single line of code...and... when you need to write code to create a more powerful solution, that task is simple, quick, and painless.
This sounds good, however as a recent Mac switcher (from Windows and Win32,
.NET) etc, I wonder where in Cocoa do I find database access? I.e. where in
Cocoa (or Carbon or Objective C) do I have classes for database access?
Core Data gives you access to Sql-lite as a persistence medium for your
model/entities.
OK, but what if I want to access data from Oracle, MySQL etc???
I'm sure one of the Cocoa experts reading this can point you in the right
direction, but I believe that there is a Cocoa interface for the Mac ODBC
drivers.
Thanks Kevin. I'll have a search around myself.
Found this - mySQL access from Cocoa:
http://mysql-cocoa.sourceforge.net/
Kevin,
James, I guess you'll find this page very interesting:
For connectivity with real databases, there's AJRDatabase
(http://sourceforge.net/projects/ajrdatabase/). It's an EOF
reimplementation, so you don't get all the CoreData-y goodness.
Then there's BaseTen (http://www.karppinen.fi/baseten/), which is under GPL
or for-pay license, only has adaptors for Postgres, and is reasonably
Coredata-like.
Thanks Johannes! I googled last night after having posted my comments, and
came across it Looks interesting! I really wonder why Apple ripped EOF out
of Cocoa, what a stupid thing to do
HelgeG,
I guess Apple ripped EOF out of Cocoa for 2 reasons.
I'd like to point out something about CoreData that may go unnoticed.
I asked the same question recently and found the following:
... and maybe also check out http://jtds.sourceforge.net for db
connectivity...