Skip to content

Configuration

trailmax edited this page Nov 20, 2016 · 2 revisions

Configuration

Configuration for NSaga is basically configuring Dependency Injection container to insert correct components into SagaMediator.

Out of the box NSaga comes with internal DI container - TinyIoC. But the configuration of components should happen through SagaMediatorBuilder. If you already have a DI container, you can skip this section and read Integration With Other DI Containers.

Saga Mediator Builder

SagaMediatorBuilder is a wrapper around TinyIoC container with some specific API for registrations of NSaga components.

var builder = Wireup.UseInternalContainer();
var mediator = builder.ResolveMediator(); 

Assemblies To Scan

It scans currently loaded assemblies for saga classes. Usually this is enough for most needs, but you might want to scan only specific assemblies. You can repace the whole list or add only specific ones:

class ReplaceAssemblies
{
    public ReplaceAssemblies()
    {
        var builder = Wireup.UseInternalContainer()
                            .ReplaceAssembliesToScan(new Assembly[] { typeof(ReplaceAssemblies).Assembly })
                            .AddAssembliesToScan(new Assembly[] {typeof(VerySimpleSaga).Assembly});
    }
}

Saga Repository

The default configuration gives you only in-memory persistence: InMemorySagaRepository which uses static concurrent dictionaries. This will be erased when you restart your application. You can replace implementation of ISagaRepository with your own type:

var builder = Wireup.UseInternalContainer()
                    .UseRepository<DummySagaRepository>();

Message Serialiser

To replace the way messages are serialised you need to implement IMessageSerialiser and replace it in the builder:

var builder = Wireup.UseInternalContainer()
                    .UseMessageSerialiser<DummyMessageSerialiser>();

Saga Factories

You can replace the way sagas are resolved, though it will be strange to do it when using internal container, you can do it. Sagas are resolved by ISagaFactory and to replace the default you need to register type in builder:

var builder = Wireup.UseInternalContainer()
                    .UseSagaFactory<DummySagaFactory>();

Pipeline Hooks

You can add more pipeline hooks by implementing IPipelineHook. More about this in Pipeline Hooks. Add this into builder like this:

var builder = Wireup.UseInternalContainer()
                    .AddPiplineHook<DummyPipelineHook>();

Static Reference

If you are going to use sagas in more than one place, you can store your instance of SagaMediatorBuilder in global static reference: SagaMediatorBuilder.Current:

SagaMediatorBuilder.Current
                   .UseSqlServer()
                   .WithConnectionStringName("NSagaDatabase");

var sagaMediator = SagaMediatorBuilder.Current.ResolveMediator();

or assign to the static reference when the builder is configured:

var builder = Wireup.UseInternalContainer()
                    .UseRepository<DummySagaRepository>()
                    .UseMessageSerialiser<DummyMessageSerialiser>()
                    .UseSagaFactory<DummySagaFactory>();

SagaMediatorBuilder.Current = builder;

var sagaMediator = SagaMediatorBuilder.Current.ResolveMediator();

Interfaces

As you might have noticed there is a limited number of interfaces available to implment and replace:

  • IMessageSerialiser. By default provided JsonNetSerialiser. Used to serialise and deserialise messages and SagaData;
  • ISagaRepository. By default provided InMemorySagaRepository. Used to store saga states and saga headers. You can also use SqlSagaRepository
  • ISagaFactory. By default provided TinyIocSagaFactory. This is an abstraction around DI container to resolve saga instances, but this does not deal with saga state.
  • IEnumerable<IPipelineHook>. By default provided MetadataPipelineHook. This is an extension point to do any metadata modificaitons to sagas. See Pipeline Hooks for more information.