Варианты маршалинга для объектов: MBR и MBV
Варианты маршалинга для объектов: MBR и MBV
В рамках платформы .NET вы имеете на выбор два варианта того, как предоставить удаленный объект клиенту. Упрощенно говоря, маршалинг описывает правила передачи удаленного объекта из одного домена приложения в другой. При разработке объекта, предусматривающего удаленное использование, вы можете выбрать либо семантику MBR (marshal-by-reference – маршалинг по ссылке), либо семантику MBV (marshal-by-value – маршалинг по значению). Их различие заключается в следующем.
• MBR-объекты. Вызывающая сторона получает агента для осуществления доступа к удаленному объекту.
• MBV-объекты. Вызывающая сторона получает полную копию объекта для использования в своем домене приложения.
При использовании типа, относящегося к MBR-объектам, среда CLR обеспечит создание в домене приложения клиента прозрачного и реального агентов, в то время как сам MBR-объект будет оставаться в домене приложения сервера. При вызове методов удаленного типа клиентом система удаленного взаимодействия .NET (схема которой описана выше) активизируется, чтобы выполнить задачи упаковки, отправки и получения информации при обмене данными через границы доменов приложений. Для этого MBR-объекты имеют ряд свойств, "простирающихся" за рамки их физического расположения. Вы увидите, что MBR-объекты имеют различные опции конфигурации, относящиеся к их активизации и управлению циклом существования. В противоположность этому, MBV-объекты представляют собой локальные копии удалённых объектов (использующие протокол сериализации .NET, который был рассмотрен в главе 17). MBV-объекты имеют намного меньше опций конфигурации, поскольку их цикл существования контролируется непосредственно клиентом. Подобно любому другому объекту .NET, после того как клиент освободит все ссылки на MBV-тип, этот тип становится потенциальным объектом внимания для сборщика мусора. Поскольку MBV-типы являются локальными копиями удаленных объектов, процесс вызова клиентом членов соответствующего типа, вообще говоря, не предполагает никакой сетевой активности.
Следует понимать, что вполне естественным для сервера является поддержка доступа к множеству MBR- и MBV-типов. Вы можете также догадаться, что MBR-типы обычно поддерживают методы, возвращающие различные MBV-типы, что, в общем-то, напоминает автоматизированное предприятие, где один объект создает и выпускает другие связанные объекты. Здесь возникает следующий вопрос: как сконфигурировать пользовательский тип класса для использования в виде MBR-или MBV-объекта?
Конфигурация MBV-объекта
Процесс конфигураций объекта для использования в виде MBV-типа абсолютно аналогичен процессу конфигурации объекта для сериализации. Просто объявите соответствующий тип с атрибутом [Serializable].
[Serializable]
public class SportsCar {…}
Конфигурация MBR-объекта
MBR-объекты не маркируются специальным атрибутом .NET, а получаются (явно или неявно) из базового класса System.MarshalByRefObject.
public class SportsCarFactory: MarshalByRefObject {…}
Формально тип MarshalByRefObject определяется следующим образом.
public abstract class MarshalByRefObject: object {
public virtual ObjRef CreateObjRef(Type requestedType);
public virtual bool Equals(object obj);
public virtual int GetHashCode();
public virtual object GetLifetimeService();
public Type GetType();
public virtual object InitializeLifetimeService();
public virtual string ToString();
}
Функциональные возможности, наследуемые от System.Object, вполне понятны, а роль остальных членов описана в табл. 18.2.
Таблица 18.2. Основные члены System.MarshalByRefObject
Член Описание CreateObjRef() Создает объект, содержащий всю информацию, необходимую для генерирования агента, который будет использоваться для взаимодействия с удаленным объектом GetLifetimeServices() Возвращает текущий сервис-объект, контролирующий политику цикла существования для данного экземпляра InitializeLifetimeServices() Генерирует сервис-объект для контроля политики цикла существования данного экземпляраМожно сказать, что суть типа MarshalByRefObject заключается в определении членов, которые затем могут переопределяться для того, чтобы программно управлять циклом существования MBR-объекта (подробнее об управлении циклом существования объектов будет говориться в этой главе позже).
Замечание. То, что вы сконфигурировали тип в виде MBV- или MBR-объекта, совсем не означает, что этот объект следует использовать только в приложении удаленного взаимодействия, а означает только то, что этот объект можно использовать в таком приложении. Например, тип System.Windows.Forms.Form является потомком MarshalByRefObject. Поэтому при удаленном доступе он реализуется как MBR-тип, а в других случаях он будет обычным локальным объектом в домене приложения клиента.
Замечание. Как следствие предыдущего замечания обратим внимание на то, что если тип .NET не предполагает сериализацию и в его цепочке наследования нет MarshalByRefObject, то такой тип может активизироваться и использоваться только в его исходном домене приложения, т.е, такой тип является контекстно-связанным (см. главу 13).
Теперь, когда вы четко понимаете суть различий между MBR- и MBV-типами, давайте рассмотрим некоторые проблемы, специфичные для MBR-типов (к MBV-типам это не относится).