Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Entity Framework 4.0 - Get By ID Using Generics and Reflection

I am looking to be able to load an entity by ID using generics and property reflection but am unsure how to accomplish this task using Entity Framework 4.0.

I have a method in my abstract method as such:

public abstract T GetById(object id, TestContext context);

Currently, since it is abstract, I have to implement this method in every single repository class I create as such:

public override TestObject GetById(object id, TestContext context)
{
    return context.TestObject.First(x => x.TestId == (int) id);
}

Is there a way to accomplish this same task using reflection and generics in my abstract class?

like image 715
Brandon Avatar asked Mar 10 '26 19:03

Brandon


1 Answers

This is a VB example that I use. My keys are all GUIDs, but you can probably adapt this.

Public Shared Function GetKeyPropertyName(ByVal typeName As String) As String
    Dim props = Type.GetType(typeName).GetProperties
    For Each prop In props
        Dim atts = prop.GetCustomAttributes(True)
        For Each att In atts
            If TypeOf (att) Is EdmScalarPropertyAttribute Then
                If DirectCast(att, EdmScalarPropertyAttribute).EntityKeyProperty Then
                    Return prop.Name
                End If
            End If
        Next
    Next
    Throw New ApplicationException(String.Format("No key property found for type '{0}'.", typeName))
End Function

Public Shared Function GetObjectById(Of T As EntityObject)(ByVal id As Guid) As T
    Dim ctx = MyContext
    Dim entityType As Type = GetType(T)
    Dim entityTypeName As String = entityType.ToString
    Dim keyProperty As String = GetKeyPropertyName(entityTypeName)

    Dim container = ctx.MetadataWorkspace.GetEntityContainer(ctx.DefaultContainerName, Metadata.Edm.DataSpace.CSpace)

    Dim entitySetName As String = (From meta In container.BaseEntitySets Where meta.ElementType.FullName = entityTypeName Select meta.Name).First()
    Dim entitySetFullName As String = String.Format("{0}.{1}", container.Name, entitySetName)


    Dim entityKeyValues As IEnumerable(Of KeyValuePair(Of String, Object)) = _
        New KeyValuePair(Of String, Object)() {New KeyValuePair(Of String, Object)(keyProperty, id)}

    Dim key As New EntityKey(entitySetFullName, entityKeyValues)
    Return DirectCast(ctx.GetObjectByKey(key), T)
End Function
like image 123
Bill Daly Avatar answered Mar 13 '26 10:03

Bill Daly



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!