TGViewer
.NET Разработчик .NET Разработчик @netdeveloperdiary · 6.75K subscribers
Post #1430 1.92K
День 1161. #ЗаметкиНаПолях
Мягкое удаление в Entity Framework
При использовании мягкого удаления возникает проблема, что во всех запросах приходится отфильтровывать удалённые объекты:
dbSet.Where(x => x.Deleted == null);

И об этом нужно постоянно помнить.

Есть отличный способ решить эту проблему с помощью так называемых «глобальных фильтров запросов». В документации даже есть пример: https://docs.microsoft.com/en-us/ef/core/querying/filters.

Проблема в том, что в примере показано, как это сделать для отдельного объекта. Если в вашей базе данных много таблиц вам придется каждый раз не забывать добавлять конфигурацию. Придётся сделать кое-что посложнее в методе OnModelCreating контекста:
protected override void
OnModelCreating(ModelBuilder builder)
{
// остальные настройки

var entities = builder.Model
.GetEntityTypes()
.Where(e => e.ClrType.BaseType == typeof(Auditable))
.Select(e => e.ClrType);

Expression<Func<Auditable, bool>>
expression = del => del.Deleted == null;

foreach (var e in entities)
{
var p = Expression.Parameter(e);
var body =
ReplacingExpressionVisitor
.Replace(expression.Parameters.Single(),
p, expression.Body);

builder.Entity(entity)
.HasQueryFilter(
Expression.Lambda(body, p));
}

base.OnModelCreating(builder);
}
}

Сначала мы выбираем все сущности, которые наследуют от Auditable (см. предыдущий пост). Затем создаём выражение expression для фильтрации. Далее перебираем все выбранные сущности и создаём для каждого типа своё выражение путём замены параметра выражения expression на тип конкретной сущности. И наконец с помощью метода HasQueryFilter() добавляем глобальный фильтр.

Теперь все запросы в нашем приложении будут иметь фильтр и не включать мягко удалённые объекты. Если же для каких-то запросов (например, в блоке администрирования) всё-таки нужно получить все объекты, можно использовать метод IgnoreQueryFilters() в запросе.

Источник: https://dotnetcoretutorials.com/2022/03/17/using-ef-core-global-query-filters-to-ignore-soft-deleted-entities/
  • 👍 20
More from @netdeveloperdiary
  1. Sep 25, 2026День 2795. #ЗаметкиНаПолях #AI Рабочий процесс с Copilot для .NET. Начало Проблема с позиц…
  2. Sep 24, 2026День 2794. #Оффтоп #Здоровье Сегодня будет необычный пост. Завтра в Москве стартует конфер…
  3. Sep 23, 2026День 2793. #ЗаметкиНаПолях #SQL 10 Редких Возможностей SQL, Которые Стоит Знать Каждому. Ч…
  4. Sep 22, 2026День 2792. #ЗаметкиНаПолях #SQL 10 Редких Возможностей SQL, Которые Стоит Знать Каждому. Ч…
  5. Sep 21, 2026🔍Тестовое собеседование с Senior C# разработчиком уже завтра 22 сентября(уже завтра!) в 1…
  6. Sep 21, 2026День 2791. #ЗаметкиНаПолях #SQL 10 Редких Возможностей SQL, Которые Стоит Знать Каждому. Ч…
Threads Profile ViewerView any public Threads profile without an account.Open ThreadLook →Writing with AI? Make it sound human.Metric37 rewrites AI drafts so they read naturally. Free AI detector, 1,500 words free.Try Metric37 →