При разработке обработок в 1С часто возникает задача: нажать на кнопку и заполнить табличную часть данными, полученными по списку значений (например, по списку ИНН). Начинающие разработчики часто сталкиваются с искушением выполнить Запрос внутри цикла, перебирая каждый ИНН по отдельности. Давайте разберем, почему это является ошибкой и как правильно реализовать заполнение данных за один клик.
Когда вы помещаете Запрос в цикл, вы создаете ситуацию, при которой при каждом проходе цикла система совершает отдельное обращение к серверу баз данных. Если у вас в массиве 100 ИНН, вы делаете 100 отдельных запросов. Каждый такой вызов сопровождается:
В итоге, вместо того чтобы получить все данные одним махом, вы «заваливаете» сервер мелкими задачами, что приводит к значительным тормозам в интерфейсе и снижению производительности всей системы.
Вместо того чтобы запрашивать данные для каждого ИНН отдельно, соберите все ИНН в один массив и передайте его в запрос как единый параметр. Это самый быстрый и чистый способ.
Рассмотрим пример реализации:
// Собираем все ИНН из таблицы в массив
МассивИНН = Новый Массив;
Для Каждого Строка Из Объект.ТаблицаДанных Цикл
МассивИНН.Добавить(Строка.ИНН);
КонецЦикла;
// Создаем запрос, использующий массив
Запрос = Новый Запрос;
Запрос.Текст =
"ВЫБРАТЬ
| Клиенты.Наименование,
| Клиенты.ИНН
|ИЗ
| Справочник.Контрагенты КАК Клиенты
|ГДЕ
| Клиенты.ИНН В (&МассивИНН)";
Запрос.УстановитьПараметр("МассивИНН", МассивИНН);
РезультатЗапроса = Запрос.Выполнить();
Использование оператора В позволяет СУБД оптимизировать поиск по индексу для всех переданных значений сразу, что работает несоизмеримо быстрее циклического перебора.
Если вам нужно не просто получить данные, а совершить сложную обработку или соединить полученный список с другими таблицами базы данных, используйте механизм временных таблиц. Это позволяет выполнить Запрос один раз, сохранив промежуточный результат во временной памяти сервера.
Разберем алгоритм действий:
МенеджерВременныхТаблиц.ПОМЕСТИТЬ ВремТаблицаИНН).ВНУТРЕННЕЕ СОЕДИНЕНИЕ основной таблицы с вашей временной таблицей.Хотя мы стремимся к пакетной обработке, существуют ситуации, когда запрос в цикле остается единственным рабочим вариантом:
HTTPЗапрос от внешнего сервиса, который не умеет принимать списки (как показано в примере с ЗаписатьJSON в исходной теме), вам придется опрашивать его по очереди.Чтобы ваша обработка работала быстро, всегда следуйте золотому правилу: выносите запросы из циклов. Если вы заметили, что кнопка «нажать и заполнить всё» вызывает у вас желание написать Цикл...КонецЦикла с запросом внутри, остановитесь и задайте себе вопрос: «Можно ли передать все условия в этот запрос сразу?». В 99% случаев ответ — «Да».
Используйте массивы, операторы В, МенеджерВременныхТаблиц и пакетные запросы. Это сделает ваш код профессиональным, а работу пользователей — комфортной и быстрой.