Передача объектов 1С:Предприятия через COM

Раздел содержит описание некоторых особенностей передачи данных 1С:Предприятия через механизм COM/Automation.

Когда данные передаются через COM

При использовании 1С:Предприятия совместно с другими программами или системами, а также при необходимости доступа к данным нескольких разных информационных баз 1С:Предприятия, могут использоваться средства модели межкомпонентного доступа к объектам (Component Object Model, COM). Ее главная идея заключается в предоставлении универсального средства создания и освобождения объектов, и универсального способа обращения к свойствам и методам объектов, включая передачу необходимых данных. Частным случаем реализации модели COM является Automation, определяющий универсальный интерфейс IDispatch для доступа к свойствам и методам объектов, а также универсальный способ передачи данных (структура VARIANT).

1С:Предприятие поддерживает средства Automation и тем самым позволяет:

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

Набор типов данных, представимых структурой VARIANT, ограничен, и не охватывает всего многообразия типов данных, доступных в 1С:Предприятии. Ниже будут рассмотрены некоторые особенности передачи средствами COM (через структуру VARIANT) данных 1С:Предприятия различных типов.

Примитивные типы

Значения NULL и Неопределено, а также типы данных Число, Строка, Дата, Булево, определенные в 1С:Предприятии, считаются примитивными. Они представляются аналогичными типами, определенными в VARIANT. Преобразование примитивных типов 1С:Предприятия в VARIANT представлено в таблице:

Тип в 1С:Преприятии Тип VARIANT
значение NULL VT_NULL
значение Неопределено VT_EMPTY
тип Число Целое в диапазоне от -2147483648 до 2147483647 VT_I4
Другие VT_R8
тип Строка VT_BSTR
тип Дата VT_DATE
тип Булево VT_BOOL

Примитивные типы и значения, определенные в VARIANT, преобразуются в примитивные типы и значения 1С:Предприятия в соответствии со следующей таблицей.

Тип VARIANT Тип в 1С:Предприятии

VT_NULL

значение NULL

VT_EMPTY

значение Неопределено

VT_I2, VT_I4, VT_R4, VT_R8, VT_CY, VT_ERROR, VT_DECIMAL, VT_I1, VT_UI1, VT_UI2, VT_UI4, VT_I8, VT_UI8, VT_INT, VT_UINT

тип Число
VT_BSTR тип Строка
VT_DATE тип Дата
VT_BOOL тип Булево

При передаче через COM значение примитивного типа сохраняется, быть может, за исключением точности представления числа. Это значит, что, например, значение типа Строка, после передачи через VARIANT сколько угодно раз, никак не изменится, и любые операции над ней будут давать такой же результат, который они давали до передачи через VARIANT.

Массивы

В структуре VARIANT предусмотрен специальный тип - VT_ARRAY, представляющий собой массив с несколькими измерениями и заданными диапазонами индексов по каждому из измерений. Он представляется специальной структурой SAFEARRAY. Для совместимости с другими объектами, представленными в COM, в 1С:Предприятии предусмотрен специальный тип данных COMSafeArray, в который преобразуется структура SAFEARRAY и наоборот.

При получении 1С:Предприятием структуры VARIANT, содержащей данные VT_ARRAY, она преобразуется в объект 1С:Предприятия COMSafeArray. При необходимости передачи из 1С:Предприятия структуры VARIANT, содержащей данные VT_ARRAY, в 1С:Предприятии должен быть подготовлен соответствующий объект COMSafeArray.

Важно, что данные типа VT_ARRAY являются аналогом примитивных типов в том смысле, что выступают в качестве значений, а не ссылок. В частности, преобразование структуры VARIANT в COMSafeArray приводит к копированию всех содержащихся в ней данных, и наоборот.

Объектные типы

Все остальные типы данных, определенные в 1С:Предприятии, в том числе и коллекции значений, являются объектами и преобразуются к типу VT_DISPATCH структуры VARIANT.

С другой стороны, при получении 1С:Предприятием значения VARIANT типа VT_DISPATCH, оно будет преобразовано в значение типа COMОбъект, набор свойств и методов которого будет совпадать с набором свойств и методов объекта, указатель на который содержался в VARIANT типа VT_DISPATCH. Работа с таким объектом может выполняться только через предоставляемые им свойства и методы, кроме оператора Для Каждого ....

Однако, в том случае, если 1С:Предприятие узнает в нем "свой" объект, VT_DISPATCH будет обратно преобразован в исходный объект 1С:Предприятия и его можно будет использовать так, как любой другой объект 1С:Предприятия этого же типа (оператор Для Каждого ..., обращения по индексу, встроенные функции Строка(), Тип() и т.д.).

1С:Предприятие или COM-соединение, подсоединенное к некоторой информационной базе,  распознает объект как "свой" только в том случае, если он был создан этим же подсоединением к информационной базе. Например, если из COM-соединения получить элемент справочника и передать этот элемент справочника в качестве параметра какого-нибудь метода объекта, полученного из этого же COM-соединения, то при выполнении этого метода объект будет распознан как "свой". Объект, полученный из другого соединения с информационной базой, не будет распознан как "свой".

Такое поведение объектов 1С:Предприятия объясняется тем, что большинство объектов 1С:Предприятия используют свой экземпляр контекста информационной базы, из которой они получены, и в другом экземпляре контекста информационной базы они "своими" не являются. Каждое приложение 1С:Предприятия и каждый экземпляр COM-соединения поддерживает свой экземпляр контекста информационной базы. Поэтому объекты 1С:Предприятия не распознаются как "свои" не в том приложении 1С:Предприятия или экземпляре COM-соединения, в котором они были созданы.

В Automation (интерфейс IDispatch) не предусмотрено штатных средств для реализации обращений к элементам массивов по индексам. Предусмотренные в Automation индексированные свойства допускают неоднозначность толкования и не поддерживаются встроенным языком 1С:Предприятия. Это значит, что для коллекций значений, не опознанных 1С:Предприятием как "свои" объекты, невозможно обращение к элементам по индексам из встроенного языка 1С:Предприятия. Однако, многие коллекции, в том числе и коллекции, определенные в 1С:Предприятии, поддерживают специальный интерфейс IEnumVARIANT, позволяющий совершить последовательный обход всех элементов коллекции. Этот механизм используется оператором Для Каждого ..., который имеется во многих языках программирования, в том числе и во встроенном языке 1С:Предприятия. Этот же механизм используется встроенным отладчиком 1С:Предприятия, когда он показывает элементы коллекции.

Для удобства обращения к элементам коллекций, определенных в 1С:Предприятии, после передачи коллекции через VARIANT в большинстве коллекций значений (Массив, ТаблицаЗначений, Структура и другие) предусмотрены методы Получить() и Установить(), действие которых аналогично обращению к элементам коллекций по индексам.

Например, если переменная "ПолученныйМассив" содержит объект типа Массив, то оператор

Копировать в буфер обмена
Элемент = ПолученныйМассив.Получить(5); 

аналогичен оператору

Копировать в буфер обмена
Элемент = ПолученныйМассив[5];

Таким же образом оператор

Копировать в буфер обмена
ПолученныйМассив.Установить(5, НовоеЗначение); 

аналогичен оператору

Копировать в буфер обмена
ПолученныйМассив[5] = НовоеЗначение;

Также рекомендуем ознакомиться с разделом "Особенности использования COM-объектов".