it-roy-ru.com

DI в функциях Azure

У меня есть несколько библиотек классов, которые я использую в своем приложении ASP.NET Web API, которые обрабатывают все мои бэкенды, например. Операции CRUD для нескольких баз данных, таких как база данных Azure SQL, база данных Cosmos и т.д.

Я не хочу заново изобретать колесо и иметь возможность использовать их в новых функциях Azure, которые я создаю в Visual Studio 2017. Все мои методы репозитория используют интерфейс. Итак, как мне реализовать внедрение зависимостей в моей новой функции Azure?

Я не вижу никакой поддержки для DI, но я немного запутался. Похоже, что функции Azure основаны на том же SDK, что и WebJobs, и я думаю, что в прошлом году Microsoft начала поддерживать DI в WebJobs - я точно знаю, потому что я реализовал это с помощью Ninject.

Есть ли способ обойти это, чтобы я мог использовать мои существующие библиотеки в моем новом проекте функций Azure?

27
Sam

Я вижу эти два метода в дополнение к шаблону поиска служб (анти). Я также попросил их прокомментировать их.

https://blog.wille-zone.de/post/Azure-functions-dependency-injection/

https://blog.wille-zone.de/post/Azure-functions-proper-dependency-injection/

22
Sam

По этому вопросу существует открытый запрос функции на страницах GitHub для функций Azure .

Однако, как я подхожу к этому, я использую какую-то точку входа «обертка», разрешаю это с помощью локатора сервиса и запускаю функцию оттуда.

Это выглядит примерно так (упрощенно)

var builder = new ContainerBuilder();
//register my types

var container = builder.Build();

using(var scope = container.BeginLifetimeScope())
{
  var functionLogic = scope.Resolve<IMyFunctionLogic>();

  functionLogic.Execute();
}

Это немного глупо, конечно, но это лучшее, что есть на данный момент (насколько я знаю).

8
Jan_V

Я хотел бы добавить свои 2 цента к нему. Я использовал технику, которую использует Host, вводящий ILogger. Если вы посмотрите на проект запуска, я создал GenericBindingProvider, который реализует IBindingProvider. Затем для каждого типа, который я хочу ввести, я регистрирую его следующим образом:

builder.Services.AddTransient<IWelcomeService, WelcomeService>();
builder.Services.AddSingleton<IBindingProvider, GenericBindingProvider<IWelcomeService>>();

Недостатком является то, что вам нужно зарегистрировать тип, который вы хотите ввести в функцию дважды.

Образец кода:

Образец внедрения зависимости Azure V2 -

0
aczarkowski

Я видел, что блог Вилли-Зона часто упоминается, когда речь идет об этой теме, но вам не нужно идти по этому пути, чтобы использовать DI с функциями Azure.

Если вы используете версию 2, вы можете сделать свои функции Azure нестатичными. Затем вы можете добавить публичный конструктор для внедрения ваших зависимостей. Следующим шагом является добавление класса IWebJobsStartup. В вашем стартап-классе вы сможете зарегистрировать свои сервисы, как и в любом другом проекте .Net Core. 

У меня есть публичное репо, которое использует этот подход здесь: https://github.com/jedi91/MovieSearch/tree/master/MovieSearch

Вот прямая ссылка на класс запуска: https://github.com/jedi91/MovieSearch/blob/master/MovieSearch/Startup.cs

А вот и функция: https://github.com/jedi91/MovieSearch/blob/master/MovieSearch/Functions/Search.cs

Надеюсь, что этот подход помогает. Если вы хотите, чтобы ваши функции Azure оставались статичными, то подход «зона Вилли» должен работать, но мне действительно нравится этот подход, и он не требует сторонних библиотек. 

Стоит отметить, что это файл Directory.Build.target. Этот файл скопирует ваши расширения в файл хоста, чтобы DI работал после развертывания функции в Azure. Для локального запуска функции этот файл не требуется. 

0
Michael Kovacevich