Entity Framework Simple Generic GetByID but has differents PK Name

Here is example of base repository class for repositories build for entity with single property key. The GetByKey method is independent on key name or type.

using System;
using System.Data;
using System.Data.Metadata.Edm;
using System.Data.Objects;
using System.Linq;

namespace EntityKeyTest
{
    // Base repository class for entity with simple key
    public abstract class RepositoryBase<TEntity, TKey> where TEntity : class
    {
        private readonly string _entitySetName;
        private readonly string _keyName;

        protected ObjectContext Context { get; private set; }
        protected ObjectSet<TEntity> ObjectSet { get; private set; }

        protected RepositoryBase(ObjectContext context)
        {
            if (context == null)
            {
                throw new ArgumentNullException("context");
            }

            Context = context;
            ObjectSet = context.CreateObjectSet<TEntity>();

            // Get entity set for current entity type
            var entitySet = ObjectSet.EntitySet;
            // Build full name of entity set for current entity type
            _entitySetName = context.DefaultContainerName + "." + entitySet.Name;
            // Get name of the entity's key property
            _keyName = entitySet.ElementType.KeyMembers.Single().Name;
        }

        public virtual TEntity GetByKey(TKey key)
        {
            // Build entity key
            var entityKey = new EntityKey(_entitySetName, _keyName, key);
            // Query first current state manager and if entity is not found query database!!!
            return (TEntity)Context.GetObjectByKey(entityKey);
        }

        // Rest of repository implementation
    }
}

There is one trickler when using this code. If you don’t use generated class derived from ObjectContext and you use ObjectContext directly you must manually set DefaultContainerName used by your model.

Edit:

This method is for classic EF. I can think about version for Code-first if needed.

Leave a Comment