web-dev-qa-db-fra.com

Pourquoi DbContext n'implémente pas l'interface IDbContext?

Pourquoi n'y a-t-il pas d'interface IDbContext dans Entity Framework? Ne serait-il pas plus facile de tester des choses s'il y avait une interface existante avec des méthodes comme SaveChanges (), etc. à partir desquelles vous pourriez dériver votre interface de contexte de base de données personnalisée?

public interface ICustomDbContext : IDbContext
{
    // add entity set properties to existing set of methods in IDbContext
    IDbSet<SomeEntity> SomeEntities { get; }
}
52
Grief Coder

Je vois ceci IDbContext:

Voir ce lien Et puis vous créez une nouvelle classe partielle pour votre contexte d'entités avec cette interface.

public partial class YourModelEntities : DbContext, IDbContext 

EDITÉ: J'ai édité ce post, This Works for me. Mon contexte

namespace dao
{
    public interface ContextI : IDisposable
    {
        DbSet<TEntity> Set<TEntity>() where TEntity : class;
        DbSet Set(Type entityType);
        int SaveChanges();
        IEnumerable<DbEntityValidationResult> GetValidationErrors();
        DbEntityEntry<TEntity> Entry<TEntity>(TEntity entity) where TEntity:class;
        DbEntityEntry Entry(object entity);
        string ConnectionString { get; set; }
        bool AutoDetectChangedEnabled { get; set; }
        void ExecuteSqlCommand(string p, params object[] o);
        void ExecuteSqlCommand(string p);
    }
}

YourModelEntities est votre classe partielle générée automatiquement, et votre besoin de créer une nouvelle classe partielle avec le même nom, puis ajoutez votre nouvelle interface de contexte, car cet exemple est ContextI

REMARQUE: l'interface n'a pas implémenté toutes les méthodes, car les méthodes sont implémentées dans votre code de génération automatique.

namespace dao
{
    public partial class YourModelEntities :DbContext, ContextI
    {
        public string ConnectionString
        {
            get
            {
                return this.Database.Connection.ConnectionString;
            }
            set
            {
                this.Database.Connection.ConnectionString = value;
            }
        }

        bool AutoDetectChangedEnabled
        {
            get
            {
                return true;
            }
            set
            {
                throw new NotImplementedException();
            }
        }

        public void ExecuteSqlCommand(string p,params object[] os)
        {
            this.Database.ExecuteSqlCommand(p, os);
        }

        public void ExecuteSqlCommand(string p)
        {
            this.Database.ExecuteSqlCommand(p);
        }

        bool ContextI.AutoDetectChangedEnabled
        {
            get
            {
                return this.Configuration.AutoDetectChangesEnabled;
            }
            set
            {
                this.Configuration.AutoDetectChangesEnabled = value;
            }
        }

    }
}
14
user1626116

J'y pensais aussi, je suppose que vous allez l'utiliser pour moqueurDbContext. Je ne trouve aucune raison à cela, sauf que vous devrez implémenter votre propre DbSet manuellement dans votre anyway pour votre classe fictive (il faudra donc réécrire votre propre interface de toute façon).

0
Mohammed Noureldin

Créez simplement un faux DbContext étendant votre DbContext de production en remplaçant les méthodes qui compliquent les tests. De cette façon, toutes les modifications apportées au DbContext de production sont automatiquement reflétées dans les tests, à l'exception des méthodes remplacées. Pour toutes les autres classes qui traitent de la persistance et prennent le DbContext, il suffit de les étendre en passant également le faux DbContext étendu.

namespace Test.Mocks
{  
    public sealed class MockDatabaseContext : MainProject.Persistence.Database.DatabaseContext
    {
        public MockDatabaseContext(ConfigurationWrapper config) : base(config)
        {

        }      
        protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
        {

            var dbPath = "test.db";
            optionsBuilder.UseSqlite($"Filename={dbPath}");


        }
    }
}

namespace Test.Mocks
{

    public class MockInventoryFacade : InventoryFacade
    {        
        public MockInventoryFacade(MockDatabaseContext databaseContext) : base(databaseContext)
        {

        }    
    }
}
0
Sean Anderson