Страницы с тегами : Enterprise Library

Unity 2.0

Давненько я не писал про Unity. За это время успела выйти новая версия этого IoC-контейнера и появилась новая версия Enterprise Library.

Первое заметное изменение в Unity: теперь требуется подключать одну сборку Microsoft.Practices.Unity. Хотя AOP для Unity все еще лежит в отдельной сборке Microsoft.Practices.Unit.Interception.

Интерфейс класса UnityContainer расширился методами IsRegistered и свойством Registrations. Последнее позволяет анализировать что мы уже положили в контейнер.

Три больших изменения в резолвинге. 

  1. Теперь можно резолвить Func<T>, который будет возвращать зарегистрированный в контейнере экземпляр T. Аналогично можно резолвить Func<IEnumerable<T>>, который будет возвращать все зарегистрированные в контейнере именованные зависимости типа T. Это дает возможность переконфигурировать контейнер во время работы программы, так чтобы остальной код об этом не знал.
  2. При наличии нескольких конструкторов в создаваемом классе по-умолчанию выбирается конструктор с максимальным количеством параметров.
  3. В метод Resolve теперь можно передавать объекты ResolverOverride, позволяющие переопределять поведение Unity при резолвинге.

Добавились два LifetimeManager. HierarchicalLifetimeManager – чтобы дочерние контейнеры резолвили свои экземпляры, а не брали родительский. Это может пригодиться в вебе при создании дочерних контейнеров на каждый запрос. PerResolveLifetimeManager – позволяет переиспользовать один экземпляр в пределах одного вызова метода Resolve.

Подробнее можно почитать в Change Log.

PS. Также есть версия для Silverlight.

PPS. Качать здесь.



Аудит изменений с учетом контекста операций

В предыдущем посте я описал способ, который позволяет проводить аудит изменений данных в Entity Framework, не затрагивая сами классы сущностей.

Аудит изменений данных вполне возможно делать в самой БД с помощью триггеров, но в базу не попадают сведения о том какой пользователь системы произвел изменения (в случае приложения, построенного по принципу trusted subsystem) и с какой целью были проведены эти изменения.

Для каждой операции работы изменения данных существует некоторый контекст, который включает в себя как некоторые явные параметры, как имя пользователя или URL, так и неявные, например намерения, с которыми были выполнены изменения данных (частично их можно восстановить по стеку вызовов).

Для задач логирования было бы удобно иметь доступ к некоторым параметрам контекста, особенно неявным. Эти параметры должны прозрачно передаваться по цепочке вызовов. Для решения таких задач можно применить монады, но тогда придется переписать весь код под использование монад, что очень проблематично. Можно воспользоваться возможностями AOP и IoC чтобы обеспечить неявную передачу явного контекста.

Для начала нам понадобится класс для хранения текущего контекста. Как и в случае со стеком вызовов, контексты тоже могут составлять некоторый стек.

public interface IContextManager<T>
{
    void Push(T value);
    void Revert();
    IEnumerable<T> GetValues();
}


Применение Enterprise Library

Все возможности Enterprise Library можно применять по-отдельности и радоваться жизни. Но если бы это была единственная возможность я бы не написал этот пост.

Магия начинается в сборке Microsoft.Practices.EnterpriseLibrary.PolicyInjection.CallHandlers.
В этой сборке в одноименном неймспейсе содержатся call handlerы и атрибуты для навешивания обработчиков на методы. Как использовать call handlerы я рассказывал в этом посте.

Кратко опишу доступные хендлеры:

  • AuthorizationCallHandler – задействует Security Application Block для авторизации при вызове перехваченного метода
  • CachingCallHandler – обработчик, кеширующий результаты вызова перехваченного метода средствами Caching Application Block. Может быть чрезвычайно полезным для веб-разработки.
  • ExceptionCallHandler – позволяет декларативно задавать стратегию обработки исключений в перехваченном методе. Стратегии задаются средствами Exception Handling Application Block.
  • LogCallHandler – задействует Logging Application Block для логгирования вызова перехваченного метода.
  • ValidationCallHandler – вызывает валидацию параметров метода. Параметры валидации должны быть заданы атрибутами или в конфигурации Validation Application Block.
  • PerformanceCounterCallHandler – обработчик, который занимается сбором информации о параметрах быстродействия перехваченного метода. Информация сохраняется в PreformanceCounterах. В самой сборке Microsoft.Practices.EnterpriseLibrary.PolicyInjection.CallHandlers есть Installer (который можно запустить через installutil), создающий необходимые  счетчики производительности.

Если интересует только runtime AOP, то можно использовать не полновесный IoC-контейнер Unity, а легковесный генератор прокси-классов из Policy Injection Application Block.

Кроме перехватчиков вызовов существует другой способ интеграции всех application blocks с контейнером Uinty. Практический каждый application block из состава enterprise library содержит класс – расширение Unity, которое контейнер возвращать объекты-фасады при запросе определенных типов.

Все расширения можно найти в основной сборке application block, в неймспейсе Configuration.Unity. Классы расширений называются ИмяБлокаExtension.

  • Для Logging Application Block расширение заставляет Unity возвращать фасад логгера по запросу типа LogWriter.
  • Для Exception Handling Application Block  основной тип фасада – ExceptionManager.
  • Для Caching Application Block контейнер возвращает реализации интерфейсов ICacheManager, IStorageEncryptionProvider, IBackingStore.
  • Для Security Application Block контейнер возвращает реализации интерфейсов IAuthorizationProvider, ISecurityCacheProvider.
  • Для Data Access Application Block контейнер возвращает экземпляры класса Database, аналогично DatabaseFactory.CreateDatabase. Можно получать как экземпляр по-умолчанию, так и именованный экземпляр.
  • Для Cryptography Application Block (который находится в сборке Microsoft.Practices.EnterpriseLibrary.Security.Cryptography) расширение заставляет Unity возвращать фасад по запросу типа CryptographyManager, а также реализации интерфейсов IHashProvider и ISymmetricCryptoProvider.

При использовании application blocks совместно с unity все настройки блоков надо задавать в файле конфигурации. Для этого в Enterpise Library есть удобная утилита.

К сожалению я не смог придумать адекватного примера, который сможет показать хотя бы малую часть возможностей Enterprise Library с использованием Unity.



Введение в Enterpise Library

Enterprise Library – библиотека от группы patterns & practicies Microsoft. Проект живет по адресу http://www.codeplex.com/entlib.

Enterprise Library состоит из набора компонент, называемых application blocks, каждый из которых решает определенную задачу, часто возникающую при разработке ПО. 

В состав Enterprise Library входят следующие блоки:

  • Unity Application Block  - IoC-контейнер Unity
  • Policy Injection Application Block – AOP времени выполнения
  • Validation Application Block – небольшой фреймворк для валидации
  • Logging Application Block – логгер
  • Exception Handling Application Block – фреймворк для создания политик обработки исключений в приложении
  • Caching Application Block – фреймворк для кеширования
  • Security Application Block – библиотека для авторизации, практически повторение ASP.NET Membership
  • Data Access Application Block – библиотека, упрощающая работу с ADO.NET, используется другими блоками
  • Cryptography Application Block – библиотека для упрощения работы с криптографическими функциями в .NET

Все эти блоки могут настраиваться через config-файл, для этого в составе Enterprise Library есть утилита упрощающая этот процесс.

Почти все блоки можно использовать по-отдельности, но основная сила Enterprise Library состоит в том, что все блоки можно подключить через Unity.