Windsor LifeStyle - Shared instance per Graph

前端 未结 2 371
抹茶落季
抹茶落季 2020-12-07 05:02

I have 2 types of ViewModel\'s

      public class ViewModelA 
      {
          IService service;
          private ViewModelB childViewModel; 

                  


        
相关标签:
2条回答
  • 2020-12-07 05:14

    You may be able to use Scoped Lifestyles. Here's an example of some unit tests that seem to do what you want:

    [Fact]
    public void VMsInSameScopeSharesService()
    {
        var container = new WindsorContainer();
        container.Register(Component.For<ViewModelA>().LifestyleTransient());
        container.Register(Component.For<ViewModelB>().LifestyleTransient());
        container.Register(Component
            .For<IService>().ImplementedBy<NullService>().LifestyleScoped());
    
        using (container.BeginScope())
        {
            var a = container.Resolve<ViewModelA>();
    
            Assert.Equal(a.service, a.childViewModel.service);
        }
    }
    
    [Fact]
    public void VMsInDifferentScopesDoNotShareServices()
    {
        var container = new WindsorContainer();
        container.Register(Component.For<ViewModelA>().LifestyleTransient());
        container.Register(Component.For<ViewModelB>().LifestyleTransient());
        container.Register(Component
            .For<IService>().ImplementedBy<NullService>().LifestyleScoped());
    
        IService service1;
        using (container.BeginScope())
        {
            var a = container.Resolve<ViewModelA>();
    
            service1 = a.service;
        }
        IService service2;
        using (container.BeginScope())
        {
            var a = container.Resolve<ViewModelA>();
    
            service2 = a.service;
        }
    
        Assert.NotEqual(service1, service2);
    }
    

    However, this is quite an exotic requirement, which makes me wonder why you want it to behave exactly like this, or if you couldn't structure your code in a way that would make this simpler.

    0 讨论(0)
  • 2020-12-07 05:34

    What worked for me is using : LifeStyle BoundTo

        container.Register(Component.For<IService>()
                .ImplementedBy<Service>()
                .LifeStyle.BoundTo<ViewModelA>());
    

    Graph :

         public class ViewModelAConductor 
         {
             private List<ViewModelA> rootViewModels = new List<ViewModelA>();
             public ViewModelAConductor()
             {
                  ViewModelA a1 = container.Resolvce<ViewModelA>(); 
                  rootViewModels.Add(a1);
    
                  ViewModelA a2 = container.Resolvce<ViewModelA>(); 
                  rootViewModels.Add(a2); 
             }
         }
    
         public class ViewModelA
         {
              ViewModelB viewModelB;
              IService service;
    
              public ViewModelA(IService service,ViewModelB viewModelB) 
              {
                  this.service = service;
                  this.viewModelB = viewModelB;
              }               
         }
    
         public class ViewModelB
         {
              ViewModelC viewModelC;
              IService service;
    
              public ViewModelA(IService service,ViewModelC viewModelC) 
              {
                  this.service = service;
                  this.viewModelC = viewModelC;
              }               
         }  
    
         public class ViewModelC
         {
              IService service;
    
              public ViewModelA(IService service) 
              {
                  this.service = service;                 
              }               
         }  
    

    All ViewModels injected under the Graph of a1 have the same instance of IService.

    All ViewModels injected under the Graph of a2 have the same instance of IService.

    0 讨论(0)
提交回复
热议问题