diff Implab.ServiceHost/docs/XmlConfiguration.md @ 277:963b17c275be v3

Refactoring Added <array> element to injection parameters Working on registrations of factories
author cin
date Sat, 28 Apr 2018 18:48:09 +0300
parents Implab.ServiceHost/Unity/readme.md@b4e0f81c7425
children e0916ddc9950
line wrap: on
line diff
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/Implab.ServiceHost/docs/XmlConfiguration.md	Sat Apr 28 18:48:09 2018 +0300
@@ -0,0 +1,100 @@
+# XML Конфигурация IoC контейнера
+
+Данная библиоетка создавалась для загрузки и применения конфигурации к IoC контейнеру, она не предназначена для конфигурирования
+контейнера во время выполнения, большинство контейнеров уже обладают данным функционалом.
+
+На данный момент поддерживается единственный вид контейнера - [Unity Container](https://unitycontainer.github.io/)
+
+Unity уже обладает средствами загрузки конфигурации из XML, данная библиотека позволяет решать следующие задачи
+
+- Конфигурация является простым Xml документом, который можно получить из любого источика и не ограничивается `.config` файлами приложения
+- Включение существующе конфигурации `<include href='config.xml'/>` в текущую
+- Поддержка сериализованных объектов в качестве регистраций сервисов и параметров
+- Описание зависимостей может быть расширено собсвтенными элементами с произвольной структурой
+- Поддержка специфиакции генериков любой вложенности `Dictionary{Foo,Bar{Int32}}`
+
+## Общая архитектура
+
+`Implab.ServiceHost.Unity` содержит в себе классы для загрузки и применения XML конфигурации к IoC контейнеру, в частности к Unity.
+
+1. Настраивается схема `ContainerConfigurationSchema`
+2. Загружается документ и десереализуется в виде `ContainerElement`
+3. Создается `ContainerBuilder` при помощи которого применяются настройки из `ContainerElement`
+
+`ContainerConfigurationSchema` - определяет элементы которые могут быть использованы в конфигурации контейнера, предоставляет настроенный `XmlSerializer`.
+
+`ContainerBuilder` - основной класс, который используется для применения конфигурации к контейнеру, добавляет записи регистрации сервисов.
+
+`ContainerElement` - Корневой элемент конфигурации, который загружается из документа.
+
+Классы заканчивающиеся словом `Builder` используются для применения конфигурации к контейнеру,
+классы заканчивающиеся на `Element` содержат информацию о конфигурации и десериализуются из исходного документа.
+
+## Структура конфигурации контейнера
+
+Элемент верхнего уровня всегда `ContainerElemnt`, он используется для хранения набора элеметов, которые распознаются и выполняются `ContainerBuilder`.
+
+Все элементы, входящие в контейнер наследуются от абстрактного класса `ContainerItemElement`,
+который позволяет получить текущий `ContainerBuilder` и выполнить над ним какие-либо действия.
+
+Примерами элементов контейнера могут быть
+
+- `<include href='config.xml'/>` - включение конфигурации из указанного места
+- `<namespace name='My.App'/>` - добавление пространства имен для поиска типов
+- `<register type='MyGenericType{}'/>` - добавление в контейнер регистрации типа ``My.App.MyGenericType`1``
+
+Полный набор элементов, доступных для использования в контейнере определяет схема `ContainerConfigurationSchema`,
+разработчик может расширить контейнер совими собственными элементами зарегистрировав их в схеме.
+
+Например, мы используем компоненту `MyHttpClient` для загрузки данных
+
+```xml
+    <register type="IClient" mapTo="MyHttpClient">
+        <property name="proxy">
+            <value>socks5://proxy1.my.company</value>
+        </property>
+    </register>
+```
+
+При частом использовании можно сделать описание конфигурации несколько проще,
+описав новый эелемент конфигурации
+
+```csharp
+public class MyHttpClientElement : ContainerItemElement {
+
+    public string Proxy { get; set; }
+
+    public override void Visit(ContainerBuilder builder) {
+        // создаем описание элемента
+        var registration = new RegistrationElement {
+            RegistrationType = "IClient",
+            ImplementationType = "My.App.MyHttpClient",
+            Injectors = new [] {
+                new PropertyInjectionElement {
+                    Name = "Proxy",
+                    Value = ValueParameterElement {
+                        Value = Proxy
+                    }
+                }
+            }
+        };
+
+        // применяем созданное описание к контейнеру
+        builder.Visit(registration)
+    }
+}
+```
+
+Регистрируем новый элемент в схеме
+
+```csharp
+schema.RegisterContainerElement<MyHttpClientElement>("http");
+```
+
+Используем новый элемент в конфигурации
+
+```xml
+    <http>
+        <proxy>socks5://proxy1.my.company</propxy>
+    </http>
+```
\ No newline at end of file