Мне нужно предоставить доступ к контексту данных Entity Framework сторонним плагинам. Цель состоит в том, чтобы позволить этим плагинам получать только данные и не позволять им выполнять вставку, обновление или удаление или любые другие команды модификации базы данных. Следовательно, как я могу сделать контекст данных или сущность только для чтения.
112
DbContext
, дайте имIQueryable
несколько.Ответы:
Помимо подключения к пользователю, имеющему доступ только для чтения, есть еще несколько вещей, которые вы можете сделать со своим DbContext.
источник
AsNoTracking()
делает невозможным использование отложенной загрузки.public override Task<int> SaveChangesAsync()
.(context as IObjectContextAdapter).ObjectContext.SaveChanges()
все равно будет работать. Лучшим выбором является использованиеDbContext(string nameOrConnectionString);
конструктора со строкой подключения для чтения / записи для создания базы данных и строкой подключения только для чтения впоследствии.В отличие от принятого ответа, я считаю, что было бы лучше отдать предпочтение композиции, а не наследованию . Тогда не было бы необходимости хранить такие методы, как SaveChanges, для создания исключения. Более того, зачем вообще нужны такие методы? Вы должны спроектировать класс таким образом, чтобы его потребителя не обманули, когда он посмотрит на его список методов. Открытый интерфейс должен соответствовать фактическим намерениям и цели класса, тогда как в принятом ответе наличие SaveChanges не означает, что Context доступен только для чтения.
В тех местах, где мне нужен контекст только для чтения, например на стороне чтения шаблона CQRS , я использую следующую реализацию. Он не предоставляет своим потребителям ничего, кроме возможностей запросов.
Используя ReadOnlyDataContext, вы можете получить доступ только к возможностям запросов DbContext. Допустим, у вас есть объект с именем Order, тогда вы должны использовать экземпляр ReadOnlyDataContext, как показано ниже.
источник
IDisposable
public IQueryable<TEntity> Get<TEntity>() where TEntity : class { return _dbContext.Query<TEntity>().AsNoTracking(); }