Jason Fifer
Jason Fifer

Reputation: 25

Entity Framework: How to get the EntitySetName of a TPT or TPH Entity

I have an Employee entity that inherits from a Person entity that inherits from a Resource entity (Employee -> Person -> Resource). Is it possible to programmatically get the EntitySetName of Employee (which should be Resources)?

Upvotes: 2

Views: 1612

Answers (1)

Slauma
Slauma

Reputation: 177173

I take the example from here...

http://msmvps.com/blogs/kevinmcneish/archive/2009/12/03/entity-framework-programmatically-determining-the-entity-set-name-of-an-entity.aspx

... and consider only the else case in the code snippet (so, we have no entity instance with a key):

// I have tested with EF 4.1/DbContext, for EF 4.0 forget this line
var objectContext = ((IObjectContextAdapter)dbContext).ObjectContext;

Type entityType = typeof(Employee);
string entityTypeName = entityType.Name;

var container = objectContext.MetadataWorkspace.GetEntityContainer(
    objectContext.DefaultContainerName, DataSpace.CSpace);
string entitySetName = (from meta in container.BaseEntitySets
                        where meta.ElementType.Name == entityTypeName
                        select meta.Name).First();
string fullEntitySetName = container.Name + "." + entitySetName;

Now the problem is that this code throws an exception in First() because there is no BaseEntitySet with element type name equals "Employee". Obviously because there is only a set for the base type in the model = "Resource".

A possible fix is to change the second and third line above to:

Type entityType = typeof(Employee);
while (entityType.BaseType.Name != "Object")
    entityType = entityType.BaseType;
string entityTypeName = entityType.Name;

This should give back "Resources" as the entitySetName IF...

  • Your entities are not derived from EntityObject (in this case it would probably work if you replace "Object" by "EntityObject" in the while loop above)
  • Your entities are not derived from another custom type which is not an entity in the model. For example if you have Resource derived from a base type MyBaseObject but didn't include it in the model (there is no DbSet<MyBaseObject> or ObjectSet<MyBaseObject>) then you would have to replace "Object" by "MyBaseObject" in the while loop.

The second limitation is not nice because you could have different non-model base types in your entity classes which would make the code above not very general applicable.

Perhaps there is a smarter way to get the model base type directly from the MetadataWorkspace, but I don't know.

Upvotes: 3

Related Questions