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