I started looking at the latest the EF team had to offer and while things have progressed immensely over the years it appears that there is still some room for improvement. Given the turmoil over the possible demise of LINQ to SQL I know that the use of Entity Framework is inevitable for me and probably just around the corner.
With my newest project I have started to plug in an ADO.NET Entity Data Model (EDMX) where I would normally plug in LINQ to SQL Classes (DBML). I still dropped the file into my Domain directory so that all the classes that are generated show up where I would expect them. I then connect to my database in the Server Explorer, expand my database, then expand tables, and drag over all of my tables unto the new Entity design surface. This creates a bunch of classes for me named exactly as my tables are named? ARGH! This is the first pain point. I rename each and every table from a plural form to a single form. With this corrected I can then go in and edit my Connection() helper class to return Entities instead of a DataContext.
From this…
0: public class Connection
1: {
2: public RanchBuddyDataContext GetContext()
3: {
4: string connString = ConfigurationService.GetRanchBuddyEntitiesConnectionString();
5: RanchBuddyDataContext dc =new RanchBuddyDataContext(connString);
6: dc.CommandTimeout = 60;
7: return dc;
8: }
9: }
To this…
0: public class Connection
1: {
2: public RanchBuddyEntities GetContext()
3: {
4: string connString = ConfigurationService.GetRanchBuddyEntitiesConnectionString();
5: RanchBuddyEntities dc = new RanchBuddyEntities(connString);
6: dc.CommandTimeout = 60;
7: return dc;
8: }
9: }
That was pretty easy! I can now start to create my repository layer which connects to my database through the Entity Framework. The syntax is a little different but mostly the same. And once you get the hang of it it is very easy to get to work. Where I used to select directly from DataContext.TableCollection I now have to do something like this to select a record:
0: public Account GetAccountByUsername(string Username)
1: {
2: Account result = null;
3: using (RanchBuddyEntities dc = connection.GetContext())
4: {
5: result = dc.AccountSet.Where(a => a.Username == Username).FirstOrDefault();
6: }
7: return result;
8: }
Something like this to save a record:
0: public RepositoryStatus SaveAccount(Account account)
1: {
2: RepositoryStatus rs = new RepositoryStatus();
3: try
4: {
5: using (RanchBuddyEntities dc = connection.GetContext())
6: {
7: if(account.AccountID > 0)
8: {
9: dc.Attach(account);
10: }
11: else
12: {
13: dc.AddToAccountSet(account);
14: }
15: dc.SaveChanges();
16: }
17: rs.SetObject(account);
18: rs.AddMessage("Your account was successfully saved!");
19: rs.StatusType = Status.StatusTypes.Success;
20: }
21: catch(Exception e)
22: {
23: rs.SetObject(account);
24: rs.AddMessage(e.Message + e.StackTrace);
25: rs.StatusType = Status.StatusTypes.Failure;
26: }
27: return rs;
28: }
And something like this to delete a record:
0: public RepositoryStatus DeleteAccount(Account account)
1: {
2: RepositoryStatus rs =new RepositoryStatus();
3: try
4: {
5: using (RanchBuddyEntities dc = connection.GetContext())
6: {
7: dc.Attach(account);
8: dc.DeleteObject(account);
9: dc.SaveChanges();
10: }
11: rs.SetObject(new object());
12: rs.AddMessage("Your account was successfully deleted!");
13: rs.StatusType =Status.StatusTypes.Success;
14: }
15: catch(Exception e)
16: {
17: rs.SetObject(new object());
18: rs.AddMessage(e.Message + e.StackTrace);
19: rs.StatusType =Status.StatusTypes.Failure;
20: }
21: return rs;
22: }
In some ways this is actually easier than working with LINQ to SQL. Let’s continue on.
Ok, I added a column to one of my previously included tables. In LINQ to SQL I would just delete the entity and re-drag it to the design surface. Let’s do that here for EF. Deleting the entity works great. Now let’s re-add the table. Wait…it won’t let me? What is that about. Apparently there are issues with the designer that don’t quite clean every thing out as one might expect. Deleting the entity only removed it from the view. As far as EF is concerned the entity is still in play! To really delete the table so that you can re-add it you have to dig into the EDMX and remove all references to that table! FUN FUN FUN.
With the table deleted, then all references to the table deleted, I am now able to add my table back to the design surface. Cool. Close the design surface and let’s do something else. (this only happens now and then…but bare with me!) Oh wait…re-open the design surface real quick and let’s do a bit more work there. Wait…what’s this…Visual Studio periodically forgets how to open an EDMX file you say? Guess what…the only way to correct this issue is to close your solution and reload it! The other stuff I can live with. But this particular issue is sort of lame!
All in all and especially since I have no choice – working with the Entity Framework doesn’t seem like brain surgery just yet. I am hoping that all the issues I had working with disconnected contexts and many to many tables is rectified. Also, I am hoping that having all the relationships left intact doesn’t cause me the same pains as LINQ to SQL did…guess I can always turn them off like I tend to do in LINQ to SQL.