Использование SQL-функций для фильтрации позволяет обеспечить проверку более сложных условий, нежели просто сравнение полей с помощью стандартных операций.
Например, можно проверить существование связанной записи в другой таблице, либо собрать какое то комплексное значение с помощью функции и в фильтре проверить его соответствие ожидаемому.
К примеру, предположим у нас есть сущность Организация, а также связанная с ним сущность Роль организации.
Перечисление Роль в свою очередь имеет следующие значения:
/// <summary>
/// Роли организаций
/// </summary>
public enum ContragentRoleEnum
{
/// <summary>
/// Прочие
/// </summary>
Other = 1,
/// <summary>
/// Эксплуатация
/// </summary>
Exploit = 2,
/// <summary>
/// Экспертиза
/// </summary>
Expert = 3,
/// <summary>
/// Владение
/// </summary>
Ownership = 4,
/// <summary>
/// Аренда
/// </summary>
Rent = 5,
/// <summary>
/// СРО
/// </summary>
SRO = 6,
...
}
Задача - в форме организовать выбор Организаций, которые имеют Роль = СРО
Для решения этой задачи есть два пути
-
Кастомный фильтр в коде на C# (не тема данной статьи)
-
Фильтр по SQL-функции (а вот это попробуем)
Создадим функцию, которая проверяет наличие соответствующей Роли у переданной Организации:
После чего зарегистрируем эту функцию в качестве расширения сущности Организация и настроим фильтр
После построения приложения, на выбор будут предагаться записи организаций, которые имеют роль СРО, казалось бы задача решена.
Запрос и его план выглядят примерно вот так:
Как мы видим - созданная нами функция будет вызываться для каждой записи в выборке, что замедляет выполнение запроса.
Начиная с версии 5.4.7230, появилась возможность оптимизации подобных запросов. Для этого нужно в настройках SQL-функции отметить чекбокс “Встраивать в фильтры по возможности”:
После этого, в целевом решении тело данной функции будет встроено в запрос. Обновленный запрос будет выглядеть примерно вот так:
а его план выполнения будет более эффективен:
Таким образом, в данном случае, мы получили ускорение выполнения запроса примерно в 45 раз.
Данный вид оптимизации доступен только для функций написанных на языке sql, и оперирующих простыми типами данных.