При разработке в расширениях 1С программисты часто сталкиваются с ситуацией, когда необходимо связать новый документ с документом-основанием. Однако стандартный подход через расширение типа существующего реквизита ДокументОснование часто натыкается на технологический барьер: режим совместимости конфигурации (например, 8.3.17 и ниже) не позволяет изменять составные типы данных в расширениях. В этой статье мы подробно разберем, как обойти это ограничение, сохранив чистоту кода и архитектурную правильность решения.
Прежде чем переходить к решениям, проанализируем ситуацию. В режиме совместимости ниже 8.3.17 платформа 1С накладывает жесткие ограничения на реструктуризацию таблиц базы данных через механизмы расширений. Когда мы пытаемся добавить новый тип (наш самописный документ из расширения) в существующий реквизит основной конфигурации ДокументОснование, платформа пытается изменить физическую структуру таблицы в СУБД. Режим совместимости блокирует это действие, выдавая ошибку: «Изменение типов недопустимо в режиме совместимости 8.3.17 и ниже».
Попытки поднять режим совместимости всей базы ради одной задачи — рискованный путь, который может привести к неработоспособности типовых механизмов (особенно если конфигурация находится на поддержке). Поэтому рассмотрим альтернативные и более безопасные пути решения.
Это самый надежный и рекомендуемый способ. Вместо того чтобы мучить стандартный реквизит, мы добавим свой собственный, который будет хранить нужную нам ссылку. Рассмотрим по шагам, как это реализовать.
Шаг 1. Добавление реквизита в расширение. Найдем в расширении документ, который мы создаем (например, «Платежное поручение»), и добавим ему новый реквизит расш_ДокументОснование. В качестве типа укажем ссылку на наш самописный документ ДокументСсылка.Платеж. Так как это новый объект метаданных в расширении, никаких конфликтов с режимом совместимости не возникнет.
Шаг 2. Перехват события заполнения. Теперь нам нужно сделать так, чтобы при создании «на основании» этот реквизит заполнялся автоматически. Для этого воспользуемся процедурой ОбработкаЗаполнения в модуле объекта документа. Нам потребуется аннотация &После, чтобы не затирать типовое заполнение.
Проанализируем пример кода:
&После("ОбработкаЗаполнения")
Процедура расш_ОбработкаЗаполнения(ДанныеЗаполнения, ТекстЗаполнения, СтандартнаяОбработка)
// Проверяем, что в качестве основания передан именно наш документ "Платеж"
Если ТипЗнч(ДанныеЗаполнения) = Тип("ДокументСсылка.Платеж") Тогда
// Заполняем наш новый реквизит ссылкой на основание
ЭтотОбъект.расш_ДокументОснование = ДанныеЗаполнения;
// Здесь также можно программно заполнить другие реквизиты документа
// значениями из документа-основания
ЭтотОбъект.СуммаДокумента = ДанныеЗаполнения.Сумма;
ЭтотОбъект.Комментарий = "Создано на основании документа Платеж № " + ДанныеЗаполнения.Номер;
КонецЕсли;
КонецПроцедуры
Этот метод гарантирует, что ссылка будет получена в момент создания объекта в памяти и сохранится при записи документа в базу данных.
Если создание документа происходит программно (например, из формы списка документа «Платеж» по кнопке), мы можем использовать возможности платформы по передаче параметров формы. Рассмотрим ситуацию, когда мы открываем форму нового документа и хотим передать в нее данные.
В коде вызова (в форме документа-источника) мы можем подготовить структуру:
ПараметрыФормы = Новый Структура;
ЗначенияЗаполнения = Новый Структура;
ЗначенияЗаполнения.Вставить("расш_ДокументОснование", Объект.Ссылка);
ПараметрыФормы.Вставить("ЗначенияЗаполнения", ЗначенияЗаполнения);
ОткрытьФорму("Документ.ПлатежноеПоручение.ФормаОбъекта", ПараметрыФормы);
Если имя ключа в структуре ЗначенияЗаполнения совпадает с именем реквизита в расширении (расш_ДокументОснование), платформа автоматически подставит значение в новый документ при открытии формы. Это избавляет от необходимости писать лишний код в модуле объекта, если заполнение нужно только при интерактивном создании.
Бывают случаи, когда изменять структуру документа (даже в расширении) нежелательно или когда связей «один-ко-многим» может быть слишком много. В такой ситуации разберем вариант использования вспомогательного регистра сведений.
Мы можем создать в расширении непериодический регистр сведений расш_СвязиДокументов с двумя измерениями:
В этом случае при записи подчиненного документа (например, в событии ПередЗаписью) мы будем делать запись в этот регистр. Это позволит нам не только хранить связь, но и строить отчеты по структуре подчиненности, не затрагивая основные реквизиты документов.
После того как мы успешно сохранили ссылку в новом реквизите расш_ДокументОснование, нам наверняка захочется видеть эту связь в стандартном отчете «Структура подчиненности». В расширении мы можем создать объект метаданных Критерий отбора.
Выясним, как его настроить:
расш_СвязанныеДокументы.расш_ДокументОснование у документа «Платежное поручение».Теперь при нажатии на кнопку «Связанные документы» в интерфейсе пользователь увидит всю цепочку документов, несмотря на то что связь реализована через кастомный реквизит в расширении.
Подводя итог, проанализируем лучшие практики для работы в условиях ограничений режима совместимости:
расш_). Это поможет избежать конфликтов имен при будущих обновлениях основной конфигурации.Рассмотренные нами подходы позволяют гибко решать задачи интеграции самописных объектов с типовыми конфигурациями, обходя технологические ограничения платформы 1С и сохраняя возможность легкого обновления системы в будущем.