Когда мы сталкиваемся с необходимостью доработать типовой отчет в 1С, часто возникает задача по модификации его схемы компоновки данных (СКД). Особенно остро эта проблема проявляется при использовании расширений конфигурации. Многие разработчики сталкиваются с ситуацией, когда изменения, внесенные в СКД стандартного отчета, прекрасно работают в основной конфигурации, но перестают функционировать после переноса в расширение, выдавая ошибку типа "Поле не найдено". Давайте разберемся, почему это происходит и как правильно реализовать доработку отчета на СКД в расширении.
Обычно проблема проявляется, когда мы пытаемся добавить новое поле (например, "Объект.Код", как в нашем случае) в отчет, основанный на СКД, такой как "СправкаРасчетАмортизации". Мы изменяем макет СКД отчета, добавляем поле в запрос и в настройки схемы, и в основной конфигурации все работает. Однако, при заимствовании этого макета в расширение и попытке использования отчета, система сообщает об ошибке: "Отчет не сформирован! Поле не найдено 'Объект.Код'". Это происходит из-за особенностей работы расширений с заимствованными объектами, особенно с макетами. Например, в конфигурации 1С:Предприятие 8.3 (8.3.20.1674) Бухгалтерия предприятия КОРП, редакция 3.0 (3.0.108.36), отчет "СправкаРасчетАмортизации" ведет себя именно так при попытке добавить поле "Код" основного средства через расширение.
Расширения 1С позволяют заимствовать объекты из основной конфигурации. Однако, в случае с макетами СКД, заимствованный макет часто ведет себя как объект только для чтения. Это означает, что даже если мы заимствуем макет в расширение, напрямую редактировать его содержимое (например, запрос или структуру полей) через конфигуратор платформы может быть затруднительно или невозможно. Отчет продолжает использовать оригинальный макет из основной конфигурации, либо если расширение пытается использовать свой измененный, но некорректно заимствованный макет, возникают ошибки, так как платформа не "видит" внесенные в него изменения. Это основная причина, почему мы видим ошибку "Поле не найдено", хотя и внесли изменения в расширении.
Для успешной модификации отчета на СКД в расширении, необходимо придерживаться одного из следующих подходов. Каждый из них имеет свои особенности, и выбор зависит от сложности задачи и специфики типового отчета.
Этот метод является наиболее простым и обеспечивает максимальную свободу действий. Мы полностью создаем копию стандартного отчета в расширении, фактически создавая новый отчет на основе типового. Давайте рассмотрим шаги, которые нам необходимо выполнить:
СправкаРасчетАмортизации_Расширенная или СправкаРасчетАмортизацииСКодомОС. Важно, чтобы это имя не конфликтовало с существующими отчетами.Отчет.СправкаРасчетАмортизации). Открываем его макет схемы компоновки данных. Копируем содержимое этого макета. Возвращаемся в наш новый отчет в расширении и вставляем скопированный макет. Присваиваем ему уникальное имя (например, ОсновнаяСхемаКомпоновкиДанныхРасш).ВЫБРАТЬ, используя необходимые соединения с другими таблицами, если это требуется. Например, для добавления кода основного средства нам может потребоваться присоединить таблицу справочника "Основные средства" и выбрать из нее реквизит Код.
ВЫБРАТЬ
СпрОС.Код КАК КодОсновногоСредства,
ТаблицаДвижений.ОсновноеСредство КАК ОсновноеСредство,
// ... другие поля типового запроса
ИЗ
РегистрНакопления.АмортизацияОС.ОстаткиИОбороты КАК ТаблицаДвижений
ЛЕВОЕ СОЕДИНЕНИЕ Справочник.ОсновныеСредства КАК СпрОС
ПО ТаблицаДвижений.ОсновноеСредство = СпрОС.Ссылка
// ... прочие соединения и условия
КодОсновногоСредства) должно появиться в списке "Поля". Убеждаемся, что для него корректно определены тип данных и заголовок.Этот подход гарантирует, что мы работаем с полностью независимой схемой и не сталкиваемся с ограничениями заимствованных объектов, что значительно упрощает отладку и модификацию.
Для многих типовых бухгалтерских отчетов 1С, таких как "СправкаРасчетАмортизации", платформа предоставляет специальный, более элегантный механизм для подмены схемы компоновки данных. Этот механизм обычно реализован через общие модули, например, БухгалтерскиеОтчеты, и позволяет отчетам динамически выбирать, какую СКД использовать. Мы должны реализовать его в расширении. Рассмотрим шаги:
Отчет.СправкаРасчетАмортизации). Затем в расширении создаем новый макет, копируя содержимое макета СКД из типового отчета и присваиваем ему уникальное имя (например, СхемаСправкаРасчетАмортизации_Расш).ТекущаяСхемаКомпоновкиДанных: Заимствуем объект "Отчет" в расширении. В метаданных заимствованного отчета (в расширении) проверяем наличие реквизита с именем ТекущаяСхемаКомпоновкиДанных строкового типа. Если его нет, создаем его. Если он уже есть, просто убеждаемся, что он строкового типа. Этот реквизит будет использоваться для динамического хранения имени макета СКД, который должен быть использован.НовыеПараметрыВыбораСхемыКомпоновкиДанных: Эта процедура предназначена для определения параметров, которые могут влиять на выбор схемы. Если у вас нет особых условий для выбора схемы (например, в зависимости от прав пользователя, версии программы или других настроек), она может возвращать пустую структуру или просто ничего. Мы можем использовать ее для передачи дополнительных сведений.ТекущаяСхемаКомпоновкиДанных: Эта процедура принимает структуру параметров (которая была заполнена в предыдущей процедуре, если это необходимо) и должна возвращать имя макета СКД, который будет использоваться для формирования отчета. Именно здесь мы указываем имя нашего нового, измененного макета из расширения.Вот пример кода, который мы должны добавить в модуль менеджера заимствованного отчета в расширении:
// Процедура вызывается платформой для получения параметров, влияющих на выбор схемы.
// Используется в стандартных отчетах, где схема может зависеть от версии конфигурации,
// настроек организации и т.п. Мы можем использовать ее для наших нужд.
Процедура НовыеПараметрыВыбораСхемыКомпоновкиДанных(СтруктураПараметров) Экспорт
// Пример: Мы можем добавить параметр, который будет определять,
// использовать ли расширенную схему по умолчанию.
СтруктураПараметров.Вставить("ИспользоватьРасширеннуюСхему", Истина);
КонецПроцедуры
// Процедура вызывается платформой для получения имени схемы компоновки данных.
// Здесь мы указываем имя нашего измененного макета из расширения.
Функция ТекущаяСхемаКомпоновкиДанных(СтруктураПараметров) Экспорт
// Мы проверяем параметр, если он есть, чтобы использовать нашу схему.
// Это позволяет гибко переключаться между стандартной и расширенной схемой.
Если СтруктураПараметров.Свойство("ИспользоватьРасширеннуюСхему") И СтруктураПараметров.ИспользоватьРасширеннуюСхему Тогда
Возврат "СхемаСправкаРасчетАмортизации_Расш"; // Важно: это имя нашего макета СКД в расширении!
Иначе
// Если наша расширенная схема не должна использоваться, возвращаем имя
// стандартного макета из основной конфигурации.
Возврат "ОсновнаяСхемаКомпоновкиДанных";
КонецЕсли;
КонецФункции
Обратите внимание, что имя ОсновнаяСхемаКомпоновкиДанных – это стандартное имя макета СКД в большинстве типовых отчетов 1С, и его мы возвращаем, если не хотим использовать расширенную схему. Имя СхемаСправкаРасчетАмоновкиДанных_Расш – это имя нашего макета в расширении, которое мы создали на первом шаге.
Этот механизм позволяет отчету быть гибким и использовать вашу измененную схему, не затрагивая при этом саму конфигурацию и обеспечивая корректное функционирование в расширении.
Давайте подробнее разберем, почему возникает ошибка "Поле не найдено 'Объект.Код'", даже если кажется, что все сделано правильно. Понимание этих причин поможет нам избежать подобных ошибок в будущем:
ВЫБРАТЬ
// ... другие поля
Объекты.Код КАК КодОбъекта
ИЗ
Справочник.Объекты КАК Объекты
// ... прочие соединения и условия, например, соединение с таблицей,
// из которой мы выбираем другие данные для отчета
Если поле КодОбъекта не будет выбрано запросом, СКД никогда его не "увидит", и при попытке обратиться к нему возникнет ошибка.
В некоторых случаях, когда требуется более сложная логика добавления полей, фильтров или группировок, или если необходимо динамически формировать схему в зависимости от условий, можно прибегнуть к программному изменению схемы компоновки данных. Этот подход позволяет динамически модифицировать структуру СКД непосредственно в коде модуля отчета или расширения. Мы можем получить схему компоновки данных как объект СхемаКомпоновкиДанных и программно добавлять в нее элементы:
// Пример программного добавления вычисляемого поля
// Эта функция может быть вызвана из модуля отчета или общего модуля расширения.
Процедура ДобавитьВычисляемоеПоле(СхемаКомпоновкиДанных)
// Создаем новый элемент коллекции полей СКД
НовоеПоле = СхемаКомпоновкиДанных.Поля.Добавить(Тип("ПолеКомпоновкиДанных"));
// Указываем имя поля, как оно будет использоваться в СКД
НовоеПоле.Поле = "МоеНовоеВычисляемоеПоле";
// Определяем заголовок, который будет отображаться пользователю
НовоеПоле.Заголовок = "Мое новое вычисляемое поле";
// Задаем выражение для вычисления значения поля.
// Оно может ссылаться на другие поля в схеме или на параметры.
НовоеПоле.Выражение = "Число(Объект.Код) * 10";
// Указываем роль поля (Измерение, Ресурс, Реквизит и т.д.)
НовоеПоле.Роль = "Измерение";
КонецПроцедуры
// Пример использования в модуле отчета или обработки, которая формирует отчет
// ...
// Получаем макет СКД из расширения (используя наш измененный макет)
МакетСКД = ОтчетОбъект.ПолучитьМакет("СхемаСправкаРасчетАмортизации_Расш");
// Создаем объект СхемаКомпоновкиДанных из макета
СхемаКомпоновкиДанных = МакетСКД.ПолучитьМакет("ОсновнаяСхема");
// Вызываем нашу процедуру для добавления вычисляемого поля
ДобавитьВычисляемоеПоле(СхемаКомпоновкиДанных);
// Далее работаем с компоновщиком данных, передавая ему модифицированную схему
КомпоновщикМакета = Новый КомпоновщикМакетаКомпоновкиДанных;
МакетКомпоновки = КомпоновщикМакета.Выполнить(СхемаКомпоновкиДанных, КомпоновщикНастроек.Настройки, ПараметрыДанных);
// ... дальнейшая работа с процессором компоновки данных
Этот подход дает максимальную гибкость, позволяя вносить изменения в структуру СКД без прямого изменения макета в конфигураторе, но требует более глубокого понимания программного интерфейса СКД и умения работать с объектами СхемаКомпоновкиДанных, НастройкиКомпоновкиДанных и другими. Для упрощения этой задачи можно использовать генератор программного кода схемы компоновки данных.
Для успешной работы с расширениями и СКД, а также для предотвращения возможных проблем, мы должны учесть следующие важные моменты:
Следуя этим рекомендациям и выбирая подходящий подход, мы сможем успешно доработать отчеты на СКД в расширениях 1С и избежать распространенных ошибок типа "Поле не найдено", обеспечивая стабильную и корректную работу наших доработок.