2017-03-17 41 views
1

SimpleInjectorContainerAdapter是否支持通過SimpleInjector容器註冊的Sagas,使用下面的代碼我總是得到異常;SimpleInjectorContainerAdapter,註冊Sagas

型RebusPlaypen.MyMessageA,RebusPlaypen不能被分派到任何HANDL ERS ​​

下面的代碼演示了這個問題。這可能是因爲我錯誤地實施了Saga註冊,還是SimpleInjectorContainerAdapter不支持這種類型的註冊?

using Rebus.Bus; 
using Rebus.Config; 
using Rebus.Handlers; 
using Rebus.Retry.Simple; 
using Rebus.Routing.TypeBased; 
using Rebus.Sagas; 
using Rebus.SimpleInjector; 
using Rebus.Transport.InMem; 
using SimpleInjector; 
using System; 
using System.Threading.Tasks; 

// Rebus.3.1.2 
// Rebus.SimpleInjector.3.0.0 

namespace RebusPlaypen 
{ 
    public interface IMyDependency 
    { 
      void DoSomethingGood(); 
    } 

    public class MyDependency : IMyDependency 
    { 
      public void DoSomethingGood() 
      { 
       Console.WriteLine("I've done something"); 
      } 
    } 

    public class MyMessageA 
    { 
      public Guid CollationId { get; set; } 
      public string FaveIceCreamFlavour { get; set; } 
    } 

    public class MyMessageB 
    { 
      public Guid CollationId { get; set; } 
      public string FaveBand{ get; set; } 
    } 

    public class MyMessageSagaData : ISagaData 
    { 
      public Guid Id {get;set;} 
      public int Revision {get;set;} 
      public Guid CollationId {get;set;} 
      public bool HasFaveBand { get; set; } 
    } 

    public interface IMyMessageSaga : IAmInitiatedBy<MyMessageA>, 
      IHandleMessages<MyMessageB> 
    { 
    } 

    public class MyMessageSaga: Saga<MyMessageSagaData>, 
      IMyMessageSaga 
    { 
      readonly IMyDependency _myDependency; 
      readonly IBus _bus; 

      public MyMessageSaga(IMyDependency myDependency, 
       IBus bus) 
      { 
       _myDependency = myDependency; 
       _bus = bus; 
      } 

      protected override void CorrelateMessages(ICorrelationConfig<MyMessageSagaData> config) 
      { 
       config.Correlate<MyMessageA>(s => s.CollationId, d => d.CollationId); 
       config.Correlate<MyMessageB>(s => s.CollationId, d => d.CollationId); 
      } 

      public async Task Handle(MyMessageA message) 
      { 
       Console.WriteLine("Handled MyMessageA"); 
       _myDependency.DoSomethingGood(); 
       await _bus.Send(new MyMessageB { CollationId = message.CollationId, FaveBand = "Depeche Mode" }); 
       await PossiblyPerformCompleteAction(); 
      } 

      public async Task Handle(MyMessageB message) 
      { 
       Console.WriteLine("Handled MyMessageB"); 
       _myDependency.DoSomethingGood(); 
       Data.HasFaveBand = true; 
       await PossiblyPerformCompleteAction(); 
      } 

      async Task PossiblyPerformCompleteAction() 
      { 
       if (Data.HasFaveBand) 
       { 
        MarkAsComplete(); 
       } 
      } 
    } 

    public static class RebusSimpleInjectorSagaDemo 
    { 
      public static void Run() 
      { 
       var container = new Container(); 
       container.Register<IMyDependency, MyDependency>(); 
       container.Register<MyMessageSaga>(Lifestyle.Transient); 
       container.Register<IMyMessageSaga>(() => container.GetInstance<MyMessageSaga>(), Lifestyle.Transient); 

       var network = new InMemNetwork(true); 
       var adapter = new SimpleInjectorContainerAdapter(container); 

       var _bus = Configure 
        .With(adapter) 
        .Logging(l => l.ColoredConsole(Rebus.Logging.LogLevel.Error)) 
        .Transport(t => t.UseInMemoryTransport(network,"my_nice_queue")) 
        .Routing(r => r.TypeBased().MapAssemblyOf<MyMessageA>("my_nice_queue")) 
        .Options(o => 
        { 
          o.SetNumberOfWorkers(1); 
          o.SetMaxParallelism(1); 
          o.SimpleRetryStrategy(maxDeliveryAttempts: 1); 
        }) 

        .Start(); 

       container.Verify(); 

       _bus.Send(new MyMessageA { CollationId = Guid.NewGuid(), FaveIceCreamFlavour = "Strawberry" }).Wait(); 

       Console.WriteLine("Running"); 
       Console.ReadLine(); 
      } 
    } 
} 

回答

0

不,你使用的IoC容器的事情,你必須確保你的處理程序是由IHandleMessages<TMessage>實現他們提供的解決。

如果嘗試

container.GetAllInstances<IHandleMessages<MyMessageA>>(); 

container.GetAllInstances<IHandleMessages<MyMessageB>>(); 

,你會看到沒有處理程序返回。這就是爲什麼Rebus找不到任何處理程序來發送消息到:)

+0

感謝您的信息,但仍然有這個問題。如果我爲容器添加以下注冊,那麼仍然會得到相同的異常; \t \t \t \t container.Register ,MyMessageSaga>(); \t \t \t \t container.Register ,MyMessageSaga>(); –

+0

以下注冊允許此工作: - container.RegisterCollection(typeof(IHandleMessages <>),new [] {Assembly.GetExecutingAssembly()}); –

1

爲了完整,以下更改允許原始問題中的代碼與Simple Injector容器正常工作;

public static class RebusSimpleInjectorSagaDemo 
{ 
     public static void Run() 
     { 
      var container = new Container(); 
      container.Register<IMyDependency, MyDependency>(); 

      // The missing registration 
      container.RegisterCollection(typeof(IHandleMessages<>), new [] {Assembly.GetExecutingAssembly()});** 

      var network = new InMemNetwork(true); 
      var adapter = new SimpleInjectorContainerAdapter(container); 

      var _bus = Configure 
       .With(adapter) 
       .Logging(l => l.ColoredConsole(Rebus.Logging.LogLevel.Error)) 
       .Transport(t => t.UseInMemoryTransport(network,"my_nice_queue")) 
       .Routing(r => r.TypeBased().MapAssemblyOf<MyMessageA>("my_nice_queue")) 
       .Options(o => 
       { 
         o.SetNumberOfWorkers(1); 
         o.SetMaxParallelism(1); 
         o.SimpleRetryStrategy(maxDeliveryAttempts: 1); 
       }) 

       .Start(); 

      container.Verify(); 
      _bus.Send(new MyMessageA { CollationId = Guid.NewGuid(), FaveIceCreamFlavour = "Strawberry" }).Wait(); 

      Console.WriteLine("Running"); 
      Console.ReadLine(); 
     } 
}