В процессе эксплуатации систем на базе 1С, особенно таких крупных, как УПП (Управление производственным предприятием), часто возникают ситуации, когда в регистрах накопления появляются «битые» записи — движения с незаполненным измерением Организация. Это может произойти из-за ошибок в коде доработок, некорректного использования документа Корректировка записей регистров или принудительной очистки реквизитов. Рассмотрим подробно, как решить эту задачу программно и с помощью специализированных инструментов.
Для начала проанализируем, как правильно определить список регистров, которые содержат измерение Организация. Распространенной ошибкой начинающих разработчиков является попытка использовать метод Содержит() непосредственно к коллекции метаданных измерений. Как было замечено в обсуждении, код типа Регистр.Измерения.Содержит(Метаданные.Справочники.Организации) вернет ложь.
Выясним причину: метод Содержит() проверяет наличие конкретного объекта метаданных (самого измерения) в коллекции, а не тип данных, который это измерение может принимать. Для корректного поиска нам необходимо анализировать описание типов каждого измерения.
Рассмотрим правильный алгоритм обхода метаданных:
Для Каждого МенеджерРегистра Из Метаданные.РегистрыНакопления Цикл
Для Каждого Измерение Из МенеджерРегистра.Измерения Цикл
Если Измерение.Тип.СодержитТип(Тип("СправочникСсылка.Организации")) Тогда
// Мы нашли нужный регистр и имя измерения (оно может называться не Организация, а например, Фирма)
Сообщить("Регистр: " + МенеджерРегистра.Имя + ", Измерение: " + Измерение.Имя);
КонецЕсли;
КонецЦикла;
КонецЦикла;
Просто удалить записи из таблиц базы данных напрямую через 1С невозможно (кроме использования Direct SQL, что крайне опасно). Правильный путь — работа с объектом НаборЗаписей. Разберем по шагам процесс очистки для конкретного регистра:
РегистрНакопленияНаборЗаписей с отбором по этому регистратору.ТаблицаЗначений, удаляем строки, где организация пустая, и записываем набор обратно в базу.Рассмотрим пример кода для обработки одного регистра:
Процедура ОчиститьДвиженияПоРегистру(ИмяРегистра, ИмяИзмерения)
Запрос = Новый Запрос;
Запрос.Текст = "ВЫБРАТЬ РАЗЛИЧНЫЕ Регистратор ИЗ РегистрНакопления." + ИмяРегистра + " ГДЕ " + ИмяИзмерения + " = ЗНАЧЕНИЕ(Справочник.Организации.ПустаяСсылка)";
Результат = Запрос.Выполнить();
Выборка = Результат.Выбрать();
Пока Выборка.Следующий() Цикл
Набор = РегистрыНакопления[ИмяРегистра].СоздатьНаборЗаписей();
Набор.Отбор.Регистратор.Установить(Выборка.Регистратор);
Набор.Прочитать();
ТЗ = Набор.Выгрузить();
// Удаляем строки с пустой организацией
ПараметрыОтбора = Новый Структура(ИмяИзмерения, Справочники.Организации.ПустаяСсылка());
СтрокиДляУдаления = ТЗ.НайтиСтроки(ПараметрыОтбора);
Для Каждого СтрокаТЗ Из СтрокиДляУдаления Цикл
ТЗ.Удалить(СтрокаТЗ);
КонецЦикла;
Набор.Загрузить(ТЗ);
Набор.Записать(Истина); // Флаг Истина важен для замещения существующих записей
КонецЦикла;
КонецПроцедуры
В случае с конфигурацией УПП, основной объем таких записей часто генерируется документами ручного ввода — Корректировка записей регистров. Проанализируем важный нюанс: этот документ может содержать движения сразу по десяти разным регистрам.
Если мы просто очистим движения по одному регистру, документ останется в базе. Если после нашей чистки у документа вообще не осталось движений ни по одному регистру (он стал «пустым»), его целесообразно пометить на удаление. Однако будьте осторожны: проверяйте табличную часть ТаблицаРегистров в самом документе, чтобы убедиться, что он действительно больше не нужен.
Если задача разовая и писать сложную обработку нет желания, профессиональное сообщество рекомендует использовать Инструменты разработчика (автор @TormozIt). Это мощный комплекс, который позволяет выполнять групповые операции над данными гораздо быстрее.
Посмотрим, как решить задачу через консоль запросов ИР:
Это экономит время на отладку кода обхода метаданных и обработку исключительных ситуаций (например, когда объект заблокирован другим пользователем).
Важно: Любое массовое удаление записей из регистров накопления — это деструктивная операция. Перед выполнением обязательно проанализируйте следующие моменты:
Таким образом, мы рассмотрели как программный подход к очистке метаданных с использованием ОписаниеТипов и НаборЗаписей, так и возможность использования готовых инструментов, что является более предпочтительным для сложных конфигураций вроде УПП.