Many to Many Relationships with CodeFluent Entities
Yesterday, Scott Allen posted on his OdeToCode.com blog a very interesting blog post named Many to Many Relationships with EF illustrating how to setup a many to many relationship with EF Code First and then, and it’s the interesting part to us, how to use the SelectMany operator to “flatten” a sequence of book authors.
In fact, we thought it was so interesting that we decided to post a little something showing how to do it in a model-first way, using CodeFluent Entities. The result is the same, yet the way to do it is quite different.
Developing the Sample
Unlike EF Code First, CodeFluent Entities is model-first, therefore it all starts by creating a model.
Here’s our model (btw here’s a little preview of our soon-to-come vector-based & metro style theme):
Code generators (named producers in the product) will translate this platform independent model into actual code. So the SQL Server producer will translate the Book and Author entities into tables, their properties into columns, since a many to many relationship is declared between the Book and Author entities, an association table will also be created.
Another nice feature which you can see in the screenshot above is that you can add what we call “instances” to your entities which will be translated by actual lines of data. It’s a convenient way to initialize your generated database with data.
Now that we have our database and data, let’s write our method which will load all this data in a flat view.
Using CodeFluent Entities you can create actual SQL views and that’s precisely what we did:
Note: see the “Auto infer lightweight entitiy” checkbox on the upper right? Checking this will generate a dedicated .NET class mapped to your view ;) See here for more info.
We created a view named “FlatView” which selects book ids, titles and author names. Here’s what it generates:
CREATE VIEW [dbo].[vBooksFlatView] AS SELECT [Books].[Id], [Authors].[Name], [Books].[Title] FROM [Books] LEFT OUTER JOIN [Authors_Books_Books_Authors] ON ([Books].[Id] = [Authors_Books_Books_Authors].[Id2]) LEFT OUTER JOIN [Authors] ON ([Authors_Books_Books_Authors].[Id] = [Authors].[Id]) GO
Now that we have our view, we created method which loads from this view:
Methods are once again platform independent and will be translated in regular methods by a .NET producer or into stored procedures by a persistence producer. Here’s what the SQL Server producer generates:
CREATE PROCEDURE [dbo].[Books_LoadFromFlatView] AS SELECT [vBooksFlatView].[Id], [vBooksFlatView].[Name], [vBooksFlatView].[Title] FROM [vBooksFlatView] RETURN
Now let’s run side by side EF’s dynamically generated query (on the left) and CodeFluent Entities’ static one (on the right) to compare results:
Hooray, looks good
Points of Interest
Many to many relationships are easy to setup: create two properties, hold shift+click and make them point to one another, set its cardinality, and you’ve got your relation! Association tables and all related code will automatically be generated.
Initialize your generated database with data: specify instances to get test data or default data.
No dynamic code: CodeFluent Entities generates stored procedures, views and etc. No dynamic code is used to so you can easily debug and predict what’s going to happen at runtime.
Platform Independent: all this logic is outside of your code, it documents your application and provides a clear picture of what the application does and how it does it. Furthermore, you can add producers to translate this model to other technologies: want to go from C# to VB.NET? Push a button. Support Oracle Database or generate WCF Services? Add a producer.