Как исправить ошибки «Поле объекта не обнаружено (БанковскиеСчетаОрганизаций)» и «Выборка может быть упорядочена только по реквизитам...» в 1С

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

При работе с внешними обработками в среде «1С:Предприятие» разработчики и пользователи часто сталкиваются с ситуацией, когда обработка, идеально выполняющая свои функции в одной конфигурации, наотрез отказывается запускаться в другой. Типичный пример — перенос удобного инструмента для автоматического заполнения шаблонов договоров Word из конфигурации «1С:Управление торговлей 11» (УТ 11) в конфигурацию «1С:Бухгалтерия предприятия 3.0» (БП 3.0).

В этой статье мы подробно разберем, почему возникают ошибки «Поле объекта не обнаружено (БанковскиеСчетаОрганизаций)» и последующая за ней «Выборка может быть упорядочена только по реквизитам, имеющими базовый тип...», проанализируем причины их появления на уровне архитектуры платформы и СУБД, а также рассмотрим практические варианты их устранения.


Часть 1. Разбор и устранение первой ошибки: «Поле объекта не обнаружено (БанковскиеСчетаОрганизаций)»

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

Рассмотрим подробнее разницу в архитектуре хранения данных между УТ 11 и БП 3.0:

  1. Архитектура «1С:Управление торговлей 11» (а также ERP и КА 2): В этих конфигурациях учет банковских счетов разделен на два независимых справочника. Счета нашей собственной компании (организации) хранятся в справочнике БанковскиеСчетаОрганизаций. Счета сторонних контрагентов, клиентов и партнеров находятся в справочнике БанковскиеСчетаКонтрагентов.
  2. Архитектура «1С:Бухгалтерия предприятия 3.0» (включая Базовую версию): В бухгалтерии структура данных максимально упрощена для облегчения ведения учета. Здесь нет разделения на два справочника. Все банковские счета (и наших организаций, и контрагентов) регистрируются в одном едином справочнике — БанковскиеСчета.

Поскольку скачанная внешняя обработка изначально проектировалась под стандарты торговых решений (УТ 11), в ее коде содержатся прямые ссылки на объект Справочники.БанковскиеСчетаОрганизаций. При попытке выполнить этот код в БП 3.0 платформа закономерно сообщает об ошибке.

Пошаговое решение первой проблемы:

Для исправления этой ошибки нам потребуется изменить обращение к справочнику в коде обработки. Выполним следующие действия:

  1. Откроем конфигуратор вашей базы данных «1С:Бухгалтерия предприятия».
  2. Через меню Файл -> Открыть найдем и откроем файл внешней обработки (формат .epf).
  3. Откроем модуль управляемой формы обработки или ее объектный модуль (в зависимости от того, где реализован алгоритм заполнения реквизитов). Для этого нажмем правой кнопкой мыши по корню обработки и выберем Открыть модуль объекта, либо перейдем на вкладку Формы, откроем форму и перейдем на вкладку Модуль.
  4. Используем глобальный поиск по тексту модуля (сочетание клавиш Ctrl + F). Нам нужно найти все вхождения строки БанковскиеСчетаОрганизаций.
  5. Заменим все найденные обращения Справочники.БанковскиеСчетаОрганизаций на корректное для бухгалтерии имя справочника — Справочники.БанковскиеСчета.

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


Часть 2. Разбор и устранение второй ошибки: «Выборка может быть упорядочена только по реквизитам, имеющими базовый тип...»

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

Синтаксис этого метода выглядит следующим образом:

Выборка = Справочники.БанковскиеСчета.Выбрать(Родитель, Владелец, Отбор, Порядок);

В качестве параметра Порядок разработчики часто указывают сортировку, например, по владельцу счета или по какому-то другому реквизиту. Однако платформа 1С накладывает жесткие ограничения на использование параметра Порядок в методе Выбрать():

В справочнике БанковскиеСчета конфигурации БП 3.0 стандартный реквизит Владелец является сложным составным типом (он может ссылаться как на справочник Организации, так и на справочник Контрагенты). Ссылка не является базовым типом, поэтому при попытке отсортировать выборку по полю Владелец платформа на уровне СУБД блокирует операцию и выдает ошибку.

Варианты решения второй проблемы:

Рассмотрим три способа исправления этой ошибки, начиная от самого простого и заканчивая наиболее профессиональным с точки зрения стандартов разработки «1С».

Способ 1. Использование механизма запросов (Рекомендуемый подход)

