Сверка выполнена 2026-09-18 по версии 0.8.0. Перечень возможностей языка
запросов взят из раздела «Язык запросов» Синтакс-помощника платформы
8.3.27.2342. Статус — из кода open-sdbl (src/lexer.rs,
src/query/core/parser.rs, src/query/core/codegen/) и спецификаций
openspec/specs/.
Обозначения: ✅ поддерживается · 🟡 частично (см. примечание) · ❌ не
поддерживается. В графе «Примечание / реакция» — диагностика, которую
выдаёт компилятор (QueryDiagnosticKind), если конструкция встречается в
запросе.
Страницы Синтакс-помощника, по которым проверялись конструкции, названы во вводных абзацах разделов; открыть страницу можно поиском по её названию.
Обзор проекта, примеры запросов и описание API — в README.
Корпус реальных запросов демо-конфигурации и результат компилятора на них
лежит в tests/fixtures/demo (описание — в README рядом): 382 запроса, из
них 381 фикстура метаданных способна разрешить, компилируется 377. Это
измерение, а не оценка: каждая строка таблицы ниже проверяется на пробной
базе, а корпус показывает, на что запросы натыкаются чаще всего.
Каждый скомпилированный запрос корпуса выполняется на настоящей базе
PostgreSQL (EXPLAIN): сервер принимает их все. Это отдельная проверка от
голденов — те подтверждают, что SQL такой, каким его задумал компилятор, а
выполнение подтверждает, что сервер его принимает.
Порядок предложений по странице «Секция ВЫБРАТЬ (Описание запроса)»:
ВЫБРАТЬ [РАЗРЕШЕННЫЕ] [РАЗЛИЧНЫЕ] [ПЕРВЫЕ n] <поля> [ПОМЕСТИТЬ …] [ИЗ …] [ИНДЕКСИРОВАТЬ ПО …] [ГДЕ …] [СГРУППИРОВАТЬ ПО …] [ИМЕЮЩИЕ …] [ДЛЯ ИЗМЕНЕНИЯ …], затем ОБЪЕДИНИТЬ, УПОРЯДОЧИТЬ ПО,
АВТОУПОРЯДОЧИВАНИЕ, ИТОГИ. Три модификатора после ВЫБРАТЬ идут в
любом порядке — замерено на 8.3.27, все шесть перестановок
РАЗРЕШЕННЫЕ/РАЗЛИЧНЫЕ/ПЕРВЫЕ n дают один результат; повторённый
модификатор — диагностика.
| Статус | Конструкция (RU / EN) | Примечание / реакция |
|---|---|---|
| ✅ | ВЫБРАТЬ / SELECT |
|
| ✅ | РАЗЛИЧНЫЕ / DISTINCT |
оператор оставляет только проецируемые значения, поэтому УПОРЯДОЧИТЬ ПО адресует колонки выборки по позиции, как у группировки и объединения; поле, которого нет в выборке, — диагностика (иначе SQL отказывается: строковая колонка проецируется с приведением к тексту, а упорядочивание шло по самой колонке) |
| ✅ | УПОРЯДОЧИТЬ ПО по составному полю (Регистратор, субконто, момент времени) |
по пути и по псевдониму: сортировка раскладывается по всем колонкам поля в их порядке — тип, затем значение, — с направлением терма; при РАЗЛИЧНЫЕ, объединении и группировке ссылка адресуется позицией той колонки, которой её выводит проекция |
| ✅ | ПЕРВЫЕ n / TOP n |
TOP (n) на MSSQL, LIMIT n на PostgreSQL; n — целое ≥ 0, ПЕРВЫЕ 0 отвечает колонками без строк (так конфигурации заводят пустую временную таблицу) |
| 🟡 | РАЗРЕШЕННЫЕ / ALLOWED |
только после первого ВЫБРАТЬ оператора, действует на его вложенные запросы, В (…), объединение и виртуальные таблицы; операторы пакета независимы; фильтры не читаются из ролей, а запрашиваются у приложения (Prepared::restriction_request → CompileOptions::restrictions) как условия на SDBL (в том числе в полной форме ТекущаяТаблица [КАК Т] [ИЗ <таблица> [КАК Т]] [<соединения>] ГДЕ …, где ТекущаяТаблица и псевдоним квалифицируют поля таблицы и во вложенных запросах условия, описание источника называет саму ограничиваемую таблицу, а ЛЕВОЕ/ВНУТРЕННЕЕ СОЕДИНЕНИЕ … ПО … компилируются в коррелированный предикат, не размножающий строки; другой источник, ПРАВОЕ/ПОЛНОЕ соединение и соединение не с таблицей метаданных — диагностика) и оборачивают таблицу в производную (SELECT … FROM t AS "__restricted" WHERE …), у виртуальных таблиц добавляются к их условию (только прямые поля); разыменованные таблицы не фильтруются; в консоли — \restrict; подробнее — README «Ограничения доступа» |
| ✅ | Принудительный режим ограничений (RestrictionMode::Restricted) |
выбирается при prepare_with_options, хранится в Prepared и не понижается при компиляции; фильтрует каждый оператор пакета, вложенные запросы, ветки объединения, соединения, виртуальные и временные таблицы независимо от слова РАЗРЕШЕННЫЕ; в запрос ограничений добавляются неявные чтения — цель разыменования, каждый кандидат составной ссылки, цель представления — и решение по ним действительно оборачивает соединение; каждой цели нужен явный AccessDecision (можно всё / по условию / нельзя), цель без решения и ошибка в условии — Restriction, запрет — ложный предикат; обход иерархии, КритерийОтбора, Константы, проекция вложенной табличной части, отложенное представление ссылки и временная таблица из нерестриктивного пакета отклоняются UnsupportedFeature до генерации SQL |
| ✅ | Псевдонимы [КАК] / [AS] |
безымянная проекция поля получает метку по написанию в тексте (Т.Ссылка → «Ссылка», Т.Ref → «Ref», Д.Регистратор → «Регистратор»), а разыменование — по сегментам пути слитно (Д.Организация.Наименование → «ОрганизацияНаименование»), как на платформе, и под этим именем колонку читают вложенный запрос и временная таблица; после КАК псевдонимом может быть и ключевое слово, не открывающее следующую секцию (КАК Конец, КАК Порядок); для полей и источников; КАК необязательно — замерено на 8.3.27, короткая форма принимается у поля, агрегата, ВЫБОР, константы и разыменования, у объекта, соединения, вложенного запроса, виртуальной и временной таблицы, и на неё ссылаются УПОРЯДОЧИТЬ ПО, СГРУППИРОВАТЬ ПО и ИТОГИ; слово ровно одно (Имя Второе — синтаксическая ошибка), контекстное ключевое слово псевдонимом быть может (ВЫБРАТЬ 1 Сумма), а слово, открывающее следующую секцию (ИТОГИ, ИНДЕКСИРОВАТЬ), — нет |
| ✅ | Полное имя источника как квалификатор (Справочник.Товары.Наименование) |
работает, только если у источника нет псевдонима — замерено на 8.3.27; с псевдонимом платформа отвечает «Поле не найдено», и компилятор тоже; путь продолжается разыменованием (Справочник.Товары.Поставщик.Наименование) |
| ✅ | Разыменование через псевдоним выборки | платформа его не принимает («Поле не найдено "К.Наименование"» для ВЫБРАТЬ Т.Клиент КАК К, К.Наименование, замерено на 8.3.27) — здесь оно тоже диагностика |
| 🟡 | *, Псевдоним.* |
* — только без других полей, без JOIN и при одном источнике в ИЗ (несколько через запятую — диагностика, платформа допускает); Псевдоним.* (по псевдониму или, без него, по имени объекта) разворачивается во все поля источника в порядке метаданных на своём месте в списке — и один, и рядом с другими полями, и в соединениях, повторные метки делаются уникальными; Имя.* не-источника называет табличную часть |
| ✅ | Запрос без ИЗ |
в 1С ИЗ можно опустить при полностью квалифицированных полях; open-sdbl без ИЗ компилирует только выражения без источника (ВЫБРАТЬ 1), в том числе с ГДЕ: условие превращается в WHERE без FROM, как отвечает платформа |
| 🟡 | Вложенные таблицы в выборке Состав, Состав.(Поле, …), Состав.* |
компилируются во второй оператор, связанный с главным по ссылке владельца: CompiledQuery.nested несёт его SQL, колонки и структурную связь (индексы колонок-ключей с обеих сторон), а главный оператор получает служебную колонку ключа (service_columns); платформа делает то же самое — замерено на 8.3.27: она кладёт ключи во временную таблицу pg_temp.ttN и читает секцию соединением с ней; Состав и Состав.* дают ссылку, номер строки и реквизиты, Состав.(…) — ровно перечисленные колонки (псевдонимы внутри списка принимаются и отбрасываются); вместе с ИТОГИ, в объединении и во вложенном запросе — диагностика; ПУСТАЯТАБЛИЦА.(…) / EMPTYTABLE не поддержана |
| ✅ | ПОМЕСТИТЬ <ВТ> / INTO, УНИЧТОЖИТЬ <ВТ> / DROP |
базы-копии только на чтение, поэтому таблица эмулируется CTE vt1, vt2, …: ПОМЕСТИТЬ определяет CTE и возвращает строку Количество, УНИЧТОЖИТЬ SQL не порождает и скрывает имя (можно определить заново); определения хранит TempTablesManager, в WITH попадают только достижимые; правила определения — как у вложенного запроса (*, отложенные представления и УПОРЯДОЧИТЬ ПО без ПЕРВЫЕ запрещены); неизвестное или дублирующее имя — TemporaryTable |
| ✅ | ДОБАВИТЬ <ВТ> / ADD (добавление строк в существующую ВТ) |
новая CTE SELECT … FROM vtK UNION ALL <оператор>, имя переключается на неё; структура сверяется строго (число колонок, виды, цели и ширина ссылок), расширения типа нет; метки колонок остаются от первого определения; поле перед ДОБАВИТЬ не обязано иметь псевдоним, в отличие от 1С |
| 🟡 | ИНДЕКСИРОВАТЬ ПО … / INDEX BY, ИНДЕКСИРОВАТЬ ПО НАБОРАМ ((…),(…)) / INDEX BY SETS, модификатор УНИКАЛЬНО / UNIQUE |
разбирается и проверяется (поля обязаны быть в списке выборки, иначе TemporaryTable; поле может быть уточнено псевдонимом источника — ИНДЕКСИРОВАТЬ ПО Т.Поле называет метку Поле, как принимает платформа), SQL не порождает: у CTE индексов нет |
| ✅ | ИЗ КритерийОтбора.<Имя>(<значение>) / FilterCriterion |
объединение UNION ALL по одному выбору на каждое поле состава критерия; единственное поле Ссылка несёт найденный объект как payload RTRef ‖ RRRef, поэтому разыменовывается, группируется и соединяется как ссылка производного источника; ссылочное значение сравнивается своим 16-байтовым идентификатором; критерий, состав которого не достаёт ни одного живого поля, — диагностика |
| ✅ | ИЗ ЖурналДокументов.<Имя> / DocumentJournal |
таблица журнала со стандартными полями Ссылка, Тип, Дата, Номер, ПометкаУдаления, Проведен и собственными графами по именам метаданных; Ссылка — ссылка зарегистрированного документа: одна колонка, если журнал регистрирует один вид документа, и пара RTRef ‖ RRRef, если несколько, поэтому разыменование и соединение работают как у любой ссылки; Тип — значение типа этой ссылки |
| 🟡 | <Источник>.<ТабличнаяЧасть>.<Поле> в условии |
компилируется в коррелированный EXISTS по таблице части: строка владельца отвечает один раз, сколько бы её строк ни подошло — замерено на 8.3.27 (документ с двумя подходящими строками пришёл один раз, КОЛИЧЕСТВО(*) = 4, а не 5); секция называется через владельца (Д.Товары.Количество), потому что голое <Состав>.<Поле> — это обращение к своим колонкам у запроса, читающего секцию источником; колонка секции, хранимая парой ссылки, сравнивается по payload RTRef ‖ RRRef, другая сторона расширяется так же, как в обычном сравнении составной ссылки; прочие составные колонки секции — диагностика; вне сравнения путь не поддержан |
| ✅ | ИЗ <Вид>.<Объект>.<ТабличнаяЧасть> |
табличная часть читается как источник у всех видов, которые её имеют: справочники, документы, планы видов характеристик, планы счетов, планы видов расчёта, бизнес-процессы, задачи и планы обмена; у прочих видов — диагностика |
| ✅ | ИЗ <ВТ> [КАК Псевдоним] (чтение временной таблицы) |
имя без точки читается как временная таблица, в том числе в соединениях, вложенных запросах и В (…); с псевдонимом источник адресуется только им, без псевдонима квалификатором служит имя таблицы (платформа голое имя объекта не принимает вовсе — это наше послабление); колонки приходят с видами из определения; разыменование — как у вложенного источника |
| ❌ | ИЗ &ВнешнийИсточник (ВТ из таблицы значений) |
внешние источники данных в компиляторе отсутствуют |
| ✅ | ИЗ / FROM: несколько источников через запятую |
каждый элемент списка — источник со своими соединениями; рендерится цепочкой CROSS JOIN в порядке записи; условие соединения видит только источники своего элемента, как в 1С (иначе UnknownField); разделители у таких источников ставятся как у базового; элемент со своими соединениями заключается в скобки и присоединяется целиком — платформа отвечает Товары, Смешанные ПОЛНОЕ СОЕДИНЕНИЕ Клиенты 26 строками, то есть 13 × (0 ⟗ 2), а не 2 (замерено); * при нескольких источниках — диагностика |
| ✅ | ИЗ (вложенный запрос) КАК Псевдоним, в том числе в соединениях |
псевдоним обязателен; колонки подзапроса становятся полями источника с их ColumnKind; внутри допустимы объединения, группировка, соединения, ПЕРВЫЕ, РАЗЛИЧНЫЕ, inline-представления, УПОРЯДОЧИТЬ ПО только когда у каждой ветки есть ПЕРВЫЕ (у объединения порядок ни на что не влияет и отбрасывается); запрещены * и отложенные представления; разыменование — только через колонку-ссылку с одной фиксированной целью; коррелированные ссылки на внешние источники — диагностика; глубина вложенности ≤ 16 |
| 🟡 | ИЗ &Таблица [КАК Т] и СОЕДИНЕНИЕ &Таблица (таблица значений как параметр) |
параметр ParameterValue::Table { columns, rows } с типизированными колонками ParameterColumn { name, kind } (строка, число, булево, дата, двоичные, ссылка на объект или на несколько, ЛюбаяСсылка — ссылка без целей); строки встраиваются в CTE оператора SELECT 1 AS "__row", CAST(значение AS тип) … UNION ALL SELECT 2, … (первая строка приводится к типу колонки, пустая таблица — SELECT … WHERE 1 = 0 из типизированных NULL), источник читает CTE по имени; значения проверяются по виду колонки, ссылка обязана указывать на одну из целей; ссылки на несколько объектов или ЛюбаяСсылка — payload RTRef ‖ RRRef; даты в домене хранения; в операторе с ПОМЕСТИТЬ CTE уезжает к определению таблицы; кривая таблица (разная длина строк, значение не того вида, повтор имени колонки, вид NULL/Неопределено/тип, список внутри) и скаляр вместо таблицы — диагностика Parameter; несвязанный проход подготовки видит колонки, названные в тексте; в консоли — литерал ТАБЛИЦА(Код КАК СТРОКА, Ссылка КАК Справочник.Номенклатура)((строка), …) |
| 🟡 | [ВНУТРЕННЕЕ] СОЕДИНЕНИЕ, ЛЕВОЕ/ПРАВОЕ/ПОЛНОЕ [ВНЕШНЕЕ] СОЕДИНЕНИЕ … ПО / [INNER] JOIN, LEFT/RIGHT/FULL [OUTER] JOIN … ON |
источник соединения может нести свои соединения до собственного ПО (условия закрываются в обратном порядке), такая группа компилируется в равносильную плоскую цепочку, внешнее соединение первым — замерено на платформе; группа, у которой внешнее соединение ЛЕВОЕ/ПРАВОЕ/ПОЛНОЕ, а вложенное не ЛЕВОЕ, — диагностика, потому что плоская цепочка отвечает иначе (замерено: 21 строка против 13); отличие: платформа не видит из вложенного условия внешние источники, мы их допускаем; цепочка любого числа соединений в порядке записи; ссылки разной ширины в равенстве приводятся к RTRef ‖ RRRef (фиксированная получает номер типа цели, составная конкатенируется, payload остаётся как есть), две составные сравниваются почленно; ПО внутреннего, левого и правого соединения — любое условие над присоединяемым и более ранними источниками (ИСТИНА, сравнение с параметром, неравенство, МЕЖДУ, разыменование, в том числе через ВЫРАЗИТЬ), как принимают платформа и серверы; ПО полного соединения содержит хотя бы одно равенство прямых полей или одношаговых разыменований присоединяемого и любого более раннего источника (иначе сервер не спланирует FULL JOIN), дополнительно — скалярные фильтры через И; при разыменовании в ПО соединения разыменования выводятся группой рядом со своим источником; ссылка на источник, присоединяемый позже, — диагностика; путь глубже одного шага в ПО — диагностика; ПОЛНОЕ компилируется в нативный FULL JOIN и ведёт себя как остальные соединения: допустимо в цепочке, под агрегатами и с группировкой, разыменование в его ПО выносится внутрь своей стороны; платформа вместо FULL JOIN шлёт разложение — UNION ALL внутреннего соединения и двух антисоединений через НЕ СУЩЕСТВУЕТ (замерено на 8.3.27), но на равенстве оба отвечают одинаково, что сверено пробами построчно; условие ПО остаётся цепочкой равенств через И, иначе сервер откажется планировать соединение |
| ✅ | ГДЕ / WHERE |
|
| ✅ | СГРУППИРОВАТЬ ПО / GROUP BY, ИМЕЮЩИЕ / HAVING |
ключи — путь поля (одно разыменование), псевдоним проекции или выражение, совпадающее с проекцией; проекция, которая не читает ни одного поля источника, — константа набора строк: её не требуется ни группировать, ни ставить рядом с агрегатом (как отвечает платформа); каждая неагрегатная проекция обязана быть ключом, разыменованием ключа (Сотрудник.Наименование при ключе Сотрудник — присоединённая колонка добавляется в GROUP BY) или выражением над ключами (-Сумма, ЕСТЬNULL(Ключ, &П) + 1); ссылочный ключ группируется по всем физическим членам; ИМЕЮЩИЕ — предикат с агрегатами; сортировка сгруппированной ветви — по ключам (и без их проекции), разыменованиям ключей, псевдонимам и выражениям с агрегатом (МАКСИМУМ(Период) УБЫВ); с ПОЛНОЕ СОЕДИНЕНИЕ группировка разрешена и отвечает как платформа |
| ❌ | СГРУППИРОВАТЬ [ВСЕ] ПО ГРУППИРУЮЩИМ НАБОРАМ ((…),(…)) / GROUP BY GROUPING SETS |
|
| ✅ | ОБЪЕДИНИТЬ [ВСЕ] / UNION [ALL] |
ветви должны совпадать по числу значений; значения разных типов образуют составное значение, как на платформе — замерено на 8.3.27: каждая ветвь пишет член своего типа, ноль остальных членов и тег своего типа, и все члены остаются NULL, пока значение ветви NULL; ветвь, которая уже выдаёт члены, сохраняет свой порядок, остальные подстраиваются под неё; ссылки разной ширины по-прежнему приводятся к RTRef ‖ RRRef; колонки, не являющиеся членами одного значения, — диагностика. Отличие: у объединения только скалярных ветвей порядок членов наш (значение первым, _TYPE последним, как у ВЫБОР), у платформы _TYPE первым — на результат это не влияет, обе стороны объединения согласованы между собой |
| 🟡 | УПОРЯДОЧИТЬ ПО … ВОЗР/УБЫВ / ORDER BY … ASC/DESC |
только в конце запроса; ключ — поле, псевдоним проекции или любое выражение (ВЫБОР, арифметика, ЕСТЬNULL, ТИПЗНАЧЕНИЯ), порядковые номера не поддержаны; при JOIN, группировке и ОБЪЕДИНИТЬ порядок задаётся по колонкам результата, поэтому ключ обязан быть полем проекции или псевдонимом, а выражение отклоняется; с ИТОГИ ключ может отсутствовать в проекции — он выводится скрытой колонкой __order_<n>; упорядочивание по типу идёт в порядке кодировки (Неопределено, примитивы, ссылки по номеру таблицы), как на платформе; у оператора с соединениями (без объединения, группировки и РАЗЛИЧНЫЕ) можно сортировать и по непроецируемому полю — оно сортируется своей колонкой, проецируемое — по позиции |
| ❌ | УПОРЯДОЧИТЬ ПО … [ВОЗР/УБЫВ] ИЕРАРХИЯ / HIERARCHY |
|
| 🟡 | АВТОУПОРЯДОЧИВАНИЕ / AUTOORDER |
принимается после УПОРЯДОЧИТЬ ПО (и без него) и ничего не добавляет: платформа досортировывает по представлениям ссылок, компилятор сортирует только по написанным ключам |
| 🟡 | ИТОГИ [поля] ПО [ОБЩИЕ] точки [[ТОЛЬКО] ИЕРАРХИЯ] [ПЕРИОДАМИ(…)] / TOTALS … BY [OVERALL] … [[ONLY] HIERARCHY] [PERIODS] |
результат — строки обхода Прямой: общий итог, затем итог каждой группы перед её строками, группы в порядке первого появления в упорядоченной выборке; итоговые поля — агрегаты по колонкам результата (агрегат пишется в свою колонку, выражение — в колонку из КАК), в прочих колонках NULL; контрольная точка — колонка результата (точка вне списка выборки — диагностика, платформа допускает); ПЕРИОДАМИ разбирается и проверяется, но строк не добавляет (платформа дополняет периоды только в обходе по группировкам); CompileOptions::totals_level добавляет колонку __level = Уровень(), консоль её включает; ИЕРАРХИЯ/ТОЛЬКО ИЕРАРХИЯ — одна контрольная точка (вторая — UnsupportedFeature) с одноцелевой ссылкой на иерархический справочник (иначе Syntax): строка итога по иерархии для каждой папки-предка через рекурсивные CTE по _ParentIDRRef (WITH RECURSIVE на PostgreSQL; на SQL Server действует MAXRECURSION 100), она суммирует строки самой папки и всех потомков; уровень папки — её глубина, итог группы на уровень ниже строки над ним (у папки-ключа — ниже её собственной строки иерархии), детальная запись ещё ниже, при ОБЩИЕ всё на единицу глубже; при ТОЛЬКО группировка по родителю значения; ПО X, X ИЕРАРХИЯ равносильно ПО X ИЕРАРХИЯ; родители ищутся по базовой таблице и таблицам расширений справочника; сверено с платформой на четырёх пробах построчно; отличие: папки-соседи идут в порядке первого появления строк под ними, тогда как платформа сортирует их по полям УПОРЯДОЧИТЬ ПО, вычисленным для самих папок; с ПОМЕСТИТЬ — Syntax, во вложенных запросах — UnsupportedFeature |
| ❌ | ДЛЯ ИЗМЕНЕНИЯ [OF таблицы] / FOR UPDATE [OF] |
компилятор только для чтения |
| ✅ | [НЕ] В (вложенный запрос) |
подзапрос с одной колонкой совместимого вида либо с колонками-членами одного составного значения: замерено на 8.3.27, платформа сравнивает члены рядом ((TYPE, S, RTRef, RRRef) IN (SELECT …)), раскладывая вторую сторону по тем же членам — свой член несёт значение, дискриминатор — тег, остальные — ноль своего типа, и все они остаются NULL, пока значение NULL; на SQL Server строкового сравнения нет, поэтому составная форма там отклоняется диагностикой; составное значение с внешней стороны отвечает своими членами, а если его членов не хватает — диагностика; строковый член сравнивается как текст с обеих сторон; колонки, не являющиеся членами одного значения, — диагностика, как раньше; источники внешнего оператора видны в подзапросе по своему псевдониму (коррелированный подзапрос), безымянное поле по-прежнему ищется только среди собственных источников, а производный источник ИЗ (…) внешние псевдонимы не видит — SQL вычисляет его до внешней строки; ссылки сравниваются на одной ширине (fixed сторона расширяется до RTRef ‖ RRRef) — и в кортеже (А, Б) В (…) тоже: элемент-ссылка нескольких типов сравнивается как payload, составное поле (субконто) — по своим членам с колонками Имя_TYPE/Имя подзапроса; подзапросы в списке выбора — ❌ (их нет и в 1С) |
| ✅ | (А, Б) [НЕ] В (вложенный запрос) |
кортеж полей против подзапроса с тем же числом колонок совместимых видов; рендерится как EXISTS по подзапросу с равенством на каждую колонку на обоих диалектах, в том числе в условии виртуальной таблицы; ссылка нескольких типов с любой стороны и кортеж вне такого условия — диагностика |
| 🟡 | Пакет запросов ; |
операторы пакета компилируются последовательно (не более 64) и собираются в один SQL-оператор: результат даёт последний, как Запрос.Выполнить(); промежуточные запросы без ПОМЕСТИТЬ только проверяются; массива результатов, как у ВыполнитьПакет(), нет; пакет из одного УНИЧТОЖИТЬ строк не возвращает |
| 🟡 | Разыменование Поле.Реквизит[.Реквизит…] |
сколько угодно шагов: каждый шаг присоединяет цель предыдущего, одинаковые шаги ветви делят одно соединение; допустимо в проекции, ГДЕ, СГРУППИРОВАТЬ ПО, УПОРЯДОЧИТЬ ПО, а в ПО соединения — только один шаг, в том числе у ПОЛНОЕ; имя таблицы можно опускать, если поле уникально среди источников; продолжать путь через составную ссылку нельзя — диагностика, платформа так умеет |
| ✅ | Поле-пара RTRef ‖ RRRef (Регистратор, Ссылка журнала, payload критерия) как значение |
такая пара — всегда ссылка, _TYPE у неё нет; агрегат над парой (МАКСИМУМ(Регистратор)) — тот же payload с тем же видом, ЕСТЬNULL над ним расширения не требует; замерено на 8.3.27 на регистре с двумя видами регистратора: платформа принимает её значением везде — в проекции, ВЫБОР, ЕСТЬNULL, сравнении (почленном), ЕСТЬ NULL (оба члена), ССЫЛКА (по _RTRef), группировке и упорядочивании (оба члена) и в агрегате (по склейке членов). Здесь пара в выражении рендерится своим payload RTRef ‖ RRRef с видом runtime-typed ссылки, ТИПЗНАЧЕНИЯ от неё — тег ссылки рядом с номером таблицы из _RTRef, агрегат берётся от payload |
| ✅ | Разыменование составного поля (ЛюбаяСсылка, Регистратор, payload подзапроса или ВТ) |
цели берутся из SchemaStorage, из описания типа в Config, из вида колонки подзапроса либо перебором ссылочных объектов; SchemaStorage не называет цели ссылки, допускающей несколько таблиц (["R",0,0,"",4] против ["R",0,0,"Reference53",3]), но их называет Config: у объекта третий идентификатор его класса — это ссылочный тип, которым его называют другие, а у реквизита есть описание {"Pattern", {"#", <ссылочный тип>}, …} (и то и другое замерено на 8.3.27 на пробной конфигурации); описание типа может называть целый вид, а не объект («любой справочник», «любой бизнес-процесс», «любая ссылка») — это десять платформенных констант, замеренных на 8.3.27, и такой тип раскрывается во все объекты своего вида; если же описание называет не хранимый объект (определяемый тип, характеристику), список остаётся пустым и работает перебор, и стандартные поля в нём распознаются по имени, так что Т.Регистратор.Дата и Т.Объект.Родитель разыменовываются; если присоединяемых целей больше 256 (столько таблиц принимает в одном операторе SQL Server), нужна ВЫРАЗИТЬ; предел считает цели, которые действительно дают соединение, а не кандидатов перебора: корпусный запрос перебирает больше 256 объектов и соединяет 94, давая 65 КБ SQL со 188 LEFT JOIN, который живой сервер планирует и выполняет; на каждую цель LEFT JOIN с охраной по типу, значение — ВЫБОР по _RTRef, для типов без реквизита NULL; цели, которые типизируют реквизит по-разному, дают одно составное значение: каждая пишет член своего типа, ноль остальных членов и тег своего типа, и все они остаются NULL, пока значение этой цели NULL (замерено на 8.3.27, форма та же, что у ВЫБОР разнотипных ветвей); ссылки расширяются до RTRef ‖ RRRef; путь продолжается за составной шаг — замерено на 8.3.27: остаток пути проходится внутри каждой цели (соединения после составного шага идут без охраны, потому что цель уже фиксирована), ветви выбираются тем же CASE по типу, а цель, в которой остаток пути не разрешается, в результат не попадает; составной шаг глубже вкладывает ещё один CASE; больше 256 целей и представление результата — диагностика; значение, разыменованное через многотипную ссылку (Регистратор.Организация), в выражении — его член-значение (CASE по целям), сравнение со ссылочной константой — через её payload RTRef ‖ RRRef |
| ✅ | .Представление / .Presentation |
через callback-план приложения (см. README «Callback ABI представлений») |
Грамматика логических выражений по страницам «Логические выражения в языке
запросов» и «Логические операторы»: сравнение > < = >= <= <>, [НЕ] В [ИЕРАРХИИ] (список | подзапрос), [НЕ] МЕЖДУ … И …, ЕСТЬ [НЕ] NULL, ССЫЛКА <Имя таблицы> (операнд — поле или ВЫРАЗИТЬ(поле КАК та же таблица)), [НЕ] ПОДОБНО … [СПЕЦСИМВОЛ …], связки И ИЛИ НЕ.
| Статус | Оператор | Примечание / реакция |
|---|---|---|
| ✅ | + - * / |
% — ❌ (в справке не описан) |
| ✅ | + как конкатенация строк |
замерено на 8.3.27: платформа склеивает строки и отказывает, если рядом со строкой стоит другой тип («Неверные параметры "+"»), — здесь так же; операнды приводятся к тексту, вид выражения — String |
| ✅ | = <> < > <= >= |
|
| 🟡 | Сравнение составного поля со значением (=, <>, В) |
предикат собирается по физическим членам, как это делает платформа: _TYPE сравнивается с тегом типа значения, а член этого типа — со значением; ссылка сравнивает ещё и _RTRef, а поле с единственным ссылочным типом хранит _RTRef не отдельной колонкой, и он синтезируется из _TYPE; значение типа, который поле хранить не может, даёт пустую выборку, а параметр без значения — сравнение с NULL; сравнение двух составных полей, >/< (платформа упорядочивает по тегу типа) и ЕСТЬNULL над составным полем не поддержаны — диагностика |
| ✅ | Логическое выражение как значение | сравнение, И/ИЛИ/НЕ, ЕСТЬ NULL, ПОДОБНО, МЕЖДУ, ССЫЛКА и В отвечают булевым значением в проекции, ветви ВЫБОР и упорядочивании; NULL в операнде даёт NULL — замерено на 8.3.27. На PostgreSQL это само предикатное выражение, на SQL Server булевых значений нет, поэтому значение рендерится трёхветочным CASE WHEN p THEN 0x01 WHEN NOT p THEN 0x00 END (сохраняет NULL), а предикатная позиция остаётся обычным предикатом |
| ✅ | И / ИЛИ / НЕ (AND / OR / NOT) |
приоритет замерен на платформе: НЕ слабее любого сравнения и сильнее И, поэтому НЕ Т.Цена = 10 отрицает сравнение, а НЕ А > 10 И Б < 30 отрицает только первое; НЕ покрывает также ПОДОБНО, В, В ИЕРАРХИИ, ССЫЛКА и ЕСТЬ NULL; унарные + и - по-прежнему относятся к своему операнду; отличие: НЕ х МЕЖДУ а И б платформа не принимает (нужно х НЕ МЕЖДУ а И б), мы разбираем как отрицание сравнения; на MSSQL булевы поля в предикатах приводятся к = 0x01 |
| ✅ | В (список) / IN (...) |
непустой список скалярных выражений, в том числе ЗНАЧЕНИЕ(...) |
| ✅ | НЕ В (список) / NOT IN |
|
| ✅ | [НЕ] В ИЕРАРХИИ (…) / IN HIERARCHY |
значение совпадает с элементом списка или лежит под ним по цепочке _ParentIDRRef; спуск — рекурсивная CTE на каждый предикат (WITH RECURSIVE на PostgreSQL, WITH на SQL Server), проверка через EXISTS, поэтому NULL в списке ничего не портит; пустая ссылка охватывает весь справочник, а справочник без колонки родителя вырождается в обычное вхождение — как на платформе; слева — поле с единственной ссылочной целью либо составная ссылка: у составной сравнивается идентификатор, а тип обязан совпасть с типом семян, потому что значение другого типа ни под каким семенем не лежит (замерено на 8.3.27); если тип семян неизвестен при компиляции — например, параметр связан NULL — спуск не строится и остаётся сравнение идентификаторов, которые уникальны; справа — вложенный запрос или константы (поле в списке — диагностика, CTE не видит внешнюю строку); в операторе с ПОМЕСТИТЬ/ДОБАВИТЬ рекурсивные CTE переезжают к определению таблицы под именами __hier_t<id>_<n> и объявляются перед её CTE в каждом читающем её операторе (WITH RECURSIVE на PostgreSQL) |
| ✅ | [НЕ] МЕЖДУ … И … / BETWEEN |
границы включаются, обратные границы дают пустую выборку, NULL не совпадает — как на платформе; значение и границы — любые скалярные выражения |
| ✅ | [НЕ] ПОДОБНО … [СПЕЦСИМВОЛ …] / [NOT] LIKE … [ESCAPE …] |
шаблон передаётся в LIKE без переписывания на обоих провайдерах (на PostgreSQL классы […] обеспечивает mchar); операнды — строки; принимается и как значение (проекция, ВЫБОР, упорядочивание), как на платформе |
| ✅ | ЕСТЬ NULL / ЕСТЬ НЕ NULL (IS [NOT] NULL) |
составное поле и универсальная ссылка проверяются по одному члену — _TYPE, иначе RRRef: он NULL ровно тогда, когда строки нет, поэтому у собственных строк таблицы ответ всегда ЛОЖЬ, а у непопавшей строки внешнего соединения — ИСТИНА, как на платформе |
| ✅ | ССЫЛКА Справочник.X / REFS |
операнд — прямое поле или одношаговое разыменование; составное поле сравнивает _RTRef с номером типа, payload вложенного запроса — первые четыре байта; поле с единственной целью даёт ИСТИНА и для пустой ссылки, как платформа; чужой тип и нессылочное поле — Syntax (в 1С «Несовместимые типы») |
| ✅ | ВЫБОР [выражение] КОГДА … ТОГДА … [ИНАЧЕ …] КОНЕЦ / CASE [expr] WHEN … THEN … [ELSE …] END |
простая форма сравнивает каждую альтернативу с выражением после ВЫБОР по тем же правилам, что и сравнение в ГДЕ (ссылки, составные поля, значения типа); NULL в выражении не совпадает ни с одной альтернативой, как на платформе; ветки разных типов дают значение составного типа: в проекции оно раскладывается по членам (<имя> — payload ссылки, <имя>_S, <имя>_N, <имя>_T, <имя>_L и <имя>_TYPE), каждая ветка пишет своё значение в свой член и нули в остальные — так же хранит и возвращает платформа; ветка, состоящая из одних NULL (например вложенный ВЫБОР по несвязанным параметрам), получает тип альтернативы: без этого PostgreSQL читает её как text и отвергает соседство с payload ссылки; двоичные данные и УникальныйИдентификатор члена в раскладке 1С не имеют (такое значение не попадает в таблицу), поэтому получают собственные члены <имя>_B и <имя>_U с тегом NULL — платформа отвечает на такую ветвь двоичными данными, а ТИПЗНАЧЕНИЯ от неё даёт Null (замерено на 8.3.27); ТИПЗНАЧЕНИЯ от самого разнотипного ВЫБОР пока не компилируется; вне проекции разнотипные ветки — диагностика, кроме сравнения и ПРЕДСТАВЛЕНИЕ: в сравнении со значением ветвь другого вида отдаёт NULL и потому не совпадает (как на платформе; <> с такой ветвью даёт NULL, а не платформенную истину), при сравнении с NULL или параметром без значения ветви меряются по первой типизированной; ПРЕДСТАВЛЕНИЕ оно проталкивается в ветви и даёт одну строковую колонку (строковая ветвь — сама строка, ссылочная — представление по плану приложения), как отвечает платформа (замерено на 8.3.27); ветвь, представимая только отложенным протоколом, — диагностика; вид результата — первая не-NULL ветвь, остальные должны быть совместимы; ссылки на разные объекты расширяются до runtime-typed payload; агрегаты внутри ВЫБОР допустимы в сгруппированных ветвях и в ветвях из одних агрегатов |
Полный перечень функций языка запросов даёт страница «Функции языка запросов», агрегатные перечислены на странице «Агрегатные функции языка запросов». Английские написания взяты из двуязычной таблицы «Двуязычное представление ключевых слов» и заголовков страниц функций.
| Статус | Функция | Примечание |
|---|---|---|
| ✅ | КОЛИЧЕСТВО(*), КОЛИЧЕСТВО(x), КОЛИЧЕСТВО(РАЗЛИЧНЫЕ x) / COUNT([DISTINCT] …) |
ColumnKind::Number; РАЗЛИЧНЫЕ в 1С тоже допустимо только у КОЛИЧЕСТВО |
| ✅ | СУММА / SUM |
аргумент — любое скалярное выражение (СУММА(ВЫБОР … КОНЕЦ)) |
| ✅ | МИНИМУМ / MIN, МАКСИМУМ / MAX |
аргумент — любое скалярное выражение; тип результата — тип аргумента; ссылочное выражение агрегируется как payload |
| ✅ | СРЕДНЕЕ / AVG |
аргумент — любое скалярное выражение, РАЗЛИЧНЫЕ и * не допускаются; результат — Number; на SQL Server среднее целочисленных литералов целое, у numeric колонок шесть знаков после запятой, PostgreSQL возвращает полную точность |
| ❌ | СГРУППИРОВАНОПО(x) / GROUPEDBY |
имеет смысл только с группирующими наборами |
| Статус | Функция | Примечание |
|---|---|---|
| ✅ | ВЫРАЗИТЬ(x КАК БУЛЕВО | ЧИСЛО [(Длина[, Точность])] | СТРОКА [(Длина)] | ДАТА) / CAST … AS BOOLEAN | NUMBER | STRING | DATE |
ЧИСЛО без параметров на MSSQL — numeric(38, 10); в 1С длина СТРОКА ограничена 1024 |
| ✅ | ВЫРАЗИТЬ(x КАК Справочник.X)[.Реквизит] |
сужается не только поле, но и выражение: ссылка того же типа сохраняет значение, payload сужается по префиксу типа, значение, которое NULL при любом типе (в том числе несвязанный параметр), даёт NULL названного типа, прочие виды — диагностика, как их отвергает платформа; значение — RRRef под guard RTRef, чужие типы → NULL (как в 1С); одно разыменование через LEFT JOIN; в ПО допустимо само сужение, но не .Реквизит после него («JOIN condition supports direct fields only») |
| ✅ | ЗНАЧЕНИЕ(Перечисление.X.Y), ЗНАЧЕНИЕ(Справочник.X.Предопределенный), ЗНАЧЕНИЕ(ПланСчетов.X.Счет), ЗНАЧЕНИЕ(ПланВидовХарактеристик.X.Вид) / VALUE |
справочники, перечисления, планы счетов и планы видов характеристик (предопределённые элементы лежат в ресурсах <guid>.1c, .9 и .7 соответственно, замерено на УНФ и демо-бухгалтерии; планы видов расчёта — после замера); имена внутри скобок принимаются и тогда, когда совпадают с ключевым словом (в реальных конфигурациях есть значение перечисления НеОпределено) |
| 🟡 | ЗНАЧЕНИЕ(ВидДвиженияНакопления.Приход), ЗНАЧЕНИЕ(ВидДвиженияБухгалтерии.Дебет), ЗНАЧЕНИЕ(ВидСчета.АктивноПассивный) / AccumulationRecordType, AccountingRecordType, AccountType |
системные перечисления компилируются в число, которое хранит платформа: Приход 0, Расход 1 (колонка _RecordKind), Дебет 0, Кредит 1 (_Correspond), Активный 0, Пассивный 1, АктивноПассивный 2 (_Kind плана счетов, замерено на плане счетов УНФ по предопределённым счетам); принимаются везде, где принимается числовой литерал, в том числе в условиях виртуальных таблиц; ТИПЗНАЧЕНИЯ от такого значения отвечает числом, а платформа — типом перечисления |
| ✅ | ЗНАЧЕНИЕ(<Вид>.<Объект>.ПустаяСсылка) / EmptyRef |
16 нулевых байт с видом Reference{targets: [объект]} для всех ссылочных видов; сравнение с runtime-typed полем проверяет _RTRef и _RRRef |
| ✅ | Литерал ТИП(Строка), ТИП(Справочник.X) / TYPE |
аргумент — Строка, Число, Дата, Булево (String, Number, Date, Boolean) или объект метаданных с номером типа; прочее — диагностика Syntax, как в 1С («Таблица не найдена») |
| ✅ | ТИПЗНАЧЕНИЯ(x) / VALUETYPE |
вид колонки — Type, значение — 5 байт: тег _TYPE платформы (0x01 Неопределено, 0x02 Булево, 0x03 Число, 0x04 Дата, 0x05 Строка, 0x08 ссылка, 0x00 тип NULL — замерено на платформе) и номер таблицы ссылки; составное поле читает _TYPE и _RTRef, поле из вложенного запроса — колонку <имя>_TYPE рядом с payload, универсальная ссылка — префикс payload, прочие выражения дают константу своего вида под охраной IS NULL; NULL и несвязанный параметр дают тип NULL, так что результат никогда не NULL; двоичные поля, УникальныйИдентификатор и неклассифицированные типы — UnsupportedFeature; группировка и упорядочивание по типу не поддержаны; консоль печатает имя типа (Справочник.Товары, Строка) |
| ✅ | ЕСТЬNULL(x, y) / ISNULL |
COALESCE(x, y); вид — вид x (или y, если x — NULL); ссылки расширяются как в ВЫБОР; строковый результат на PostgreSQL приводится к text, как и у ВЫБОР и агрегатов, иначе тип-расширение mvarchar не читается драйвером |
| ✅ | ПРЕДСТАВЛЕНИЕ(x) / PRESENTATION, ПРЕДСТАВЛЕНИЕССЫЛКИ(x) / REFPRESENTATION |
аргументом принимается любое выражение — замерено на 8.3.27: значение, которое не ссылка, само себе представление (строка отвечает собой, склейка — результатом, число — цифрами); ссылочное выражение несёт саму ссылку отложенной колонкой представления — так же, как универсальная ссылка поля, и приложение разрешает её вторым проходом (сверено: консоль разрешает пробу в те же имена, что печатает платформа); универсальные ссылки полей резолвятся отложенно пакетами; аргументом может быть агрегат — такая проекция считается агрегатной, и ветвь агрегирует (замерено на 8.3.27: ПРЕДСТАВЛЕНИЕ(МАКСИМУМ(Т.Клиент)) даёт представление наибольшей ссылки, ПРЕДСТАВЛЕНИЕ(КОЛИЧЕСТВО(*)) — число текстом, с группировкой — по каждой группе) |
| ✅ | УНИКАЛЬНЫЙИДЕНТИФИКАТОР(x) / UUID |
нативный uuid / uniqueidentifier; аргумент — ссылочное поле; NULL → NULL как в 1С; нессылочный аргумент — ошибка компиляции (в 1С — ошибка выполнения) |
| ✅ | АВТОНОМЕРЗАПИСИ() / RECORDAUTONUMBER |
ROW_NUMBER() OVER (ORDER BY (SELECT NULL)) — уникальный номер строки без определённого порядка; в 1С допустима только в запросе с ПОМЕСТИТЬ, компилятор принимает её в любом операторе |
| ❌ | РАЗМЕРХРАНИМЫХДАННЫХ |
английское написание в справке не приведено |
| Статус | Функция | Примечание |
|---|---|---|
| ✅ | ПОДСТРОКА(x, нач, длина) / SUBSTRING |
позиции с единицы, длина за концом обрезается, нулевая длина даёт пустую строку |
| ❌ | СТРОКА(x) / STRING, как цель ВЫРАЗИТЬ — ✅ |
платформа возвращает локализованное представление (10,00, 15.01.2024 00:00:00, Да), воспроизвести это в SQL точно нельзя; используйте ВЫРАЗИТЬ(x КАК СТРОКА) |
| ✅ | ДлинаСтроки(x) / StringLength |
считает и концевые пробелы, поэтому на SQL Server не LEN, а LEN(x + '.') - 1 |
| ✅ | СокрЛП / TrimAll, СокрЛ / TrimL, СокрП / TrimR |
убирают пробелы |
| ✅ | ВРег / Upper, НРег / Lower |
|
| ✅ | Лев(x, n) / Left, Прав(x, n) / Right |
английские имена совпадают с ключевыми словами соединений, поэтому распознаются только в выражении; на PostgreSQL выводятся через substring, так как left/right появились в 9.1 |
| ✅ | СтрНайти(x, подстрока) / StrFind, СтрЗаменить / StrReplace |
СтрНайти возвращает позицию с единицы и 0, если подстроки нет; СтрЗаменить заменяет все вхождения |
НСтр в Синтакс-помощнике как функция языка запросов не значится
(предыдущая редакция таблицы ошибочно включала её).
| Статус | Функция | Примечание |
|---|---|---|
| ✅ | Окр(x[, разрядность]) / Round, Цел(x) / Int |
Окр округляет от нуля и принимает отрицательную разрядность, разрядность по умолчанию 0; Цел отсекает к нулю; на SQL Server результат сохраняет масштаб аргумента |
| ✅ | ACos, ASin, ATan, Cos, Sin, Tan, Exp, Log, Log10, Pow, Sqrt |
Log — натуральный логарифм (на PostgreSQL это ln, а log — десятичный), Log10 — десятичный; тригонометрические на PostgreSQL приводят аргумент к double precision |
| Статус | Функция | Примечание |
|---|---|---|
| ✅ | ДАТАВРЕМЯ(г, м, д[, ч, мин, с]) / DATETIME |
только целочисленные литералы; на MSSQL учитывается _YearOffset |
| ✅ | НАЧАЛОПЕРИОДА(x, МИНУТА | ЧАС | ДЕНЬ | НЕДЕЛЯ | МЕСЯЦ | КВАРТАЛ | ГОД | ДЕКАДА | ПОЛУГОДИЕ) / BEGINOFPERIOD |
все девять периодов; неделя с понедельника; на SQL Server 2008 — эмуляция DATEADD/DATEDIFF |
| ✅ | КОНЕЦПЕРИОДА(x, период) / ENDOFPERIOD |
те же девять периодов; последняя секунда периода, декада заканчивается 10-м, 20-м или последним днём месяца; СЕКУНДА — диагностика Syntax, как в 1С |
| ✅ | ДОБАВИТЬКДАТЕ(x, период, n) / DATEADD |
десять периодов, включая СЕКУНДА; n — любое числовое выражение, поле или параметр; конец месяца «прижимается»; дробное n округляется для СЕКУНДА…МЕСЯЦ и усекается для ДЕКАДА, КВАРТАЛ, ПОЛУГОДИЕ, ГОД — так считает платформа |
| ✅ | РАЗНОСТЬДАТ(a, b, СЕКУНДА | МИНУТА | ЧАС | ДЕНЬ | МЕСЯЦ | КВАРТАЛ | ГОД) / DATEDIFF |
считает пересечённые границы единицы (31.12 23:59:59 → 01.01 в днях даёт 1), как DATEDIFF SQL Server и платформа; НЕДЕЛЯ, ДЕКАДА, ПОЛУГОДИЕ — диагностика Syntax; секунды не переполняются на всём диапазоне дат |
| ✅ | ГОД, КВАРТАЛ, МЕСЯЦ, ДЕНЬГОДА, ДЕНЬ, НЕДЕЛЯ, ДЕНЬНЕДЕЛИ, ЧАС, МИНУТА, СЕКУНДА / YEAR, QUARTER, MONTH, DAYOFYEAR, DAY, WEEK, WEEKDAY, HOUR, MINUTE, SECOND |
результат — целое число; ДЕНЬНЕДЕЛИ — 1 (понедельник) … 7 (воскресенье) независимо от DATEFIRST; НЕДЕЛЯ — нумерация платформы, не ISO 8601: неделя, в которую попадает 1 января, — первая, недели начинаются с понедельника, нумерация начинается заново 1 января; имена функций остаются допустимыми псевдонимами (ГОД(Дата) КАК Год); на MSSQL части берутся от логической даты с учётом _YearOffset |
Списки параметров ниже — в порядке, заданном страницами таблиц Синтакс- помощника; в 1С любой параметр можно опустить, оставив запятую. Страница справки у виртуальной таблицы называется так же, как сама таблица.
| Статус | Источник | Примечание |
|---|---|---|
| ✅ | Справочник, Документ, Перечисление, ПланВидовХарактеристик, ПланСчетов, ПланВидовРасчета, ПланОбмена, РегистрСведений, РегистрНакопления, РегистрБухгалтерии, РегистрРасчета, БизнесПроцесс, Задача, Константа, Последовательность |
русские, английские и короткие имена видов (Catalog/Reference, InfoRg, AccumRg, …); объект должен иметь живую таблицу |
| ✅ | Табличные части Документ.X.ТЧ, Справочник.X.ТЧ |
стандартные поля строки Ссылка, НомерСтроки; таблицы расширений X/X1 объединяются UNION ALL |
| ✅ | Константы / Constants (как одна таблица) |
поля — имена констант, * допускается; в SQL — UNION ALL только по константам, которые упоминает запрос, свёрнутый MAX в одну строку; незаписанная константа даёт NULL; разделители применяются в каждой ветви |
| ✅ | Константа.<Имя> / Constant.<Name> (как отдельная таблица) |
одно поле Значение / Value; имя самой константы полем не является — замерено на 8.3.27: ВЫБРАТЬ * ИЗ Константа.ОсновнойТовар даёт колонку Значение, а К.ОсновнойТовар — «Поле не найдено»; поле проецируется, фильтруется, группируется, упорядочивается и разыменовывается как любое другое; разделители таблицы применяются как у обычного источника; состав * пока расходится с платформой (мы показываем независимый разделитель и RecordKey, платформа — нет) |
| ❌ | ВнешнийИсточникДанных |
внешние источники данных в компиляторе отсутствуют; КритерийОтбора и ЖурналДокументов поддерживаются — см. их строки выше |
| ✅ | Главная таблица РегистрБухгалтерии.X: СчетДт/СчетКт (AccountDr/AccountCr; Счет без корреспонденции), балансовые измерения и ресурсы по имени, небалансовые — <Имя>Дт/<Имя>Кт (<Имя>Dr/<Имя>Cr), реквизиты, Период, Регистратор, НомерСтроки, Активность |
назначения полей, флаг «Балансовый» и план счетов регистра читаются из Config (коллекции и флаг замерены на 8.3.27 по регистру Управленческий УНФ); колонки _Fld<N>Dt/_Fld<N>Ct относятся к полю N; УточнениеПериода не отвечается |
| ✅ | Служебные части: Изменения (ПланОбмена/регистрация изменений; поля Узел/Node и НомерСообщения/MessageNo), БазовыеВидыРасчета, ВедущиеВидыРасчета, ВытесняющиеВидыРасчета, ВидыСубконто |
остальные служебные таблицы видны в \dt, но во FROM дают UnsupportedFeature |
| ✅ | РегистрСведений.X.СрезПоследних(Период, Условие) / SliceLast |
оба аргумента необязательны; условие — по прямым измерениям и разделителям; только активные записи (как в 1С с 8.3.18) |
| ✅ | РегистрСведений.X.СрезПервых(Период, Условие) / SliceFirst |
|
| ✅ | РегистрНакопления.X.Остатки(Период, Условие) / Balance |
только регистры остатков; ресурсы суммируются по измерениям, которые запрос не читает, как на платформе (измерение из условия самой виртуальной таблицы группировки не добавляет); условие принимает разыменование (Номенклатура.Родитель = &Р) — цель присоединяется к ветке итогов и к ветке движений; список аргументов можно опустить |
| 🟡 | РегистрНакопления.X.Обороты(НачалоПериода, КонецПериода, Периодичность, Условие) / Turnovers |
у регистра остатков на каждый ресурс отвечаются <Ресурс>Оборот, <Ресурс>Приход и <Ресурс>Расход (суммы по виду записи), у оборотного — только <Ресурс>Оборот; периодичность — календарная единица от Секунда до Год, пишется именем периода; Период (документированное умолчание: «только за период, не разворачивать») равносильна опущенной периодичности; Авто («определяется по используемым в запросе полям периодов») даёт поля Период, ПериодСекунда…ПериодГод (начало соответствующего периода записи), Регистратор и НомерСтроки как измерения: прочитанные разворачивают таблицу, непрочитанные суммируются, без них — весь интервал; таблица получает поле Период (начало периода записи) и группируется по нему даже тогда, когда запрос Период не читает, как на платформе; Регистратор группирует по периоду и регистратору записи и выдаёт поля Период и Регистратор, Запись добавляет НомерСтроки и даёт строку на каждую запись регистра; НомерСтроки при Регистратор недоступен, как на платформе; поля ПериодГод…ПериодСекунда недоступны; ресурсы суммируются по непрочитанным измерениям |
| 🟡 | РегистрНакопления.X.ОстаткиИОбороты(НачалоПериода, КонецПериода, Периодичность, МетодДополненияПериодов, Условие) / BalanceAndTurnovers |
на каждый ресурс выдаются НачальныйОстаток, Приход, Расход, Оборот, КонечныйОстаток; значения считаются по движениям: начальный остаток — знаковое движение до начала, приход и расход — движения [начало, конец) по виду записи, конечный — их сумма; суммируются по непрочитанным измерениям, как у прочих таблиц регистра; календарная периодичность группирует движения интервала по периодам и даёт поле Период — ровно то, что отвечает платформа, пока не читается колонка остатка; метод дополнения периодов принимается и без периодичности (там ему нечего дополнять, платформа его допускает); оба метода дают одни и те же строки там, где остаток не читается; под Авто те же поля разворота, что у Обороты, а остатки развёрнутой таблицы — бегущие суммы, как у регистра накопления (части Дт/Кт — от бегущей суммы), на SQL Server 2008 — диагностика; колонки остатка развёрнутой таблицы — бегущие суммы оконной функцией (SUM(SUM(…)) OVER (PARTITION BY измерения ORDER BY корзина ROWS BETWEEN …)) над движениями до Конец, разложенными по корзинам гранулярности — календарный период, регистратор, запись, — где движения до Начало образуют первую корзину, отбрасываемую после окна; под Авто гранулярность — то, что читает запрос (запись при НомерСтроки, регистратор при Регистратор/Период, иначе самый мелкий прочитанный уровень периода), запрос без колонок остатка получает отношение без окон; на SQL Server 2008 остатки развёрнутой таблицы отклоняются (нет рамки окна); метод ДвиженияИГраницыПериода пограничных строк не добавляет; Регистратор и Запись как периодичность — разворот по периоду записи и регистратору (и номеру строки), остатки — бегущие суммы по тем же корзинам, на SQL Server 2008 — диагностика (сверено на живой демо-бухгалтерии: начальный остаток плюс оборот равен конечному в каждой строке); только регистр остатков |
| 🟡 | РегистрБухгалтерии.X.Остатки(Период, УсловиеСчета, Субконто, Условие) / Balance |
только регистр с корреспонденцией, по движениям на той же свёртке сторон, что Обороты: <Ресурс>Остаток — дебет минус кредит по активным записям до Период (без него — все), <Ресурс>ОстатокДт/<Ресурс>ОстатокКт — положительная и взятая с минусом отрицательная часть остатка на том уровне, который читает запрос (пересчитываются после суммирования непрочитанных измерений, а не суммируются); комбинации с нулевыми остатками отбрасываются; <Ресурс>РазвернутыйОстатокДт/Кт — положительная и взятая с обратным знаком отрицательная части остатка по счёту, измерениям и субконто, суммируемые снаружи по непрочитанным измерениям (сверено на живой демо-бухгалтерии: разность частей равна свёрнутому остатку); у регистра без субконто аргумент «Субконто» отсутствует (Остатки(Период, УсловиеСчета, Условие)); SQL выполнен на живой базе УНФ субконто: поля Субконто<k> (составное значение) и ВидСубконто<k> по числу уровней регистра читаются из встроенных колонок стороны (_ValueDt<k>_*, _KindDt<k>RRef, замерено на демо-бухгалтерии) и суммируются, если не прочитаны; без аргумента «Субконто» позиции — порядок видов самого счёта; аргумент — один вид (ЗНАЧЕНИЕ(ПланВидовХарактеристик.…) или параметр-ссылка) либо список в скобках, тогда Субконто<j> берёт значение уровня с j-м указанным видом, а записи, у чьего счёта вида нет, отбрасываются; параметр без привязанной ссылки (не привязан либо массив, которого компилятор не видит) оставляет позиции как без аргумента; в условии видны позиционные Субконто<k> |
| 🟡 | РегистрБухгалтерии.X.Обороты(НачалоПериода, КонецПериода, Периодичность, УсловиеСчета, Субконто, Условие, УсловиеКорСчета, КорСубконто) / Turnovers |
только регистр с корреспонденцией: каждая активная запись [Начало, Конец) даёт строку дебета и строку кредита, группировка по Счет, прочитанным измерениям и календарному периоду; небалансовое измерение или ресурс читается из колонки своей стороны под общим именем; на ресурс — <Ресурс>Оборот (Дт минус Кт), <Ресурс>ОборотДт, <Ресурс>ОборотКт; непрочитанные измерения суммируются; УсловиеСчета — предикат на Счет стороны, Условие видит запись глазами стороны; у регистра без субконто платформа опускает аргументы «Субконто» (замерено на УНФ: Обороты(&Н, &К, МЕСЯЦ, , Условие)), раскладка аргументов следует наличию таблицы AccRgED; Регистратор и Запись разворачивают как у регистра накопления; корреспонденция: КорСчет, <Измерение>Кор небалансовых измерений, КорСубконто<k>/ВидКорСубконто<k> — ветка дебета читает их из кредитовых колонок, ветка кредита из дебетовых; КорСубконто перечисляет виды как Субконто, проверка на противоположной стороне; УсловиеКорСчета компилируется вместе с условием счёта; сверено на живой демо-бухгалтерии; регистр без корреспонденции — позже |
| 🟡 | РегистрБухгалтерии.X.ОстаткиИОбороты(НачалоПериода, КонецПериода, Периодичность, МетодДополненияПериодов, УсловиеСчета, Субконто, Условие) / BalanceAndTurnovers |
на ресурс: НачальныйОстаток (записи до Начало), Оборот/ОборотДт/ОборотКт за [Начало, Конец), КонечныйОстаток, части Дт/Кт обоих остатков — производные на итоговом уровне; календарная периодичность, Регистратор, Запись и Авто разворачивают, остатки при этом — бегущие суммы оконной функцией (SQL Server 2008 — диагностика); метод дополнения периодов — по правилам регистра накопления; у регистра без субконто аргумент «Субконто» отсутствует; SQL выполнен на живой базе УНФ субконто — как у Остатки; <Ресурс>НачальныйРазвернутыйОстатокДт/Кт и <Ресурс>КонечныйРазвернутыйОстатокДт/Кт — только без периодичности (под разворотом — диагностика); метод дополнения периодов принимается и без периодичности |
| 🟡 | РегистрБухгалтерии.X.ОборотыДтКт(НачалоПериода, КонецПериода, Периодичность, УсловиеСчетаДт, СубконтоДт, УсловиеСчетаКт, СубконтоКт, Условие) / DrCrTurnovers |
без свёртки: одна строка на пару СчетДт/СчетКт, балансовые измерения, стороны небалансовых, СубконтоДт<k>/СубконтоКт<k> (и их виды) обеих сторон, разворот периодичности; на балансовый ресурс — <Ресурс>Оборот, на небалансовый — <Ресурс>ОборотДт/<Ресурс>ОборотКт; непрочитанные измерения суммируются; списки видов субконто каждой стороны — как у Остатки; условия видят поля записи; без субконто аргументы «СубконтоДт»/«СубконтоКт» отсутствуют; Авто, Регистратор, Запись разворачивают; SQL выполнен на живой демо-бухгалтерии |
| 🟡 | РегистрБухгалтерии.X.ДвиженияССубконто(НачалоПериода, КонецПериода, Условие, Порядок, Первые) / RecordsWithExtDimensions |
записи [Начало, Конец) с полями главной таблицы и СубконтоДт<k>, ВидСубконтоДт<k>, СубконтоКт<k>, ВидСубконтоКт<k> из встроенных колонок; условие видит те же поля и безсторонние имена Счет, Субконто<k>, ВидСубконто<k>, небалансовые измерения и ресурсы — такое условие выполняется, если верно для дебета или для кредита (по синтакс-помощнику, на платформе не замерено); Первые — число или параметр-число: LIMIT/TOP (N) в порядке Порядок (поля записи по возрастанию, одно или кортеж; параметр NULL — без порядка) или в порядке записи (период, регистратор, номер строки); Порядок без Первые ничего не меняет (у источника нет порядка, SQL Server не принимает ORDER BY в подзапросе) |
| ✅ | РегистрБухгалтерии.X.Субконто / ExtDimensions (без параметров) |
таблица _AccRgED: Период, Регистратор, НомерСтроки, УточнениеПериода, ВидДвижения (Correspond, сторона записи), Вид (ссылка на план видов характеристик), Значение (составное значение); замерено на демо-бухгалтерии: строка на запись, сторону и уровень |
| ❌ | РегистрРасчета.X.ФактическийПериодДействия(Условие) / AdjustedEffectivePeriod |
|
| ❌ | РегистрРасчета.X.ДанныеГрафика(Условие) / ScheduleData |
|
| ❌ | РегистрРасчета.X.База<Регистр>(ИзмеренияОсновногоРегистра, ИзмеренияБазовогоРегистра, Разрезы, Условие) / Base<Register> |
|
| 🟡 | Периоды и условия виртуальных таблиц | период — литерал, ДАТАВРЕМЯ, параметр-дата, а также НАЧАЛОПЕРИОДА, КОНЕЦПЕРИОДА, ДОБАВИТЬКДАТЕ над ними (Обороты(НАЧАЛОПЕРИОДА(&П, МЕСЯЦ), КОНЕЦПЕРИОДА(&П, МЕСЯЦ))); условие агрегирующих таблиц (Остатки, Обороты, ОстаткиИОбороты, условие счёта) принимает разыменование: цель присоединяется LEFT JOIN к той ветке, которую условие фильтрует (у свёртки регистра бухгалтерии — по счёту своей стороны, у остатков регистра накопления — к итогам и к движениям порознь); условие срезов — прямые поля |
В скобках — написание, которое принимает open-sdbl, если оно отличается от
имени 1С. Английские имена платформы Ref, DeletionMark и LineNumber не
распознаются: пишите ID, Marked, LineNo или русский синоним.
| Статус | Поле (RU / EN) | Примечание |
|---|---|---|
| ✅ | Ссылка / Ref (ID), Код / Code, Наименование / Description, ПометкаУдаления / DeletionMark (Marked), ВерсияДанных / Version, Номер / Number, Дата / Date, Проведен / Posted, Регистратор / Recorder, НомерСтроки / LineNumber (LineNo), Период / Period, Активность / Active, Родитель / Parent (ParentID), Владелец / Owner (OwnerID) |
у каждого из четырнадцати полей принимаются оба синонима — русский и схемный |
| 🟡 | Предопределенный / Predefined, ЭтоГруппа / IsFolder |
вычисляются, как на платформе: ЭтоГруппа — отрицание колонки Folder (она хранит ИСТИНУ у элемента), Предопределенный — непустой PredefinedID; отвечают в проекции, ГДЕ, группировке, упорядочивании и через ссылку, вид колонки — Boolean; в * не попадают, там остаются схемные колонки |
| ✅ | Стандартные поля плана счетов: Вид/Kind, Забалансовый/OffBalance, Порядок/Order (OrderField) |
колонки _Kind, _OffBalance, _OrderField таблицы _Acc; Вид сравнивается с ЗНАЧЕНИЕ(ВидСчета.…), работает и через разыменование (Т.СчетДт.Вид) |
| ✅ | Стандартные поля бизнес-процессов и задач: Завершен/Completed, Стартован/Started, ВедущаяЗадача/HeadTask, Наименование/Name, Выполнена/Executed, БизнесПроцесс/BusinessProcess, ТочкаМаршрута/Point |
имена проверены на платформе на пробной конфигурации с бизнес-процессом и его задачей |
| 🟡 | ИмяПредопределенныхДанных / PredefinedDataName |
сопоставляется с именем предопределённого элемента, объявленным в конфигурации: строка с именем, пустая строка у непредопределённой записи, NULL у непопавшей строки соединения; вид колонки — String. Платформа хранит идентификатор и переводит его в имя вне SQL, поэтому упорядочивание и сравнения </> идут по имени, а не по идентификатору, ПОДОБНО и строковые функции над полем принимаются (платформа их запрещает), а имя, которого нет, даёт пустую выборку, а не ошибку |
| ✅ | ВидДвижения / RecordType |
принимается и схемное имя из SchemaStorage (RecordKind); имя запроса проверено на платформе |
| 🟡 | МоментВремени / PointInTime |
пара «дата + ссылка», физической колонки за ней нет: у документа это Дата и Ссылка, у записи регистра, подчинённого регистратору, — Период и Регистратор. Замерено на 8.3.27: платформа раскладывает пару на две колонки выборки (<имя>_T — дата, <имя> — ссылка), на два члена в УПОРЯДОЧИТЬ ПО, СГРУППИРОВАТЬ ПО и РАЗЛИЧНЫЕ; так же поступает и компилятор. У справочника и у независимого регистра сведений поля нет — диагностика, как на платформе; агрегат и разыменование платформа тоже запрещает. Отличие: сравнение двух моментов времени платформа раскрывает лексикографически (дата >, при равенстве — ссылка), здесь пара в выражениях отклоняется диагностикой |
| ✅ | Источник.Представление / Presentation |
представление собственной ссылки источника; путь тот же, что у ПРЕДСТАВЛЕНИЕССЫЛКИ(Источник.Ссылка) — план представления запрашивается у приложения; источник без собственной ссылки — диагностика |
| ✅ | ТипЗначения / ValueType у плана видов характеристик |
колонка Type объекта |
| ✅ | Порядок / Order у перечисления |
колонка EnumOrder: порядок объявления значения, начиная с нуля (замерено на платформе) |
| ✅ | Реквизиты, добавленные расширениями | по _ExtensionsRestruct |
По странице «Константы и параметры в языке запросов» литералами являются
ИСТИНА, ЛОЖЬ, число, строка, ДАТАВРЕМЯ(…), ТИП(…), параметр &Имя,
НЕОПРЕДЕЛЕНО, NULL.
| Статус | Элемент | Примечание |
|---|---|---|
| ✅ | Строки "…" с удвоением "" |
многострочные литералы с | — ❌ |
| ✅ | Числа | |
| ✅ | ИСТИНА / ЛОЖЬ / NULL (TRUE / FALSE) |
|
| 🟡 | НЕОПРЕДЕЛЕНО / UNDEFINED |
компилируется в NULL, вид колонки — Undefined; сравнение с литералом сравнивает тип значения с типом «Неопределено»: составное поле совпадает только при теге 0x01, значение вида, который не может хранить Неопределено (двоичное, УникальныйИдентификатор, тип), даёт константный предикат ЛОЖЬ (<> — ИСТИНА), как платформа возвращает пустую выборку вместо ошибки; в ВЫБОР, ЕСТЬNULL и ОБЪЕДИНИТЬ совместим с любым видом, как NULL; отличие от 1С: в результате Неопределено неотличимо от NULL |
| ✅ | ТИП(…) / TYPE |
см. раздел 3 |
| ✅ | Бинарные литералы 0x… |
расширение open-sdbl (нет в 1С) |
| 🟡 | Даты | только через ДАТАВРЕМЯ; строковые даты допускаются лишь в аргументах виртуальных таблиц |
| ✅ | Параметры &Имя |
значения передаются через CompileOptions::parameters и инлайнятся типизированными литералами (Null, Boolean, Number, String, Date, Reference, Binary, List только в В (…)); в консоли — \set, \params, \unset |
| ✅ | Параметры сеанса &Имя |
расширение open-sdbl: CompileOptions::session (SessionParameters) видны всем запросам и ограничениям доступа сеанса; параметр запроса с тем же именем имеет приоритет; неиспользованный параметр сеанса — не ошибка; в консоли — \session |
| ✅ | Разделители данных (общие реквизиты Разделять) |
как в 1С: каждая разделённая таблица получает _Fld<N> = <значение>, значение — из параметра сеанса, привязанного к разделителю в Config (иначе по имени реквизита); без значения Независимо и совместно фильтруется пустым значением, Независимо — диагностика Parameter; параметр использования ЛОЖЬ отключает предикат |
| ✅ | Бинарный литерал в формате вывода консоли против ссылочного поля | 16 байт для одночленной ссылки, 20 байт RTRef ‖ RRRef для runtime-typed поля (=, <>, В); иная длина — диагностика |
| ✅ | Комментарии // |
- Бинарные литералы
0x…. - Ключевое слово
ONвместоПОв условии соединения; короткие английские имена видов метаданных (Reference,InfoRg,AccumRg, …) и физические имена стандартных полей (Folder,ParentID,RecordKind, …). ColumnKindдля каждой колонки результата и нативные типы вместо текста.- Колонка
__levelу результата сИТОГИ(по опцииCompileOptions::totals_level, в консоли включена): уровень строки, какУровень()у выборки по группировкам, потому что результат — плоский набор строк, а не дерево. - Параметры сеанса:
SessionParametersвидны каждому запросу и каждому ограничению доступа, в отличие от параметров одногоЗапроса. - Разделители данных без значения в сеансе фильтруются пустым значением (общие данные), а не читаются целиком; платформа в этом случае не фильтрует.
- Прикладная политика вместо ролей конфигурации: представления значений
(
PresentationPlan) и построчные ограниченияРАЗРЕШЕННЫЕ(AccessRestriction) приходят от приложения через callback, потому что ядро не выполняет ввод-вывод и не читает роли. - Уровень диалекта MSSQL (
2008/2012), поддержка PostgreSQL 9.0+ и баз платформы 8.2 безPartNo.
Основной источник — Синтакс-помощник платформы 1С:Предприятие 8.3.27.2342
(/opt/1cv8/x86_64/8.3.27.2342): раздел «Язык запросов» с корневой страницей
«Синтаксис текста запросов» и страницы таблиц. Названия страниц приведены
так, как их показывает сам Синтакс-помощник. Программно те же страницы читает
MCP-сервер unica (unica.documentation.search / unica.documentation.get,
корпус platform-help, authority: vendor): страница находится поиском по
названию.
Дополнительные источники (для истории; при расхождениях приоритет у Синтакс-помощника):
- kb.1ci.com, «Query language»: https://kb.1ci.com/1C_Enterprise_Platform/FAQ/Development/Queries/Query_language/
- Грамматика 1c-syntax (ключевые слова RU/EN): https://github.com/1c-syntax/1c-syntax/blob/master/1c-query.YAML-tmLanguage
- 1С:Зазеркалье, «Новые функции языка запросов» (строковые и математические функции появились в 8.3.20): https://wonderland.v8.1c.ru/blog/novye-funktsii-yazyka-zaprosov-i-sistemy-komponovki-dannykh/