В процессе разработки на платформе 1С:Предприятие 8 программисты часто сталкиваются с ситуацией, когда при программном создании нового элемента справочника или документа метод ПолучитьСсылку() возвращает результат, который в отладчике выглядит как «Объект не найден» с последующим набором символов (GUID). На первый взгляд это кажется ошибкой, свидетельствующей о нарушении целостности базы данных или некорректной работе кода. Однако в большинстве случаев это штатное поведение платформы.
В этой статье мы подробно разберем, почему так происходит, как платформа 1С работает с идентификаторами и что нужно сделать, чтобы получить корректное представление объекта. Мы проанализируем внутренние механизмы формирования ссылок и выясним, когда стоит беспокоиться, а когда — продолжать работу.
Рассмотрим ситуацию, когда мы создаем новый объект программно. Платформа 1С позволяет получить ссылку на объект еще до того, как он будет физически записан в таблицу базы данных. Это делается с помощью метода ПолучитьСсылку() для менеджера справочника или метода ПолучитьСсылкуНового() для самого объекта.
Выясним причину появления надписи «Объект не найден». Когда мы выполняем следующий код:
НовыйКонтрагент = Справочники.Контрагенты.СоздатьЭлемент();
НоваяСсылка = Справочники.Контрагенты.ПолучитьСсылку();
НовыйКонтрагент.УстановитьСсылкуНового(НоваяСсылка);
В переменной НоваяСсылка уже содержится уникальный идентификатор (GUID). Однако 1С — это объектно-ориентированная система, где у каждой ссылки есть «представление» (обычно это Наименование или Код). Когда отладчик пытается показать вам значение переменной, он обращается к базе данных, чтобы найти текстовое описание этого GUID. Поскольку команда Записать() еще не была выполнена, в базе данных записи с таким идентификатором нет. Система честно сообщает: «Объект не найден», так как она не может найти поля, из которых строится строковое представление.
Важно понимать: сама ссылка при этом является валидной и не пустой. Проверка НоваяСсылка.Пустая() вернет Ложь.
Самый простой и логичный способ избавиться от этого статуса — физически создать запись в базе данных. Проанализируем, как изменится состояние ссылки после записи:
НовыйКонтрагент = Справочники.Контрагенты.СоздатьЭлемент();
НовыйКонтрагент.Наименование = "ООО Ромашка";
// На данный момент ПолучитьСсылкуНового() вернет "Объект не найден"
НовыйКонтрагент.Записать();
// Теперь та же самая ссылка будет отображаться как "ООО Ромашка"
Разберем по шагам, что произошло: после вызова метода Записать() платформа создала строку в таблице Справочник.Контрагенты. Теперь, когда отладчик или интерфейс обращается к ссылке, механизм получения представления находит запись по GUID и извлекает наименование.
Бывают случаи, когда объект в базе точно существует, но метод все равно возвращает «Объект не найден». Рассмотрим ситуацию, когда под полными правами всё работает корректно, а под правами обычного пользователя — нет. Здесь в игру вступает механизм RLS (Row Level Security).
Проанализируем работу системы под ограничениями:
Чтение, но и право Просмотр.В этом случае необходимо проверить настройки ролей в конфигураторе и убедиться, что у пользователя достаточно прав на чтение полей, входящих в представление объекта.
Часто программисты пытаются использовать ссылку, полученную через ПолучитьСсылку(), в запросах до записи объекта. Посмотрим на пример типичной ошибки:
БудущаяСсылка = Справочники.Контрагенты.ПолучитьСсылку();
// Объект еще не записан
Запрос = Новый Запрос;
Запрос.Текст = "ВЫБРАТЬ Ссылка ИЗ Справочник.Контрагенты ГДЕ Ссылка = &Ссылка";
Запрос.УстановитьПараметр("Ссылка", БудущаяСсылка);
Результат = Запрос.Выполнить();
// Результат будет пустым
Выясним, почему это происходит. Несмотря на то, что переменная БудущаяСсылка содержит уникальный GUID, в таблице базы данных физически нет такой строки. Запрос ищет данные на диске (в СУБД), а не в оперативной памяти. Поэтому, пока не вызван метод Записать(), такая ссылка бесполезна для использования в условиях запросов ГДЕ или соединениях таблиц.
Рассмотрим несколько советов, которые помогут правильно работать с такими ссылками:
Ссылка.ПолучитьОбъект(). Если метод вернул Неопределено, значит, объекта действительно нет в базе данных.ПолучитьСсылку(Новый УникальныйИдентификатор()) позволяет заранее предсказать, какой будет ссылка у объекта. Это удобно при обмене данными, когда нужно зарезервировать ID до момента загрузки всех реквизитов.Подведем итог: статус «Объект не найден» при выполнении ПолучитьСсылку() — это не баг, а фича отладчика 1С, который честно говорит нам о том, что данных в БД еще нет, хотя идентификатор уже зарезервирован в памяти. Понимание этого механизма позволяет избежать лишних проверок и писать более эффективный код для создания связанных цепочек документов и справочников.