При миграции информационной базы из файлового варианта в клиент-серверный или при развертывании базы из файла выгрузки .dt администраторы часто сталкиваются с ошибкой HRESULT=80040E2F. Система сообщает о невозможности создания уникального индекса из-за дублирующихся ключей. Рассмотрим подробно, почему это происходит и как устранить проблему, сохранив целостность данных.
Проанализируем текст ошибки, представленный в системном сообщении. В нем указано имя объекта: dbo._AccRgAT2674. Для специалиста 1С это имя является «говорящим»:
_AccRg означает, что данные принадлежат Регистру бухгалтерии (Accounting Register).AT (Aggregates/Totals) указывает на то, что это таблица итогов данного регистра.2674 соответствует внутреннему номеру объекта в конкретной конфигурации.Суть проблемы заключается в том, что в исходной базе (в файле .dt) содержатся записи, которые с точки зрения SQL Server являются идентичными для ключевых полей индекса. При попытке массовой вставки данных (Bulk Insert) SQL Server пытается построить уникальный индекс, но натыкается на дубль и прерывает операцию.
В тексте ошибки часто фигурирует странная дата, например, 4016-12-01. Разберем, откуда она берется. В платформе 1С реализован механизм «смещения дат» (обычно на 2000 лет) для корректной работы с минимальными значениями дат в различных СУБД. Значение в пятом тысячелетии может возникнуть по нескольким причинам:
Поскольку ошибка локализована в таблице итогов (AT), а не в таблице самих движений, самым простым и эффективным способом будет полная очистка и пересчет этих данных. Итоги — это производные данные, которые 1С может восстановить на основании первичных записей регистра. Выполним следующие шаги в исходной базе (до выгрузки в .dt):
_AccRgAT..dt.Если метод с итогами не помог, вероятно, повреждена сама структура таблиц в файле .1CD. Стандартное «Тестирование и исправление» из конфигуратора может не справиться, так как оно работает на логическом уровне. Воспользуемся утилитой chdbfl.exe, которая находится в папке bin установленной платформы.
Рассмотрим порядок действий:
chdbfl.exe.1Cv8.1CD.После завершения работы утилиты следует снова попробовать выполнить выгрузку и загрузку в SQL.
Если база имеет огромный объем и пересчет итогов занимает слишком много времени, можно попытаться найти и удалить конкретную запись-дубль. Для этого нам потребуется написать небольшую обработку, которая проанализирует записи регистра.
Посмотрим на пример логики поиска проблемных записей:
Запрос = Новый Запрос;
Запрос.Текст =
"ВЫБРАТЬ
| Регистр.Период,
| Регистр.Счет,
| Регистр.Организация,
| КОЛИЧЕСТВО(*) КАК КоличествоДублей
|ИЗ
| РегистрБухгалтерии.Хозрасчетный.Итоги КАК Регистр
|СГРУППИРОВАТЬ ПО
| Регистр.Период,
| Регистр.Счет,
| Регистр.Организация
|ИМЕЮЩИЕ
| КОЛИЧЕСТВО(*) > 1";
Результат = Запрос.Выполнить();
Если Не Результат.Пустой() Тогда
Выборка = Результат.Выбрать();
Пока Выборка.Следующий() Цикл
Сообщить("Найден дубль по счету " + Выборка.Счет + " на дату " + Выборка.Период);
КонецЦикла;
КонецЕсли;
Важно помнить, что в уникальный индекс таблицы итогов входит множество полей (субконто, измерения, валюты). В запросе выше приведен упрощенный пример. Чтобы найти точный дубль, нужно добавить в группировку все поля, которые перечислены в ошибке SQL (те самые <NULL> и 0x88d5... в скобках сообщения).
В самых сложных случаях, когда база не открывается ни в режиме Предприятия, ни в режиме Конфигуратора, можно воспользоваться неофициальной утилитой Tool1CD для прямого чтения файла .1CD.
Проанализируем ситуацию по шагам:
Tool1CD._AccRgAT[номер]._Period).Внимание: Прямое редактирование таблиц — это крайняя мера, которая может привести к окончательной порче базы данных. Всегда работайте только с копией!
Как отмечают участники обсуждения, процедура ТиИ часто не решает проблему CREATE UNIQUE INDEX. Это происходит потому, что при установке флага «Реиндексация таблиц» платформа пытается выполнить ту же самую операцию, что и SQL Server при загрузке — создать индекс. Если в данных уже есть дубль, создание индекса прервется с ошибкой еще до того, как ТиИ перейдет к этапу «Проверка логической целостности», на котором теоретически дубли могли быть вычищены.
Для успешного решения проблемы мы рекомендуем начинать с Метода 1 (Отключение и очистка итогов). Это наиболее безопасный и «штатный» способ, который в 90% случаев устраняет ошибки в таблицах _AccRgAT и _AccumRgAT. Если же ошибка возникает в таблицах движений (без суффикса AT), используйте chdbfl.exe и программный поиск дублей по регистратору.