Как присвоить полю с типом Ссылка значение NULL в 1С?

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

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

Архитектурные ограничения платформы: почему нельзя просто записать NULL

Для начала проанализируем, как устроена работа со значениями в стандартных базах данных 1С. На уровне СУБД (будь то MS SQL, PostgreSQL или IBM DB2) таблицы для стандартных реквизитов конфигурации (справочников, документов, процессов) создаются платформой с флагом NOT NULL. Это означает жесткий запрет на хранение физического значения NULL в СУБД для штатных объектов конфигурации.

Вместо физического отсутствия данных (коим и является NULL), в 1С применяются фиксированные пустые значения по умолчанию:

  1. Для ссылочных типов данных используется пустая ссылка — уникальный идентификатор, состоящий из нулей: 00000000-0000-0000-0000-000000000000.
  2. Для дат — пустая дата (например, 0001-01-01).
  3. Для числовых полей — значение 0.
  4. Для строковых полей — пустая строка "".

Если мы попытаемся в коде встроенного языка написать конструкцию вида Объект.Реквизит = NULL; для обычного реквизита справочника, система выдаст ошибку несоответствия типов. В метаданных стандартных реквизитов тип NULL попросту отсутствует.

Решение проблемы на уровне управляемой формы

Что же делать, если на форме пользователю необходимо предоставить возможность очистить поле так, чтобы система восприняла это именно как установку значения NULL (например, для последующей отправки во внешнюю систему)?

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

Для этого нам понадобится использовать объект ОписаниеТипов. Мы обратимся к свойству элемента формы ДоступныеТипы и добавим туда системный тип NULL.

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


&НаСервере
Процедура ПриСозданииНаСервере(Отказ, СтандартнаяОбработка)

    // Получаем текущее описание типов элемента формы
    БазовоеОписаниеТипов = Элементы.НоменклатураПоле.ДоступныеТипы;
    
    // Создаем новое описание типов, добавляя к исходным типам "null"
    Элементы.НоменклатураПоле.ДоступныеТипы = Новый ОписаниеТипов(БазовоеОписаниеТипов, "null");

КонецПроцедуры

Благодаря этому коду, в выпадающем списке выбора у пользователя появится возможность очистить поле (нажатием на кнопку очистки «Х»), и элементу формы будет присвоено значение NULL. На форме это значение будет визуально отображаться как пустая строка или текст <Не заполнено>.

В каких сценариях действительно необходим NULL?

Выясним причину, почему разработчики так настойчиво пытаются использовать NULL. Единственным и самым частым сценарием во встроенном языке 1С, где запись физического NULL в базу данных штатно поддерживается и критически необходима, является работа с Внешними источниками данных (ВИД).

При интеграции 1С со сторонними корпоративными базами данных (например, ERP-системами на MS SQL или Oracle, сайтами на MySQL) таблицы сторонних СУБД часто требуют передачи именно физического значения NULL для обозначения пустых или незаполненных внешних ключей. Попытка передать туда Неопределено или пустую ссылку 1С приведет к ошибке СУБД или некорректной записи данных.

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

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

Посмотрим на пример записи новой строки во внешний источник данных:


НоваяЗапись = ВнешниеИсточникиДанных.ВнешняяБД.Таблицы.Контрагенты.СоздатьНаборЗаписей();
НоваяСтрока = НоваяЗапись.Добавить();
НоваяСтрока.Код = "001";
НоваяСтрока.Наименование = "ООО Ромашка";

// Если у контрагента нет холдинга, записываем строго NULL во внешнюю СУБД
Если ХолдингНеВыбран Тогда
    НоваяСтрока.ИдентификаторРодителя = NULL;
Иначе
    НоваяСтрока.ИдентификаторРодителя = ВыбранныйХолдингКод;
КонецЕсли;

НоваяЗапись.Записать();

Обход автоматической подмены NULL на форме

Проанализируем еще одну проблему: часто при редактировании данных внешних источников через стандартные формы 1С пытается автоматически подменить NULL на значение по умолчанию для соответствующего типа (например, на пустую строку или число 0).

Чтобы предотвратить это поведение и гарантировать запись NULL во внешнюю СУБД, используйте обработчик события формы ПередЗаписьюНаСервере. Мы можем принудительно перехватить пустое значение и заменить его обратно на NULL перед фиксацией транзакции:


&НаСервере
Процедура ПередЗаписьюНаСервере(Отказ, ТекущийОбъект, ПараметрыЗаписи)

    // Проверяем, если поле заполнено пустой ссылкой внешнего источника, заменяем его на NULL
    Если ТекущийОбъект.ВнешнееПоле = ВнешниеИсточникиДанных.ВнешняяБД.Таблицы.Справочник.ПустаяСсылка() Тогда
        ТекущийОбъект.ВнешнееПоле = NULL;
    КонецЕсли;

КонецПроцедуры

Такой же подход применяется при работе с датами. По умолчанию незаполненная дата в 1С транслируется в MS SQL как минимальная дата (например, 1753-01-01). Если внешняя база данных ожидает реальный NULL в поле даты, явное присвоение NULL перед записью полностью решает эту задачу.

Ошибки СУБД: появление NULL в стандартных таблицах 1С

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

В такой ситуации вы столкнетесь со следующими симптомами:

Для исправления таких критических ошибок используйте штатную утилиту «Тестирование и исправление информационной базы» (ТИС) в режиме Конфигуратора, выбрав пункты проверки логической и ссылочной целостности с включенной опцией очистки неверных значений. В особо сложных случаях администраторам баз данных приходится выполнять прямой SQL-запрос для замены ошибочных NULL на пустые ссылки.

Разница между NULL и Неопределено при сериализации в JSON

При разработке интеграционных механизмов (веб-сервисы, REST API) важно помнить разницу между системными типами 1С при сериализации данных в формат JSON.

Хотя в формате JSON существует стандартное значение null, попытка сериализовать системный тип 1С NULL напрямую через функцию ЗаписатьJSON может привести к ошибке преобразования типов или выгрузке нежелательного текстового представления. В 1С аналогом null для корректной JSON-сериализации выступает значение Неопределено. Перед отправкой данных во внешние веб-сервисы всегда заменяйте системные значения NULL (полученные, например, из запросов или внешних источников) на Неопределено.

← На главную