Как найти помеченные на удаление объекты справочника и связанные с ними документы в 1С?

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

При подготовке информационной базы к удалению помеченных объектов или проведении аудита данных часто требуется сформировать отчет, показывающий не только сами помеченные на удаление элементы справочника (например, номенклатуру или основные средства), но и документы, в которых эти элементы задействованы. Простым запросом к таблице справочника с отбором по реквизиту ПометкаУдаления = ИСТИНА можно получить только перечень самих элементов. Чтобы выяснить, какие документы блокируют их окончательное удаление, требуется связать эти данные с метаданными конфигурации.

Разберем основные способы решения этой задачи: использование встроенного метода платформы НайтиПоСсылкам, применение готовых процедур Библиотеки стандартных подсистем (БСП), а также построение прямого запроса к конкретным таблицам документов.

Способ 1. Использование платформенного метода НайтиПоСсылкам

Наиболее универсальным инструментом платформы является метод НайтиПоСсылкам. Он позволяет проверить наличие ссылок на заданные объекты во всех таблицах базы данных или в строго определенной области поиска.

Разберем по шагам алгоритм реализации:

  1. Выбираем запросом все помеченные на удаление элементы требуемого справочника и выгружаем их ссылки в массив.
  2. Формируем область поиска (необязательно, но крайне рекомендуется для повышения производительности). Если нам нужны только документы, передаем во второй параметр метода массив объектов метаданных документов.
  3. Вызываем метод НайтиПоСсылкам, который возвращает таблицу значений с результатами поиска.

Посмотрим на пример программного кода:


// Шаг 1. Получаем массив помеченных на удаление элементов
Запрос = Новый Запрос;
Запрос.Текст = 
    "ВЫБРАТЬ
    |	Номенклатура.Ссылка КАК Ссылка
    |ИЗ
    |	Справочник.Номенклатура КАК Номенклатура
    |ГДЕ
    |	Номенклатура.ПометкаУдаления = ИСТИНА";

МассивСсылок = Запрос.Выполнить().Выгрузить().ВыгрузитьКолонку("Ссылка");

Если МассивСсылок.Количество() = 0 Тогда
    Возврат;
КонецЕсли;

// Шаг 2. Ограничиваем область поиска только документами конфигурации
ОбластьПоиска = Новый Массив;
Для Каждого МетаданноеДокумент Из Метаданные.Документы Цикл
    ОбластьПоиска.Добавить(МетаданноеДокумент);
КонецЦикла;

// Шаг 3. Выполняем поиск ссылок
ТаблицаСсылок = НайтиПоСсылкам(МассивСсылок, ОбластьПоиска);

// Обрабатываем результат
Для Каждого Стр Из ТаблицаСсылок Цикл
    ЭлементСправочника = Стр.ИсходныеДанные; // Помеченный элемент
    ДокументСсылка     = Стр.Данные;          // Документ, где найдена ссылка
    ИмяМетаданных      = Стр.Метаданные.Имя;  // Имя объекта метаданных
КонецЦикла;

Возвращаемая таблица значений всегда содержит три стандартные колонки:

  1. ИсходныеДанные — проверяемый помеченный элемент;
  2. Данные — конкретная ссылка на найденный документ;
  3. Метаданные — объект описания метаданных найденного документа (ОбъектМетаданных).

Оптимизация производительности и нюансы поиска

Проанализируем важные технические особенности, которые следует учитывать при вызове метода НайтиПоСсылкам:

  1. Ограничение области поиска. Если не передавать второй параметр ОбластьПоиска, платформа будет сканировать абсолютно все таблицы базы данных: регистры сведений, регистры накопления, планы видов характеристик и периодические реквизиты. На рабочих базах это вызовет длительные блокировки и чрезмерную нагрузку на СУБД. Ограничение списка до конкретных документов значительно ускоряет работу.
  2. Порционная обработка. Если помеченных элементов много (сотни или тысячи), передавать их в метод одним списком нельзя. Рекомендуется разбивать исходный массив на пачки по 50–100 элементов и выполнять поиск циклически.
  3. Ограничение прав на уровне записей (RLS). При выполнении метода от имени пользователя с ограниченными правами платформа вернет только те документы, на чтение которых у него есть права. Для формирования административного отчета вызов метода следует выполнять в привилегированном режиме с помощью вызова УстановитьПривилегированныйРежим(Истина).

Способ 2. Использование функций Библиотеки стандартных подсистем (БСП)

Если конфигурация разработана на базе БСП, мы можем воспользоваться встроенными механизмами общего назначения. В модуле ОбщегоНазначения предусмотрены готовые функции, которые оптимизированы для пакетной работы и автоматически учитывают исключаемые объекты метаданных.

Посмотрим на пример вызова:


// Получаем массив ссылок на помеченные элементы
МассивСсылок = Новый Массив;
// ... заполнение массива ссылками ...

ТаблицаРезультатов = ОбщегоНазначения.НайтиСсылкиНаОбъекты(МассивСсылок);

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

Способ 3. Прямой запрос к табличным частям известных документов

В ситуациях, когда требуется получить отчет только по ограниченному списку ключевых документов (например, только по документам поступления и реализации), оправдано использование прямого запроса. Это работает быстрее динамического поиска ссылок, так как СУБД использует существующие индексы табличных частей.

Рассмотрим структуру такого запроса:


ВЫБРАТЬ
	ТоварыНа Складе.Номенклатура КАК Номенклатура,
	ТоварыНа Складе.Ссылка КАК ДокументСсылка,
	"Поступление товаров и услуг" КАК ВидДокумента
ИЗ
	Документ.ПоступлениеТоваровУслуг.Товары КАК ТоварыНа Складе
ГДЕ
	ТоварыНа Складе.Номенклатура.ПометкаУдаления = ИСТИНА

ОБЪЕДИНИТЬ ВСЕ

ВЫБРАТЬ
	РеализацияТовары.Номенклатура,
	РеализацияТовары.Ссылка,
	"Реализация товаров и услуг"
ИЗ
	Документ.РеализацияТоваровУслуг.Товары КАК РеализацияТовары
ГДЕ
	РеализацияТовары.Номенклатура.ПометкаУдаления = ИСТИНА

Такой запрос можно использовать напрямую в схеме компоновки данных (СКД) без написания программного кода выгрузки в промежуточные таблицы значений.

Вывод результатов в отчет на СКД

Если отчет строится на базе СКД с использованием первого метода (НайтиПоСсылкам), напрямую написать вызов метода в тексте запроса схемы нельзя. В таком случае в схеме компоновки данных создается Набор данных - объект с именем (например, ТаблицаСвязей), а сама таблица значений формируется программно в модуле отчета в событии ПриКомпоновкеРезультата и передается во внешний набор процессора компоновки.

← На главную