---
metadata:
  - name: generator
    content: Diplodoc Platform v5.50.6
alternate:
  - https://ytsaurus.tech/docs/en/yql/builtins/codegen.md
  - https://ytsaurus.tech/docs/ru/yql/builtins/codegen.md
---
> **Documentation Index:** Fetch the complete configuration index at https://ytsaurus.tech/docs/ru/llms.txt


# Функции для работы с генерацией кода

Во время выполнения вычислений можно сгенерировать код, состоящий из узлов S-expressions. Для этого используется механизм представления кода, упакованного в [ресурс](https://ytsaurus.tech/docs/ru/yql/types/special.md). После конструирования кода можно подставить его в основную программу с помощью функции [EvaluateCode](#evaluatecode). Для отладки сконвертировать код в строку можно с помощью функции [FormatCode](#formatcode).

Возможные типы узлов в S-expressions, которые можно использовать для генерации кода:

* Атом &mdash; нетипизированная строка из нуля и более символов.
* Список &mdash; последовательность из нуля и более узлов. Соответствует типу `кортеж` в SQL.
* Вызов встроенной функции &mdash; состоит из имени, выраженного атомом, и последовательности из нуля и более узлов, которые являются аргументами этой функции.
* Объявление лямбда функции &mdash; состоит из объявления имен аргументов и узла, который является корнем тела этой лямбда функции.
* Аргумент лямбды функции &mdash; узел, который может использоваться только внутри тела лямбда-функции.
* Мир &mdash; специальный узел, маркирующий операции ввода/вывода.

Узлы S-expressions образуют ориентированный граф. При этом атомы &mdash; всегда листовые узлы, так как не могут содержать дочерних узлов.

В текстовой записи S-expressions записываются следующим образом:

* Атом &mdash; `'"foo"`. Символ апострофа (') является признаком цитирования последующей строки, обычно заключенной в кавычки.
* Список &mdash; `'("foo" "bar")`. Символ апострофа (') является признаком того, что в скобках не будет вызова функции.
* Вызов встроенной функции &mdash; `(foo "bar")`. Первый элемент внутри скобок &mdash; обязательное имя функции, а далее указываются ее аргументы.
* Объявление лямбда функции &mdash; `(lambda '(x y) (+ x y))`. После ключевого слова `lambda` стоит список из имен аргументов, за которым следует тело лямбда функции.
* Аргумент лямбда функции &mdash; `x`. В отличие от атома, строка без символа апострофа (') является ссылкой на имя в текущей области видимости. При объявлении лямбда функции в область видимости тела добавляются имена аргументов, причем при необходимости скрывается имя из объемлющей области видимости.
* Мир &mdash; `world`.

## FormatCode

Сериализация кода в виде S-expressions. Код не должен содержать свободных аргументов функций, т.е. для сериализации кода лямбда функции нужно передавать ее целиком, а не выражения, потенциально содержащие аргументы лямбда функции.

#### Примеры

```yql
SELECT FormatCode(AtomCode("foo"));
-- (
-- (return '"foo")
-- )
```

## WorldCode

Построить узел кода с типом `мир`.

#### Примеры

```yql
SELECT FormatCode(WorldCode());
-- (
-- (return world)
-- )
```

## AtomCode

Построить узел кода с типом `атом` из строки, переданной в аргумент.

#### Примеры

```yql
SELECT FormatCode(AtomCode("foo"));
-- (
-- (return '"foo")
-- )
```

## ListCode

Построить узел кода с типом `список` из набора узлов или списков узлов кода, переданных в аргументы. При этом списки из аргументов встраиваются как отдельно перечисленные узлы кода.

#### Примеры

```yql
SELECT FormatCode(ListCode(
    AtomCode("foo"),
    AtomCode("bar")));
-- (
-- (return '('"foo" '"bar"))
-- );

SELECT FormatCode(ListCode(AsList(
    AtomCode("foo"),
    AtomCode("bar"))));
-- (
-- (return '('"foo" '"bar"))
-- )
```

## FuncCode

Построить узел кода с типом `вызов встроенной функции` из строки с именем функции и набора узлов или списков узлов кода, переданных в аргументы. При этом списки из аргументов встраиваются как отдельно перечисленные узлы кода.

#### Примеры

```yql
SELECT FormatCode(FuncCode(
    "Baz",
    AtomCode("foo"),
    AtomCode("bar")));
-- (
-- (return (Baz '"foo" '"bar"))
-- )

SELECT FormatCode(FuncCode(
    "Baz",
    AsList(
        AtomCode("foo"),
        AtomCode("bar"))));
-- (
-- (return (Baz '"foo" '"bar"))
-- )
```

## LambdaCode

Построить узел кода с типом `объявление лямбда функции` можно из:

* [Лямбда функции](https://ytsaurus.tech/docs/ru/yql/syntax/expressions.md#lambda), если заранее известно количество аргументов. В этом случае в качестве аргументов этой лямбда функции будут переданы узлы типа `аргумент`.
* Количества аргументов и [лямбда функции](https://ytsaurus.tech/docs/ru/yql/syntax/expressions.md#lambda) с одним аргументом. В этом случае в качестве аргумента этой лямбды функции будет передан список узлов типа `аргумент`.

#### Примеры

```yql
SELECT FormatCode(LambdaCode(($x, $y) -> {
    RETURN FuncCode("+", $x, $y);
}));
-- (
-- (return (lambda '($1 $2) (+ $1 $2)))
-- )

SELECT FormatCode(LambdaCode(2, ($args) -> {
    RETURN FuncCode("*", Unwrap($args[0]), Unwrap($args[1]));
}));
-- (
-- (return (lambda '($1 $2) (* $1 $2)))
-- )
```

## EvaluateCode

Подстановка в основную программу узла кода, переданного в аргумент.

#### Примеры

```yql
SELECT EvaluateCode(FuncCode("Int32", AtomCode("1"))); -- 1

$lambda = EvaluateCode(LambdaCode(($x, $y) -> {
    RETURN FuncCode("+", $x, $y);
}));
SELECT $lambda(1, 2); -- 3
```

## ReprCode

Подстановка в основную программу узла кода, который является представлением результата вычисления выражения, переданного в аргумент.

#### Примеры

```yql
$add3 = EvaluateCode(LambdaCode(($x) -> {
    RETURN FuncCode("+", $x, ReprCode(1 + 2));
}));
SELECT $add3(1); -- 4
```

## QuoteCode

Подстановка в основную программу узла кода, который является представлением выражения или [лямбда функции](https://ytsaurus.tech/docs/ru/yql/syntax/expressions.md#lambda), переданной в аргумент. Если во время подстановки были найдены свободные аргументы лямбда функций, то они вычисляются и подставляются в код как в функции [ReprCode](#reprcode).

#### Примеры

```yql
$lambda = ($x, $y) -> { RETURN $x + $y };
$makeClosure = ($y) -> {
    RETURN EvaluateCode(LambdaCode(($x) -> {
        RETURN FuncCode("Apply", QuoteCode($lambda), $x, ReprCode($y))
    }))
};

$closure = $makeClosure(2);
SELECT $closure(1); -- 3
```

## PositionOf {#positionof}

#### Сигнатура

```yql
PositionOf(x)->Struct<File:String, Row:Uint32, Column:Uint32>
```

Функция доступна начиная с версии [2026.01](https://ytsaurus.tech/docs/ru/yql/changelog/2026.01.md).
Возвращает позицию узла в исходном тексте. Для именованных выражений возвращает позицию исходного узла.

#### Пример

```yql
SELECT PositionOf(1); -- ("File": "<main>", "Row": 1, "Column": 19)
```

## WithIssue {#with_issue}

#### Сигнатура

```yql
WithIssue(x, File:String, Row: Uint32, Column: Uint32, Message: String)->TypeOf(x)
```

Функция доступна начиная с версии [2026.01](https://ytsaurus.tech/docs/ru/yql/changelog/2026.01.md).
Добавляет в стек валидации пользовательский фрейм с заданной позицией и сообщением. Не имеет эффекта, если запрос прошел валидацию успешно.
Типичное использование - привязка к файлу с DSL.

#### Пример

```yql
-- декорирование выражения
SELECT WithIssue(
    1 + "foo", -- для получения ошибки
    "my_file",
    100,
    200,
    "my_message"
);

-- декорирование подзапроса
DEFINE SUBQUERY $sub() AS
    SELECT 1 + "foo"; -- для получения ошибки
END DEFINE;

$sub = ($world)->{
    return WithIssue(
        $sub($world),
        "my_file",
        100,
        200,
        "my_message"
    );
};

PROCESS $sub();
```