Самый надежный и быстродействующий способ обойти ограничения метода Выбрать() — заменить его на полноценный Запрос. В языке запросов 1С отсутствуют ограничения на упорядочивание по ссылочным полям. СУБД легко выполнит сортировку по представлению владельца или по его внутреннему идентификатору.

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


// Создаем объект Запрос для получения данных из СУБД
Запрос = Новый Запрос;
Запрос.Текст = 
    "ВЫБРАТЬ
    |	БанковскиеСчета.Ссылка КАК Ссылка,
    |	БанковскиеСчета.Наименование КАК Наименование
    |ИЗ
    |	Справочник.БанковскиеСчета КАК БанковскиеСчета
    |ГДЕ
    |	БанковскиеСчета.Владелец = &Владелец
    |	И НЕ БанковскиеСчета.ПометкаУдаления
    |УПОРЯДОЧИТЬ ПО
    |	Наименование ВОЗР"; // Сортируем по строковому наименованию счета

// Передаем параметр владельца (например, Организацию из реквизитов обработки)
Запрос.УстановитьПараметр("Владелец", Объект.Организация);

РезультатЗапроса = Запрос.Выполнить();
ВыборкаДетальныеЗаписи = РезультатЗапроса.Выбрать();

Пока ВыборкаДетальныеЗаписи.Следующий() Цикл
    // Здесь размещаем логику заполнения шаблона Word
    // Используем ВыборкаДетальныеЗаписи.Ссылка для получения данных счета
КонецЦикла;

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

Способ 2. Отключение сортировки в методе Выбрать()

Если для вывода данных в Word порядок следования банковских счетов не играет роли (например, если у ваших организаций обычно заведен всего один или два расчетных счета), самым простым решением будет полное удаление параметра сортировки из метода Выбрать().

Найдем в коде строку инициализации выборки. Она может выглядеть примерно так:

Выборка = Справочники.БанковскиеСчета.Выбрать( , ВладелецСчетов, , "Владелец");

Изменим ее, полностью удалив четвертый параметр:

Выборка = Справочники.БанковскиеСчета.Выбрать( , ВладелецСчетов);

Платформа вернет элементы в их естественном порядке (по внутреннему идентификатору GUID), не вызывая конфликта типов данных при сортировке.

Способ 3. Выгрузка в Таблицу значений и последующая сортировка

Если вам обязательно нужно отсортировать счета по владельцу или другому ссылочному полю, но переписывать логику под запросы кажется слишком трудоемкой задачей, мы можем применить промежуточную сортировку в оперативной памяти компьютера с помощью объекта ТаблицаЗначений.

Разберем этот метод по шагам на примере кода:


// Получаем выборку без указания сортировки во избежание ошибки
Выборка = Справочники.БанковскиеСчета.Выбрать( , ВладелецСчетов);

// Создаем таблицу значений для накопления данных
ТаблицаСчетов = Новый ТаблицаЗначений;
ТаблицаСчетов.Колонки.Добавить("Ссылка");
ТаблицаСчетов.Колонки.Добавить("Владелец");

// Заполняем таблицу значений данными из выборки
Пока Выборка.Следующий() Цикл
    НоваяСтрока = ТаблицаСчетов.Добавить();
    НоваяСтрока.Ссылка = Выборка.Ссылка;
    НоваяСтрока.Владелец = Выборка.Владелец;
КонецЦикла;

// Сортируем таблицу значений по полю Владелец в памяти приложения
ТаблицаСчетов.Сортировать("Владелец Возр");

// Теперь обходим отсортированную таблицу значений для вывода в Word
Для Каждого СтрокаСчета Из ТаблицаСчетов Цикл
    // Работаем с данными: СтрокаСчета.Ссылка
КонецЦикла;

Данный способ позволяет обойти ограничение СУБД, перекладывая задачу упорядочивания объектов на оперативную память клиентского сеанса 1С.


Подведем итоги

Мы совместно проанализировали причины несовместимости логики внешней обработки при переходе с «1С:Управление торговлей 11» на «1С:Бухгалтерия предприятия 3.0». Для успешной адаптации кода мы выполнили замену устаревших ссылок метаданных БанковскиеСчетаОрганизаций на универсальный справочник БанковскиеСчета.

Дополнительно мы изучили механизмы сортировки платформы «1С:Предприятие 8.3» и разобрались, почему использование метода Выбрать() с сортировкой по ссылочным полям приводит к критическим ошибкам. Реализовав один из предложенных вариантов обхода ограничения (лучше всего — через объект Запрос), вы сможете полностью восстановить работоспособность вашей обработки по автоматическому заполнению договоров по шаблонам Word.

← На главную