Разработка и Конфигурация · 9 мин
1С: как выразить значение как ссылку
Как в 1С выразить значение как ссылку: функция ССЫЛКА в запросах, ПолучитьСсылку по GUID, ЗначениеВСтрокуВнутр. Примеры кода, ошибки и проверка результата.
Задача «выразить как ссылку» возникает у разработчика 1С в двух разных ситуациях. Первая — в языке запросов, когда нужно привести поле составного типа к конкретному типу ссылки оператором ВЫРАЗИТЬ. Вторая — в коде на встроенном языке, когда из строки (обычно GUID) требуется получить объект ссылочного типа, чтобы обратиться к реквизитам элемента справочника или документа.
Обе задачи решаются штатными средствами платформы, но у каждой есть ограничения: оператор ВЫРАЗИТЬ работает только внутри запроса, а получение ссылки по строковому представлению зависит от формата, в котором хранится идентификатор. Ниже разобраны оба подхода с примерами кода, способами проверки результата и типичными ошибками.
Что означает «выразить как ссылку» в 1С
Ссылка в 1С — это не адрес и не строка, а значение специального типа: СправочникСсылка, ДокументСсылка, ПеречислениеСсылка и так далее. Ссылка указывает на конкретный объект базы данных и позволяет обращаться к его реквизитам «через точку» без получения всего объекта.
Выразить значение как ссылку означает сообщить платформе: «трактуй это значение как ссылку конкретного типа». В запросе это нужно для работы с полями составного типа и оптимизации соединений. В коде — для восстановления ссылки из строки, полученной из обмена, файла или внешней системы.
Оператор ВЫРАЗИТЬ в запросе
Основной инструмент приведения типа в языке запросов — конструкция ВЫРАЗИТЬ(Выражение КАК Тип). Если поле имеет составной тип (например, «СправочникСсылка.Номенклатура, СправочникСсылка.Контрагенты»), приведение к одному типу позволяет обращаться к реквизитам этого справочника без дополнительных соединений.
ВЫБРАТЬ
ВЫРАЗИТЬ(Регистр.Получатель КАК Справочник.Контрагенты).ИНН КАК ИНН
ИЗ
РегистрСведений.ОтветственныеЛица КАК Регистр
Если значение поля на самом деле ссылается на другой тип (не Контрагенты), результат приведения будет NULL. Это нормальное поведение, его удобно использовать для фильтрации: условие ГДЕ ВЫРАЗИТЬ(Поле КАК Справочник.Контрагенты) НЕ ЕСТЬ NULL отберёт только записи нужного типа.
Зачем приводить тип даже когда тип единственный
Даже при единственном типе поля приведение через ВЫРАЗИТЬ иногда ускоряет запрос: СУБД получает точный тип и может строить более эффективный план. Кроме того, приведение обязательно, когда значение приходит из параметра составного типа или из таблицы значений, переданной во временную таблицу, — иначе обращение к реквизитам через точку вызовет ошибку «Поле не найдено».
Функция ССЫЛКА и параметры запроса
Когда нужно сравнить поле составного типа с конкретным значением, часто достаточно передать ссылку параметром запроса: Запрос.УстановитьПараметр("Номенклатура", СсылкаНаЭлемент). Платформа сама сопоставит типы. Явное приведение в тексте запроса требуется, если параметр имеет составной тип или вы сравниваете с полем, тип которого шире.
В конструкторе запросов приведение добавляется через контекстное меню поля — пункт «Произвольное выражение», где вручную пишется ВЫРАЗИТЬ(... КАК Справочник.Имя). Имя справочника указывается так, как оно задано в конфигураторе, с учётом регистра букв не требуется.
Получение ссылки из строки GUID в коде
Самая частая прикладная задача вне запросов — восстановить ссылку из строки вида «8a1b2c3d-...», полученной из файла обмена, веб-сервиса или поля «Ссылка» в XML. Для этого используется связка из двух вызовов: конструктор УникальныйИдентификатор из строки и метод ПолучитьСсылку менеджера объекта.
СтрокаGUID = "8a1b2c3d-4e5f-6789-abcd-ef0123456789";
Ид = Новый УникальныйИдентификатор(СтрокаGUID);
СсылкаНаТовар = Справочники.Номенклатура.ПолучитьСсылку(Ид);
Метод ПолучитьСсылку не обращается к базе для проверки существования объекта — он просто формирует значение ссылочного типа с заданным идентификатором. Поэтому после него обязательна проверка: если объекта с таким GUID нет, ссылка будет «битой».
- 1Проверьте, что строка соответствует формату GUID (36 символов с дефисами)
- 2Создайте идентификатор: Новый УникальныйИдентификатор(Строка)
- 3Получите ссылку: МенеджерОбъекта.ПолучитьСсылку(Ид)
- 4Проверьте существование: Ссылка.ПолучитьОбъект() <> Неопределено или запросом по ссылке
- 5Только после проверки используйте ссылку в записях и документах
Проверка результата и битые ссылки
Ссылка, полученная по GUID, может указывать на удалённый или никогда не существовавший объект. Признак битой ссылки — строковое представление вида «<Объект не найден> (8a1:...)». Обращение к реквизитам такой ссылки через точку вернёт значения по умолчанию или вызовет ошибку в зависимости от контекста.
Надёжный способ проверки — функция ОбщегоНазначения.СсылкаСуществует (в конфигурациях на БСП) или собственная проверка запросом: ВЫБРАТЬ ПЕРВЫЕ 1 ИСТИНА ИЗ Справочник.Номенклатура ГДЕ Ссылка = &Ссылка. Вариант с ПолучитьОбъект() тоже рабочий, но медленнее, так как читает весь объект.
Как проверить результат
Показывается наименование или код объекта
Текст вида <Объект не найден> (GUID)
Запрос возвращает одну строку
Пустой результат — объекта нет в базе
Возвращается реальное значение реквизита
Значения по умолчанию или ошибка
Альтернативные способы и их ограничения
Функции ЗначениеВСтрокуВнутр и ЗначениеИзСтрокиВнутр сериализуют значение во внутренний формат платформы. Это удобно для переноса между базами на идентичных конфигурациях, но формат недокументирован и может меняться между версиями платформы, поэтому для долгосрочного хранения и обмена с внешними системами он не подходит.
Другой вариант — поиск объекта по реквизиту (коду, наименованию, внешнему идентификатору) методом НайтиПоКоду или НайтиПоРеквизиту. Он безопаснее при обмене с системами, где GUID не гарантирован, но требует уникальности искомого реквизита.
Сравнение способов получения ссылки
Быстро и точно, если GUID известен. Не проверяет существование объекта — нужна отдельная проверка.
Подходит при обмене без GUID. Требует уникальности реквизита и обращается к базе.
Только для обмена между базами на одной версии платформы. Формат не документирован.
Приведение типа внутри запроса, а не преобразование строки. Работает только со значениями ссылочного типа.
Типичные ошибки и риски
Частая ошибка — передача в ПолучитьСсылку строки не в формате GUID: конструктор УникальныйИдентификатор выдаст исключение, которое прервёт обработку, если она не обёрнута в Попытка/Исключение. Вторая ошибка — запись «битой» ссылки в реквизиты документов без проверки: такие записи потом ломают отчёты и обмены.
Также нельзя путать ВЫРАЗИТЬ с реальным преобразованием: попытка привести строковое поле к ссылочному типу в запросе не создаст ссылку, а даст NULL или ошибку на этапе исполнения. Преобразование строки в ссылку возможно только в коде встроенного языка.
FAQ
Можно ли получить ссылку из представления вида «Номенклатура 00-000001»?
Нет, строковое представление не предназначено для обратного преобразования. Нужен либо GUID объекта, либо поиск по реквизиту — например, НайтиПоКоду("00-000001") для справочника с кодом такого формата.
Чем ПолучитьСсылку отличается от НайтиПоСсылке?
ПолучитьСсылку формирует значение ссылки по GUID без обращения к данным объекта. Поиска «НайтиПоСсылке» как метода менеджера нет — существование проверяют запросом или через ПолучитьОбъект() с сравнением результата с Неопределено.
Как выразить как ссылку поле в СКД?
В схеме компоновки данных приведение делается в тексте запроса набора данных тем же оператором ВЫРАЗИТЬ(Поле КАК Справочник.Имя). В выражениях вычисляемых полей СКД язык запросов не используется, и приведение там недоступно.
Почему ВЫРАЗИТЬ возвращает NULL, хотя поле заполнено?
Значение поля относится к другому типу, чем указано в приведении. Например, поле хранит ссылку на справочник «Контрагенты», а вы приводите к «Номенклатура». Проверьте фактический тип значения функцией ТипЗнч() в коде или через ТИПЗНАЧЕНИЯ в запросе.
Безопасно ли хранить GUID объектов во внешней системе?
Да, GUID объекта неизменен в течение его жизни и сохраняется при обменах через планы обмена. Учтите только, что при загрузке данных в новую пустую базу без синхронизации по GUID идентификаторы будут сгенерированы заново.
Что важно запомнить
В запросе тип приводят оператором ВЫРАЗИТЬ(Поле КАК Тип) — он работает только со значениями ссылочного типа. Строку-GUID в ссылку преобразуют связкой Новый УникальныйИдентификатор + ПолучитьСсылку, и результат обязательно проверяют на существование объекта, чтобы не записать в базу битые ссылки.