Разрешение зависимостей интерфейса по имени в Prism WPF - PullRequest
0 голосов
/ 16 февраля 2019

У меня есть требование, когда мне нужно 3 экземпляра ZmqService, совместно используемых на разных страницах приложения.Для этого я зарегистрировал интерфейс IZmqService, как показано ниже, с отдельными именами: -

container.RegisterInstance<IZmqService>("liveViewCaptureService", new ZmqService());
container.RegisterInstance<IZmqService>("faceMatchCaptureService", new ZmqService());
container.RegisterInstance<IZmqService>("captureServiceTrigger", new ZmqService());

Теперь для моих viewModels я решил так: -

IZmqService liveViewCaptureService = container.Resolve<IZmqService>("liveViewCaptureService");
IZmqService faceMatchCaptureService = container.Resolve<IZmqService>("faceMatchCaptureService");
IZmqService captureServiceTrigger = container.Resolve<IZmqService>("captureServiceTrigger");

container.RegisterType<IManualVerificationPageViewModel, ManualVerificationPageViewModel>(
               new PerResolveLifetimeManager(),
               new InjectionConstructor(
                   new InjectionParameter<IRegionManager>(container.Resolve<IRegionManager>()),
                   new InjectionParameter<IEventAggregator>(container.Resolve<IEventAggregator>()),
                   new InjectionParameter<IDialogService>(container.Resolve<IDialogService>()),
                   new InjectionParameter<ICaptureService>(container.Resolve<ICaptureService>()),
                   new InjectionParameter<IAppConfiguration>(container.Resolve<IAppConfiguration>()),
                   new InjectionParameter<IMessageQueueService>(container.Resolve<IMessageQueueService>()),
                   new InjectionParameter(liveViewCaptureService),
                   new InjectionParameter(faceMatchCaptureService)
                   )
               );

В моем XAML,Я установил prism:ViewModelLocator.AutoWireViewModel="True"

Конструктор моей модели вида: -

public ManualVerificationPageViewModel(
            IRegionManager regionManager,
            IEventAggregator eventAggregator,
            IDialogService dialogService,
            ICaptureService captureService,
            IAppConfiguration appConfiguration,
            IMessageQueueService messageQueueService,
            IZmqService liveViewCaptureService,
            IZmqService faceMatchCaptureService
            )
        {
            _regionManager = regionManager;
            _eventAggregator = eventAggregator;
            _dialogService = dialogService;
            _captureService = captureService;
            _appConfiguration = appConfiguration;
            _messageQueueService = messageQueueService;

            _liveViewCaptureService = liveViewCaptureService;
            _faceMatchCaptureService = faceMatchCaptureService;

            SelectIdentityCommand = new DelegateCommand(DoSelectIdentity);
            VerifyCommand = new DelegateCommand(DoVerify, CanVerify)
                .ObservesProperty(() => SelectedIdentityType)
                .ObservesProperty(() => IdentityNumber);

            CancelCommand = new DelegateCommand(DoCancel);
            RecaptureCommand = new DelegateCommand(DoRecapture);
        }

Если я попытаюсь разрешить ViewModel в моем App.xaml.cs, как показано ниже,

IManualVerificationPageViewModel vm = container.Resolve<IManualVerificationPageViewModel>();

Я получаю действительную ViewModel.Но когда AutoWire происходит на моей странице, выдает следующее сообщение об ошибке: -

ResolutionFailedException: Resolution of the dependency failed, type = 'NEC.AAI.EGate.Checkin.ViewModels.ManualVerificationPageViewModel', name = '(none)'.
Exception occurred while: while resolving.
Exception is: InvalidOperationException - The current type, NEC.AAI.EGate.Services.IZmqService, is an interface and cannot be constructed. Are you missing a type mapping?
-----------------------------------------------
At the time of the exception, the container was: 
  Resolving NEC.AAI.EGate.Checkin.ViewModels.ManualVerificationPageViewModel,(none)
  Resolving parameter 'liveViewCaptureService' of constructor NEC.AAI.EGate.Checkin.ViewModels.ManualVerificationPageViewModel(Prism.Regions.IRegionManager regionManager, Prism.Events.IEventAggregator eventAggregator, NEC.AAI.EGate.UI.Common.Services.IDialogService dialogService, NEC.AAI.EGate.Services.ICaptureService captureService, NEC.AAI.EGate.Services.IAppConfiguration appConfiguration, NEC.AAI.EGate.Services.MessageQueue.IMessageQueueService messageQueueService, NEC.AAI.EGate.Services.IZmqService liveViewCaptureService, NEC.AAI.EGate.Services.IZmqService faceMatchCaptureService)
    Resolving NEC.AAI.EGate.Services.IZmqService,(none)

AutoWire работает нормально, если я регистрирую такой тип IZmqService, как это: -

IZmqService liveViewCaptureService = container.Resolve<IZmqService>("liveViewCaptureService");
IZmqService faceMatchCaptureService = container.Resolve<IZmqService>("faceMatchCaptureService");
IZmqService captureServiceTrigger = container.Resolve<IZmqService>("captureServiceTrigger");

container.RegisterType<IZmqService, ZmqService>(new InjectionConstructor());

НО этосоздает новый экземпляр IZmqService для каждого параметра конструктора вместо использования зарегистрированных типов.

Что я здесь не так делаю?

1 Ответ

0 голосов
/ 16 февраля 2019

Хорошо.Я получил разрешение.

Что я делал, так это регистрировал мой интерфейс в модели представления, и между AutoWireViewModel и интерфейсом не было никакой связи.

Все, что мне нужно было сделать, это изменить его на: -

container.RegisterType<ManualVerificationPageViewModel>(
                   new PerResolveLifetimeManager(),
                   new InjectionConstructor(
                       new InjectionParameter<IRegionManager>(container.Resolve<IRegionManager>()),
                       new InjectionParameter<IEventAggregator>(container.Resolve<IEventAggregator>()),
                       new InjectionParameter<IDialogService>(container.Resolve<IDialogService>()),
                       new InjectionParameter<ICaptureService>(container.Resolve<ICaptureService>()),
                       new InjectionParameter<IAppConfiguration>(container.Resolve<IAppConfiguration>()),
                       new InjectionParameter<IMessageQueueService>(container.Resolve<IMessageQueueService>()),
                       new InjectionParameter(container.Resolve<IZmqService>("liveViewCaptureService")),
                       new InjectionParameter(container.Resolve<IZmqService>("faceMatchCaptureService"))
                       )
                   );

и все заработало нормально.Я все еще ищу, как связать интерфейс, представление и модель представления вместе.Выложу как только узнаю.

...