Использование ILifetimeScope как зависимости

196
29 июня 2018, 23:50

Считается что резолв зависимостей не в корне компановки это плохая архитектура (ServiceLocator). Но у меня возникла задача по созданию объектов в цикле внутри сервиса.

Нужно создавать ITrainRecBuilder внутри цикла foreach. Нормально ли это?

foreach (var uit in inputDatas)
{
    using (var scope = _lifetimeScope.BeginLifetimeScope())         
    {
       var trainRecBuilder = scope.Resolve<ITrainRecBuilder>();
    }
}

GetCisRegSh - SingleInstance

IUsersRepository - SingleInstance

TrainRecService - InstancePerDependency

public class GetCisRegSh : GetSheduleAbstract
{
    private readonly IUsersRepository _usersRepository;
    private readonly TrainRecService _trainRecService;
    private readonly ILifetimeScope _lifetimeScope;
    public GetCisRegSh(IUsersRepository usersRepository,
                       TrainRecService trainRecService,
                       ILifetimeScope lifetimeScope) 
    {
        _usersRepository = usersRepository;
        _trainRecService = trainRecService;
        _lifetimeScope = lifetimeScope;
    }
    protected override async Task GetaDataRxEventHandler(Task<IEnumerable<UniversalInputType>> getDataTask)
    {
        try
        {
            //ПОЛУЧЕНИЕ ДАННЫХ--------------------------------------------------------
            var data = await getDataTask;
            var inputDatas = data as IList<UniversalInputType> ?? data.ToList();
            //СОЗДАНИЕ РАСПИСАНИЯ НА БАЗЕ ПОЛУЧЕННЫХ ДАННЫХ---------------------------
            var resultList = new List<TrainTableRec>();
            foreach (var uit in inputDatas)
            {
                using (var scope = _lifetimeScope.BeginLifetimeScope())               //РЕЗОЛВ ITrainRecBuilder
                {
                    var trainRecBuilder = scope.Resolve<ITrainRecBuilder>();
                    var trainRec = trainRecBuilder
                        .SetExternalData(uit)
                        .SetDirectionByName(uit.Direction.Name)
                        .SetStationsById(uit.StationArrival.Id, uit.StationDeparture.Id)
                        .SetAllByTypeId(uit.TrainTypeByRyle.Id)
                        .Build();
                    resultList.Add(trainRec);
                }
            }
            //ПЕРЕЗАПИСАТЬ РЕПОЗИТОРИЙ RemoteCis
            _trainRecService.ReWriteAll(resultList, TrainRecRepType.RemoteCis);
        }
        catch (Exception ex)
        {
            Console.WriteLine(ex.Message);
        }
    }
}
Answer 1

Нет, не нормально. Запрашивайте лучше Func<ITrainRecBuilder>. Или даже Func<Owned<ITrainRecBuilder>> если есть хоть какой-то шанс что реализация ITrainRecBuilder будет владеть какими-нибудь ресурсами.

private readonly Func<Owned<ITrainRecBuilder>> builderFactory;
// ...
using (var scope = builderFactory()) 
{
    var builder = scope.Value;
    // ...
}
READ ALSO
Получение данных подклассов XML C#

Получение данных подклассов XML C#

Есть класс td в нем классы tr, они все(tr) различают по значению class, нужно получить например XML

221
Ошибка - метод не объявлен в определении обобщенного типа

Ошибка - метод не объявлен в определении обобщенного типа

Я пытаюсь сгенерировать динамически следующую обобщенную функцию:

211
Как запустить анимацию по клику в Unity?

Как запустить анимацию по клику в Unity?

Есть 4 вида анимации для меню, созданы с помощью Anitamor в Unity

523
Преобразование штрих-кода в строку c#

Преобразование штрих-кода в строку c#

В общем я программно обрабатываю документы *xlsx и из нужных полей вынимаю нужные мне данные

221