Главная страница   /   7. Построение объектов (Внедрение зависимостей в .NET

Внедрение зависимостей в .NET

Внедрение зависимостей в .NET

Марк Симан

7. Построение объектов

Меню:

  • Консольные приложения
  • ASP.NET MVC
  • Windows Communication Foundation
  • Windows Presentation Foundation
  • ASP.NET (Web Forms)
  • PowerShell

Приготовление изысканных блюд из нескольких слоев – смелое начинание, особенно, если вы хотите поучаствовать в поедании этих блюд. Вы не можете хорошо кушать и готовить в одно и то же время, кроме того, многие блюда, чтобы они хорошо получились, необходимо готовить в последнюю минуту.

Профессиональные кулинары знают, как решить большинство из этих задач. Среди многих хитростей они используют в качестве основного принцип "mise en place", который можно приблизительно перевести как "все готово": все, что может быть приготовлено хорошо заранее готовится заранее. Чистятся и нарезаются овощи, нарезается мясо, подготавливается инвентарь, разогревается духовка, раскладываются инструменты и т.д.

Подготавливается настолько много компонентов, насколько это возможно. Если мороженое является частью десерта, то его можно сделать за день до приготовления десерта. Если первый слой содержит мидии, их можно почистить за несколько часов до этого. Даже такой недолговечный компонент, как беарнский соус можно приготовить за час до приготовления основного блюда. Когда гости готовы приступить к еде, необходимы только финальные приготовления: подогреть соус во время жарки мяса и т.д. Во многих случаях эта финальная композиция блюда не занимает более 5-10 минут. Рисунок 7-1 иллюстрирует этот процесс.

Рисунок 7-1: Принцип "mise en place" подразумевает приготовление всех компонентов блюда заранее для того, чтобы финальная композиция блюда была выполнена настолько быстро и легко, насколько это возможно.

Принцип "mise en place" похож на разработку слабо связанного приложения с помощью механизма внедрения зависимостей. Мы можем написать все требуемые компоненты заранее и компоновать их только тогда, когда мы должны это делать.

Примечание

В разделе "Composition Root" я сравнивал Composition Root с таким понятием Бережливой разработки программного обеспечения (Lean Software Development), как Последний ответственный момент. Сравнение Composition Root с принципом "mise en place" является схожей аналогией, несмотря на то, что при таком сравнении придается большое значение несколько другому аспекту: композиции.

Как и все аналогии, мы можем использовать их только до настоящего момента. Разница в том, что в кулинарии этапы подготовки и композиции разделены во времени, тогда как в разработке приложений это разделение проявляется в рамках модулей и уровней. Рисунок 7-2 демонстрирует то, как мы компонуем компоненты в Composition Root (часто на уровне пользовательского интерфейса).

Рисунок 7-2: Composition Root соединяет все независимые модули приложения. В противоположность "mise en place" это не происходит настолько поздно, насколько это возможно, но происходит там, где необходима интеграция различных модулей.

Первое, что происходит на этапе выполнения – это композиция объектов. Как только диаграмма объектов подключена, завершается композиция объектов и составные компоненты соединяются.

Несмотря на то, что композиция объектов – это фундаментальная основа механизма внедрения зависимостей, она является самой простой для понимания составляющей. Вы уже знаете, как это делать, поскольку вы все время компонуете объекты при создании объектов, которые содержат в себе другие объекты. В разделе 3.3. "Паттерны DI-контейнеров" мы рассмотрели основные принципы того, когда и как компоновать приложения. Следовательно, я не собираюсь использовать следующие 40 страниц для того, чтобы поведать вам о том, как компоновать объекты.

Вместо этого я хочу помочь вам обратиться к тем трудностям, которые могут возникнуть, когда вы будете компоновать объекты. Эти трудности возникают не из-за самой композиции объектов, а из-за фреймворков приложений, в которых вы хотели бы компоновать ваши объекты. Эти проблемы специфичны для каждого фреймворка и то же самое касается и резолюций. В моем случае эти проблемы принимают вид некоторых самых значимых препятствий для успешного применения механизма внедрения зависимостей, поэтому я сконцентрирую свое внимание именно на них. Это делает главу менее теоретической и более практической по сравнению с предыдущими главами.

Подсказка

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

Легко формировать целостную иерархию зависимостей приложения, когда мы имеем полный контроль над жизненным циклом приложения (как мы поступаем с приложениями командной строки). Тем не менее, большинство фреймворков (ASP.NET, WCF и т.д.) в .NET включают в себя инверсию управления, которая иногда может усложнять процесс применения механизма внедрения зависимостей. Понимание швов каждого фреймворка является ключевым моментом для применения механизма внедрения зависимостей к конкретному фреймворку. Как иллюстрирует рисунок 7-3, в этой главе мы будем рассматривать то, как реализовать Composition Root'ы в некоторых универсальных фреймворках стандартной библиотеки классов (BCL).

Рисунок 7-3: Структура этой главы принимает форму каталога различных BCL фреймворков и швов, которыми они могут обладать для разрешения механизма внедрения зависимостей. Каждый раздел написан таким образом, что его можно читать независимо от остальных разделов.

Примечание

В связи с пространственными ограничениями я не буду рассматривать приложения Windows Forms. Тем не менее, когда дело касается композиции объектов, то в этом они схожи с WPF приложениями.

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

Начнем мы с самого простого фреймворка, в котором применяется механизм внедрения зависимостей, и постепенно перейдем к более сложным фреймворкам. Когда мы дойдем до ASP.NET, нам нужно будет пересечь бездну, за пределами которой мы можем применять механизм внедрения зависимостей, только подвергая риску, по крайней мере, несколько наших принципов. Не опровергается тот факт, что такие фреймворки, как ASP.NET и PowerShell являются попросту враждебными средами для применения механизма внедрения зависимостей, поэтому мы должны сделать все так хорошо, насколько мы это можем. Тем не менее, пока мы не достигнем этой точки, нет необходимости в компромиссе.

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

7.1. Построение консольных приложений

7.2. Построение ASP.NET MVC приложений

7.3. Построение WCF приложений

7.4. Построение WPF приложений

7.5. Построение ASP.NET приложений

7.6. Построение PowerShell cmdlets

7.7. Резюме