Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Generic access to DbContext

ObjectContext allows generic access to the generated Entities. DbContext appears to have no such support. Accessing EF5 with a generic repository is challenging. Let's say I want a generic mechanism to read any given entity, call it TEntity:

public class DataRepositoryEF5<T> where T: DbContext
{
    private ObjectContext _context;        

    public DataRepositoryEF5(DbContext context)
    {
        _context = ((IObjectContextAdapter)context).ObjectContext;
    }

    public IEnumerable<TEntity> ReadAll<TEntity>() where TEntity : class,new()
    {
        return GetObjectSet<TEntity>().AsEnumerable();
    }

    protected ObjectSet<TEntity> GetObjectSet<TEntity>() where TEntity : class,new()
    {
        ObjectSet<TEntity> result;
        result = _context.CreateObjectSet<TEntity>();
        return result;
    }
}

Usage

            var context = new MyContext();            
            var repository = new DataRepositoryEF5<MyContext>(context);

            IEnumerable<Document> results = repository.GetAll<Document>();

            foreach (var item in results)
            {
                Console.WriteLine("{0} {1} {2} {3}", item.Description, item.Id, item.Property, item.Whatever);
            }

EF used to generate classes with a common base type EntityObject. Since that is no longer the case the best constraint I can have is class...

Second, because there is no equivalent of ObjectContext.CreateObjectSet<>() I am forced to cast from DbSet to ObjectSet.

With this pattern in place I have no need for DbContext. Without generics I am forced to hand code all CRUD operations. Did I miss something? If not, is it possible to tell EF5 to generate code with ObjectContext instead?

like image 706
P.Brian.Mackey Avatar asked Aug 09 '13 16:08

P.Brian.Mackey


1 Answers

have a look at this tip that I posted a while ago

Anyway the trick is by using context.Set<>

public interface IEntity
        {
            int Id { get; set; } 
        } 

public class Repository<TEntity> : IRepository<TEntity> where TEntity : class, IEntity
    {
        private IDbContext _context;
        public Repository(IDbContext context)
        {
            _context = context;
        }
          private IDbSet<TEntity> DbSet
         {
            get
            {
                return _context.Set<TEntity>();
            }
         }
          public IQueryable<TEntity> GetAll() 
          {
             return DbSet.AsQueryable(); 
          }
        public void Delete(TEntity entity)
        {
             DbSet.Remove(entity);
        }
.....
like image 97
Massimiliano Peluso Avatar answered Oct 17 '22 05:10

Massimiliano Peluso