На платформах .NET и .NET Core исполняемые файлы не размещаются прямо внутри процесса Windows, как в случае традиционных неуправляемых приложений. Взамен исполняемый файл .NET и .NET Core попадает в отдельный логический раздел внутри процесса, который называется доменом приложения. Такое дополнительное разделение традиционного процесса Windows обеспечивает несколько преимуществ.
• Домены приложений являются ключевым аспектом нейтральной к операционным системам природы платформы .NET Core, поскольку такое логическое разделение абстрагирует отличия в том, как лежащая в основе операционная система представляет
загруженный исполняемый файл.
• Домены приложений оказываются гораздо менее затратными в смысле вычислительных ресурсов и памяти по сравнению с полноценными процессами. Таким образом, среда CoreCLR способна загружать и выгружать домены приложений намного быстрее, чем формальный процесс, и может значительно улучшить масштабируемость серверных приложений.
Отдельный домен приложения полностью изолирован от других доменов приложений внутри процесса. Учитывая такой факт, имейте в виду, что приложение, выполняющееся в одном домене приложения, не может получать данные любого рода (глобальные переменные или статические поля) из другого домена приложения, если только не применяется какой-нибудь протокол распределенного программирования.
На заметку! Поддержка доменов приложений в .NET Core изменилась. В среде .NET Core существует в точности один домен приложения. Создавать новые домены приложений больше нельзя, поскольку это требует поддержки со стороны исполняющей среды и в общем случае сопряжено с высокими накладными расходами. Изоляцию сборок в .NET Core обеспечивает класс
ApplicationLoadContext
(рассматриваемый далее в главе).
Класс System.AppDomain
С выходом версии .NET Core класс
AppDomain
считается почти полностью устаревшим. Хотя большая часть оставшейся поддержки предназначена для упрощения перехода из .NET 4.x в .NET Core, она по-прежнему может приносить пользу, как объясняется в последующих двух разделах.
Взаимодействие со стандартным доменом приложения
С помощью статического свойства
AppDomain.CurrentDomain
можно получать доступ к стандартному домену приложения. При наличии такой точки доступа появляется возможность использования методов и свойств
AppDomain
для проведения диагностики во время выполнения.
Чтобы научиться взаимодействовать со стандартным доменом приложения, начните с создания нового проекта консольного приложения по имени
DefaultAppDomainApp
. Модифицируйте файл
Program.cs
, поместив в него следующий код, который просто выводит подробные сведения о стандартном домене приложения с применением нескольких членов класса
AppDomain
:
using System;
using System.IO;
using System.Linq;
using System.Reflection;
using System.Runtime.Loader;
Console.WriteLine("***** Fun with the default AppDomain *****\n");
DisplayDADStats;
Console.ReadLine;
static void DisplayDADStats
{
// Получить доступ к домену приложения для текущего потока.
AppDomain defaultAD = AppDomain.CurrentDomain;
// Вывести разнообразные статистические
данные об этом домене.
Console.WriteLine("Name of this domain: {0}",defaultAD.FriendlyName);
// Дружественное имя этого домена
Console.WriteLine("ID of domain in this process: {0}",defaultAD.Id);
// Идентификатор этого процесса
Console.WriteLine("Is this the default domain?: {0}",
defaultAD.IsDefaultAppDomain);
// Является ли этот домен стандартным
Console.WriteLine("Base directory of this domain: {0}",
defaultAD.BaseDirectory);
// Базовый каталог этого домена
Console.WriteLine("Setup Information for this domain:");
// Информация о настройке этого домена
Console.WriteLine("\tApplication Base: {0}",
defaultAD.SetupInformation.ApplicationBase);
// Базовый каталог приложения
Console.WriteLine("\t Target Framework: {0}",
defaultAD.SetupInformation.TargetFrameworkName);
// Целевая платформа
}
Ниже приведен вывод:
***** Fun with the default AppDomain *****
Name of this domain: DefaultAppDomainApp
ID of domain in this process: 1
Is this the default domain?: True
Base directory of this domain: C:\GitHub\Books\csharp8-wf\Code\Chapter_14\
Обратите внимание, что имя стандартного домена приложения будет идентичным имени содержащегося внутри него исполняемого файла (
DefaultAppDomainApp.exe
в этом примере). Кроме того, значение базового каталога, которое будет использоваться для зондирования обязательных внешних закрытых сборок, отображается на текущее местоположение развернутого исполняемого файла.
Перечисление загруженных сборок
С применением метода
GetAssemblies
уровня экземпляра можно просмотреть все сборки .NET Core, загруженные в указанный домен приложения. Метод возвращает массив объектов типа
Assembly
(рассматриваемого в главе 17). Для этого вы должны импортировать пространство имен
System.Reflection
в свой файл кода (как делали ранее).
В целях иллюстрации определите в классе Program новый вспомогательный метод по имени
ListAllAssembliesInAppDomain
. Он будет получать список всех загруженных сборок и выводить для каждой из них дружественное имя и номер версии: