Как удалить битые записи из регистра накопления?

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

В процессе работы или разработки в 1С можно столкнуться с ситуацией, когда в регистре накопления или расчета образуются зависшие записи, у которых в поле Регистратор содержится битая ссылка (в интерфейсе отображается как <Объект не найден>). Подобные «записи-сироты» нарушают целостность данных и могут вызывать ошибки при формировании отчетов или проведении документов.

Разберем причины возникновения этой проблемы, научимся правильно находить битые ссылки в запросах и рассмотрим эффективные программные методы их удаления без долговременного полного тестирования и исправления базы данных.

Почему возникают битые ссылки в регистрах?

Проанализируем основные причины появления движений без существующего документа-регистратора:

  1. Прямое удаление объектов: программный вызов метода Удалить() для документа вместо пометки на удаление без контроля ссылочной целостности.
  2. Ошибки обмена данными: при синхронизации через РИБ или EnterpriseData наборы записей передаются в целевую базу, а сам документ-регистратор не загружается из-за правил фильтрации.
  3. Запись с отключенными проверками: программная запись движения с установленным флагом ОбменДанными.Загрузка = Истина в момент, когда объекта регистратора еще нет в базе.
  4. Изменение конфигурации: снятие флага регистратора у документа в составе регистра без предварительной очистки существующих движений.

Как правильно найти битые ссылки в запросе 1С

Обратим внимание на важную особенность платформы 1С: битая ссылка хранит реальный уникальный идентификатор (GUID). По этой причине метод Пустая() для неё возвращает Ложь, а привычная проверка Регистратор.Ссылка ЕСТЬ NULL в языке запросов не работает, так как само поле Ссылка хранит записанный GUID и не равно NULL.

Чтобы отфильтровать битые ссылки в запросе, необходимо обращаться к реквизитам документа-регистратора. Если объект физически отсутствует в таблице документов, обращение к его реквизитам вернет NULL. Проанализируем пример запроса:


ВЫБРАТЬ РАЗЛИЧНЫЕ
	ТаблицаРегистра.Регистратор КАК БитаяСсылка
ИЗ
	РегистрНакопления.Продажи КАК ТаблицаРегистра
ГДЕ
	ВЫРАЗИТЬ(ТаблицаРегистра.Регистратор КАК Документ.ПродажаТоваров).Номер ЕСТЬ NULL
	И НЕ ТаблицаРегистра.Регистратор = ЗНАЧЕНИЕ(Документ.ПродажаТоваров.ПустаяСсылка)

Также в программном коде при обходе записей проверить ссылку на целостность можно следующим способом:


Если СсылкаНаРегистратор.ПолучитьОбъект() = Неопределено Тогда
	// Объект не найден в базе данных — ссылка битая
КонецЕсли;

Быстрое удаление битых записей через набор записей

Наиболее оперативный способ очистки битых движений без проведения или создания документов-заглушек — использование объекта НаборЗаписей. Битая ссылка является полноценным значением типа ссылки, поэтому её можно передавать в отбор набора записей.

Разберем по шагам алгоритм удаления таких записей:

  1. Сформируем список битых ссылок с помощью запроса или проверки ПолучитьОбъект() = Неопределено.
  2. Для каждой битой ссылки создадим набор записей регистра с соответствующим отбором по регистратору.
  3. Очистим набор и запишем его в базу данных.

Рассмотрим пример программного кода для очистки регистра накопления:


// МассивБитыхСсылок содержит найденные ссылки <Объект не найден>
Для Каждого БитаяСсылка Из МассивБитыхСсылок Цикл

	Набор = РегистрыНакопления.Продажи.СоздатьНаборЗаписей();
	Набор.Отбор.Регистратор.Установить(БитаяСсылка);
	
	// Включаем режим загрузки данных для обхода прикладных проверок
	Набор.ОбменДанными.Загрузка = Истина;
	
	// Очищаем набор и записываем (пустой набор перезапишет существующие движения)
	Набор.Очистить();
	Набор.Записать(Истина);

КонецЦикла;

Данный подход одинаково эффективно работает как для регистров накопления, так и для регистров сведений, бухгалтерии и расчета.

Альтернативные варианты решения

В зависимости от требований задачи рассмотрим еще два подходу к устранению проблемы:

  1. Точечное «Тестирование и исправление» (ТИИ): если нет времени на выполнение полной проверки всей базы данных, можно снять все флаги в утилите ТИИ и оставить только пункт «Проверка логической целостности» с выбранной опцией «Очищать ссылки» (для удаления зависших записей) или «Создавать объекты» (для создания документов-заглушек). Точечная проверка выполнится существенно быстрее полной.
  2. Восстановление документа с сохранением движений: если движения регистра необходимо сохранить, можно программно восстановить документ-регистратор с тем же GUID, используя метод УстановитьСсылкуНового():
    
    GUID = БитаяСсылка.УникальныйИдентификатор();
    НовыйДокумент = Документы.ПродажаТоваров.СоздатьДокумент();
    НовыйДокумент.УстановитьСсылкуНового(Документы.ПродажаТоваров.ПолучитьСсылку(GUID));
    НовыйДокумент.Записать();
    
    После этого битая ссылка превратится в полноценный документ, и движения привяжутся к нему.
← На главную