Параметризованные запросы и повторная компиляция
Компиляция запроса требует времени и ресурсов, поэтому в YDB предусмотрен кэш компиляции. Результат компиляции сохраняется в кэше на узле кластера и переиспользуется только при точном совпадении текста запроса. Поэтому, если в коде приложения значения попадают в YQL через конкатенацию или форматирование строк, при каждом новом наборе данных сервер получает другой текст и компилирует его заново — хотя структура SQL может оставаться той же.
Последствия:
- увеличивается задержка на этапе компиляции;
- растёт нагрузка на CPU узлов;
- при большом числе уникальных текстов ухудшается переиспользование ограниченного кэша на узле.
Избежать лишней компиляции помогает параметризованный запрос: текст YQL фиксирован, а входные значения передаются отдельно через именованные параметры (например, $userId). Ниже оба подхода сравниваются на одном примере.
Подстановка значений в текст запроса
Приложение подставляет значения прямо в текст запроса:
SELECT id, name FROM users WHERE id = 123 AND status = "active";
SELECT id, name FROM users WHERE id = 456 AND status = "inactive";
Запросы отличаются только значениями, но тексты разные — для сервера это два разных запроса, и каждый компилируется отдельно.
Передача значений параметрами
Приложение передаёт значения отдельно от текста, текст запроса не меняется:
DECLARE $userId AS Uint64;
DECLARE $status AS Utf8;
SELECT id, name FROM users WHERE id = $userId AND status = $status;
Сервер обрабатывает вызовы такого запроса по-разному:
- Первый вызов — сервер компилирует запрос и сохраняет результат в кэше на узле.
- Следующие вызовы — если текст уже есть в кэше, используется готовый результат: меняются только значения
$userIdи$status, повторная компиляция не требуется.
Параметрами передаются только значения: имя таблицы или порядок сортировки задать параметром нельзя, и при их изменении текст запроса становится другим.
Содержимое кэша компиляции смотрите в разделе Кэш компиляции запросов, а время компиляции при выполнении запросов — в топах запросов (поле CompileDuration).
Размер и настройки кэша, флаг KeepInCache, синтаксис DECLARE и передача параметров из кода описаны в разделе Параметризованные запросы справки YDB SDK.