Как исправить ошибку уникальности и перенумеровать справочник в 1С?

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

Каждый разработчик и администратор 1С рано или поздно сталкивается с ситуацией, когда пользователи жалуются: «Мы не можем создать новый элемент в справочнике, система выдает ошибку, что код не уникален!». При анализе выясняется, что в справочнике с длиной кода, например, в 9 символов, кто-то вручную ввел короткий код вроде 999 или 2999. Автонумерация платформы сбивается, и работа пользователей парализуется.

В этой статье мы подробно разберем, почему возникает эта проблема, как устроена автонумерация в 1С, и рассмотрим несколько надежных способов исправления ситуации: от быстрого обходного пути до написания правильного скрипта перенумерации и использования готовых инструментов.


Выясняем причину: почему ломается автонумерация?

Для того чтобы успешно решить проблему, нам необходимо понимать технические нюансы работы платформы 1С. Почему один некорректно введенный код ломает автоматическое создание последующих элементов?

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

Если пользователь вручную вводит короткий код без нулей (например, просто 999), встроенный парсер платформы сбивается. Согласно правилам строкового сравнения, строка 999 позиционируется как «большая», чем строка 000000999. При попытке создать следующий элемент автонумерация пытается прибавить единицу к максимальному значению, то есть к 999. Платформа пытается записать код 1000, но так как длина строки ограничена и формат нарушен, система часто зацикливается на попытке повторно выдать код 999 или выходит за рамки разрядности, выдавая ошибку уникальности.


Способ 1. Быстрое решение «в лоб» (Буквенный префикс)

Проанализируем простое и быстрое решение, упомянутое на форуме. Если вам нужно восстановить работоспособность системы прямо сейчас и у вас нет времени на монопольный запуск базы для массовой перенумерации, можно использовать «обходной маневр».

Достаточно вручную создать один новый элемент справочника и присвоить ему код с буквенным префиксом, например: А00000001 (буква «А» и далее цифры до достижения длины в 9 символов). Платформа 1С мгновенно переключится на этот формат. Все последующие элементы будут автоматически создаваться с кодами А00000002, А00000003 и так далее.

Этот способ хорош своей скоростью: не нужно выгонять пользователей из базы и писать обработки. Однако он оставляет «мусор» в старых кодах и не решает проблему системно, если в вашей организации жестко регламентирован формат кодов справочников.


Способ 2. Правильная программная перенумерация (Двойной проход)

Если принято решение навести в базе полный порядок, перенести старые некорректные коды в отдельный текстовый реквизит (например, СтарыйКод), а поле Код перенумеровать заново, нам потребуется написать внешнюю обработку. Написание цикла «в лоб» для перезаписи кодов часто приводит к ошибкам уникальности прямо во время выполнения обработки. Ведь в процессе изменения один элемент неизбежно получит код, который еще принадлежит другому, не измененному элементу.

Рассмотрим правильный алгоритм на встроенном языке 1С, состоящий из трех важных шагов.

  1. Использование режима загрузки данных: Свойство ОбменДанными.Загрузка = Истина принудительно отключает стандартные проверки платформы (включая контроль уникальности кода в момент записи) и блокирует выполнение кода в процедурах ПередЗаписью и ПриЗаписи. Это предотвращает ошибки перезаписи и ускоряет процесс.
  2. Метод «Двойного прохода»: Чтобы гарантированно избежать конфликтов, мы сначала присваиваем всем элементам временные заведомо уникальные коды с префиксом (например, ВР0000001). И только вторым проходом устанавливаем финальные чистые коды с лидирующими нулями.
  3. Сброс кэша нумерации: Метод ОбновитьНумерациюОбъектов() сообщает серверу 1С, что кэш номеров нужно очистить и рассчитать заново на основе актуальных данных в базе.

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


// Шаг 1. Переносим коды во временные, чтобы избежать конфликтов уникальности
Выборка = Справочники.Номенклатура.Выбрать();
Счетчик = 1;
Пока Выборка.Следующий() Цикл
    Объект = Выборка.ПолучитьОбъект();
    
    // Если нужно сохранить старый ручной код, переносим его в новый реквизит справочника
    // Объект.СтарыйКод = Объект.Код; 
    
    // Присваиваем временный код с префиксом "ВР" (дополняем до 9 знаков)
    Объект.Код = "ВР" + Прав("0000000" + Строка(Счетчик), 7);
    
    Объект.ОбменДанными.Загрузка = Истина; // Отключаем платформенные проверки уникальности
    Объект.Записать();
    Счетчик = Счетчик + 1;
КонецЦикла;

// Шаг 2. Записываем финальные правильные последовательные коды
Выборка = Справочники.Номенклатура.Выбрать();
Счетчик = 1;
Пока Выборка.Следующий() Цикл
    Объект = Выборка.ПолучитьОбъект();
    
    // Форматируем число в строку длиной 9 символов с лидирующими нулями
    // Параметр "ЧГ=" убирает разделение групп разрядов (чтобы не было пробелов в числах больше 1000)
    Объект.Код = Формат(Счетчик, "ЧЦ=9; ЧГ="); 
    
    Объект.ОбменДанными.Загрузка = Истина;
    Объект.Записать();
    Счетчик = Счетчик + 1;
КонецЦикла;

// Шаг 3. Сбрасываем кэш автонумерации на сервере 1С для нашего справочника
ОбновитьНумерациюОбъектов(Метаданные.Справочники.Номенклатура);

Этот код гарантирует, что все элементы справочника получат красивые, последовательные коды вида 000000001, 000000002 и так далее, а механизм автонумерации 1С будет работать корректно.


Способ 3. Использование готовых инструментов без программирования

Если вы не хотите писать код с нуля, мы можем воспользоваться стандартными сервисными инструментами, которые уже разработаны фирмой 1С.

Внешняя обработка «Универсальные подбор и обработка объектов»

Данная утилита доступна для скачивания на портале ИТС. В ней присутствует встроенный режим под названием «Перенумерация объектов». Данный инструмент берет на себя все заботы по бесконфликтной перезаписи кодов: он автоматически выполнит двухпроходное переименование, предложит вам задать префикс, начальный номер и длину кода, а также корректно обновит кэш автонумерации на сервере.

Стандартная обработка «Групповое изменение реквизитов»

Этот инструмент встроен практически во все современные конфигурации на базе БСП (Библиотеки Стандартных Подсистем). Найти его можно в разделе Администрирование — Обслуживание — Корректировка данных.

По умолчанию поле Код заблокировано для редактирования этой обработкой в целях безопасности. Чтобы обойти это ограничение, выполним следующие шаги:

  1. Откроем обработку «Групповое изменение реквизитов».
  2. В самом низу формы нажмем на ссылку «Дополнительные параметры».
  3. В открывшемся окне перейдем в раздел «Специальные возможности».
  4. Установим флаг «Режим разработчика».

После включения режима разработчика поле Код (или Номер для документов) станет доступным для изменения. Вы сможете запустить произвольный алгоритм изменения кодов для выбранных элементов справочника непосредственно в интерфейсе программы.


Резюме и рекомендации

Мы проанализировали проблему сбившейся автонумерации и нашли несколько путей ее решения. Чтобы избежать повторения подобных ситуаций в будущем, рекомендуем придерживаться простых правил:

← На главную