Домены приложений .NET
Домены приложений .NET
Теперь, когда вы понимаете роль процессов Win32 и возможностей взаимодействия с ними средствами управляемого программного кода, давайте рассмотрим понятие домена приложения .NET. По правилам платформы .NET компоновочные блоки не размещаются в рамках процесса непосредственно (как это было в традиционных приложениях Win32). Вместо этого выполняемый файл .NET помещается в обособленный логической раздел процесса, называемый доменом приложения (сокращенно AppDomain). Вы увидите, что один процесс может содержать множество доменов приложения, каждый из которых будет обслуживать свой выполняемый файл .NET. Такое дополнительное разделение традиционного процесса Win32 дает определенные преимущества, и некоторые из них указаны ниже.
• Домены приложения являются ключевым аспектом независимой от ОС природы платформы .NET, поскольку такое логическое деление абстрагируется от того, как именно ОС представляет загруженный выполняемый объект.
• Домены приложения являются существенно менее ресурсоемкими в отношении времени процессора и памяти, чем весь процесс в целом. Поэтому среда CLR способна загружать и выгружать домены приложений намного быстрее, чем формальный процесс.
• Домены приложения обеспечивают лучший уровень изоляции для загруженного приложения. Если один домен приложения в рамках процесса "терпит неудачу", остальные домены приложений могут продолжать функционировать.
Из приведенного списка следует, что один процесс может содержать любое число доменов приложения, каждый из которых полностью изолирован от других доменов приложения в рамках данного процесса (а также любого другого процесса). С учетом этого следует понимать, что приложение, выполняющееся в одном домене приложения, не может получить данные (в частности, значения глобальных переменных или статических полей) другого домена приложений иначе, как с помощью протокола удаленного взаимодействия .NET (который мы рассмотрим в главе 18).
Хотя один процесс и может принять множество доменов приложения, так бывает не всегда. Как минимум, процесс ОС будет содержать то, что обычно называют доменом приложения, созданным по умолчанию. Этот специальный домен приложения автоматически воздается средой CLR во время запуска процесса.
После этого CLR создает дополнительные домены приложения по мере необходимости, Если потребуется (хотя это и маловероятно), вы можете программно создавать домены приложения в среде выполнения в рамках выполняемого процесса, используя статические методы класса System.AppDomain. Этот класс оказывается также полезным для осуществления низкоуровневого контроля доменов приложения. Основные члены этого класса описаны в табл. 13.4.
Кроме того, тип AppDomain определяет небольшой набор событий, соответствующих различным моментам цикла существования домена приложения (табл. 13.5).
Таблица 13.4. Основные члены класса AppDomain
Член Описание CreateDomain() Статический метод, с помощью которого создается новый домен приложения в данном процессе. Среда CLR сама создает новые домены приложения по мере необходимости, поэтому вероятность того, что вам понадобится вызывать этот член, близка к нулю GetCurrentThreadId() Статический метод, возвращающий ID активного потока в данном домене приложения Unload() Еще один статический метод, позволяющий выгрузить указанный домен приложения для данного процесса BaseDirectory Свойство, возвращающее базовый каталог, используемый при поиске зависимых компоновочных блоков CreateInstance() Метод, создающий экземпляр указанного типа, определенного в указанном файле компоновочного блока ExecuteAssembly() Метод, выполняющий компоновочный блок в рамках домена приложения, заданного именем файла GetAssemblies() Метод, который читает список компоновочных блоков .NET, загруженных в данном домене приложения (двоичные файлы COM и C игнорируются) Load() Метод, используемый для динамической загрузки компоновочного блока в рамках данного домена приложенияТаблица 13.5. События типа AppDomain
Событие Описание AssemblyLoad Возникает при загрузке компоновочного блока AssemblyResolve Возникает, когда не удается идентифицировать компоновочный блок DomainUnload Возникает перед началом выгрузки домена приложения ProcessExit Возникает для домена приложения, созданного по умолчанию, когда завершается родительский процесс этого домена ResourceResolve Возникает, когда не удается идентифицировать ресурс TypeResolve Возникает, когда не удается идентифицировать тип UnhandledException Возникает, когда остается без обработки сгенерированное исключение