Как выгрузить Таблицу Значений из запроса и использовать её во временных таблицах для соединения данных

Программист 1С v8.3 (Обычные формы) IT и автоматизация бизнеса
← На главную

В практике разработки на платформе 1С:Предприятие 8.3 часто возникает необходимость обработать данные, полученные из внешних источников (SQL, Excel или API), и сопоставить их с объектами внутренней базы данных (справочниками, документами или регистрами). Оптимальным способом решения этой задачи является выгрузка данных в ТаблицуЗначений и последующая передача этой таблицы в запрос в качестве параметра. Однако начинающие разработчики часто сталкиваются с тем, что запрос к такой таблице возвращает пустой результат или выдает ошибки типов. Рассмотрим подробно, как правильно организовать этот процесс.

Почему запрос к Таблице Значений может не работать?

Разберем типичную ситуацию: вы выполняете запрос к Внешнему Источнику Данных, выгружаете результат в ТаблицуЗначений методом Результат.Выгрузить() и пытаетесь прочитать её в следующем запросе. Основная причина неудач здесь кроется в типизации. Когда мы используем ТаблицаЗначений как источник для временной таблицы в запросе, 1С требует, чтобы каждая колонка имела строго определенный тип. Если колонки не типизированы (имеют составной тип или тип Неопределено), механизм временных таблиц не сможет корректно создать структуру в базе данных (в tempdb), и соединение не сработает.

Проанализируем также поле Ссылка во внешних источниках. Оно существенно отличается от привычных нам ссылок 1С. Внешняя ссылка — это объектный идентификатор, который нельзя напрямую сравнивать со ссылкой на справочник 1С. Для связи таблиц лучше использовать примитивные типы данных: строки (артикулы, ИНН, коды) или числа (идентификаторы ID).

Шаг 1: Подготовка и строгая типизация Таблицы Значений

Для того чтобы запрос «увидел» данные в вашей таблице, мы не можем просто выгрузить результат первого запроса. Нам необходимо создать новую таблицу с четко описанной структурой. Рассмотрим, как это сделать программно:


ТЗ = Новый ТаблицаЗначений;
// Указываем конкретные типы для каждой колонки
ТЗ.Колонки.Добавить("Id", Новый ОписаниеТипов("Строка", , Новый КвалификаторыСтроки(50)));
ТЗ.Колонки.Добавить("Name", Новый ОписаниеТипов("Строка", , Новый КвалификаторыСтроки(150)));
ТЗ.Колонки.Добавить("Login", Новый ОписаниеТипов("Строка", , Новый КвалификаторыСтроки(100)));

После создания структуры нам нужно наполнить её данными из первого запроса. Рекомендуется использовать обход выборки, чтобы иметь возможность нормализовать данные, например, обрезать лишние пробелы функцией СокрЛП, что критично при работе с внешними SQL-базами (типы CHAR).


// Предположим, ЗапросКВнешнемуИсточнику уже выполнен
Выборка = ЗапросКВнешнемуИсточнику.Выполнить().Выбрать();

Пока Выборка.Следующий() Цикл
    НоваяСтрока = ТЗ.Добавить();
    НоваяСтрока.Id = СокрЛП(Выборка.Id);
    НоваяСтрока.Name = СокрЛП(Выборка.Name);
    НоваяСтрока.Login = СокрЛП(Выборка.Login);
КонецЦикла;

Шаг 2: Использование Менеджера Временных Таблиц

Для объединения данных нескольких запросов нам понадобится объект МенеджерВременныхТаблиц. Он позволяет сохранять промежуточные результаты (в нашем случае — содержимое ТаблицыЗначений) и обращаться к ним в последующих инструкциях пакета запросов.

Рассмотрим пошагово процесс помещения таблицы в запрос:


МенеджерВТ = Новый МенеджерВременныхТаблиц;
Запрос = Новый Запрос;
Запрос.МенеджерВременныхТаблиц = МенеджерВТ;

// Первый запрос пакета: помещаем ТЗ во временную таблицу
Запрос.Текст = 
"ВЫБРАТЬ
|   ВходящаяТЗ.Id КАК Id,
|   ВходящаяТЗ.Name КАК Name,
|   ВходящаяТЗ.Login КАК Login
|ПОМЕСТИТЬ ВРТаблица
|ИЗ
|   &ПараметрТЗ КАК ВходящаяТЗ;
|
|////////////////////////////////////////////////////////////////
|ВЫБРАТЬ
|   ВРТаблица.Name КАК ИмяИзВнешнегоИсточника,
|   Контрагенты.Ссылка КАК Ссылка1С,
|   Контрагенты.Код КАК Код1С
|ИЗ
|   ВРТаблица КАК ВРТаблица
|   ЛЕВОЕ СОЕДИНЕНИЕ Справочник.Контрагенты КАК Контрагенты
|   ПО ВРТаблица.Name = Контрагенты.Наименование";

Запрос.УстановитьПараметр("ПараметрТЗ", ТЗ);
РезультатЗапроса = Запрос.Выполнить();

Шаг 3: Тонкости соединения таблиц

Выясним причину, по которой ЛЕВОЕ СОЕДИНЕНИЕ может возвращать пустые поля из справочников 1С, даже если визуально данные совпадают. Посмотрим на наиболее частые ошибки:

  1. Несоответствие типов: Вы пытаетесь соединить колонку с типом Строка и колонку с типом Ссылка. Всегда соединяйте строку со строкой (например, Наименование или ИНН).
  2. Лишние пробелы: Если во внешней базе данных поле имеет тип Fixed String, оно дополняется пробелами. Перед помещением в ТЗ всегда используйте СокрЛП.
  3. Длина полей: Если длина колонки в ТаблицеЗначений меньше, чем длина поля в справочнике 1С, данные могут обрезаться, что сделает сопоставление невозможным.

Проанализируем ситуацию, когда необходимо найти дубли или задвоенные записи. Для этого можно использовать соединение таблицы самой с собой или соединение с условием ГДЕ Контрагенты.Ссылка ЕСТЬ NULL, если мы ищем записи из внешнего источника, которых еще нет в нашей базе 1С.

Практические советы по оптимизации

Если ваша ТаблицаЗначений содержит большое количество строк (более тысячи), работа запроса может замедлиться. В этом случае рекомендуется индексировать временную таблицу по полям связи сразу при её создании. Это делается с помощью инструкции ИНДЕКСИРОВАТЬ ПО в тексте запроса:


Запрос.Текст = 
"ВЫБРАТЬ
|   ТЗ.Id,
|   ТЗ.Name
|ПОМЕСТИТЬ ВРТаблица
|ИЗ
|   &ПараметрТЗ КАК ТЗ
|ИНДЕКСИРОВАТЬ ПО
|   Name";

Также важно помнить, что после завершения работы с запросом МенеджерВременныхТаблиц желательно очищать или закрывать, чтобы освободить ресурсы сервера, особенно если обработка выполняется в цикле или регламентном задании. Хотя 1С делает это автоматически при уничтожении объекта, явное управление ресурсами является признаком хорошего тона в разработке.

Таким образом, правильный алгоритм работы включает: строгую типизацию ТЗ, нормализацию строковых данных, использование Менеджера временных таблиц и контроль типов полей в условии соединения. Следуя этим шагам, вы сможете эффективно объединять данные из любых внешних систем с вашей информационной базой 1С.

← На главную