Captain Codeman Captain Codeman

Event-sourcing benefit: migrating between storage types

Contents

Introduction

Here’s an example of one benefit of Event Sourcing …

How much work would typically result from ”hey, we need to change platform and store our data in a different database …”? Even using NHibernate and going from one relational database to another, you’d potentially be looking at a significant piece of effort.

Now imagine instead trying to migrate between fundamentally different storage engines such as from SQL Server to Amazon S3 or from Oracle to MongoDB?!

Well, EventSourcing not only makes it possible, it also makes it trivially simple too.

Here’s an actual EventStore migrator implementation that took all of two minutes to write:

	var source = GetSourceEventStore();
	var destination = GetDestinationEventStore();

	foreach (var commit in source.GetFrom(StartDate))
		destination.Commit(commit);

Oh look, it’s done !! Ok, before you accuse me of being slow there is the event-store wire-up which is where one of the minutes went (I could add some XML DI configuration to make it really generic but it’s probably not worth the effort):

	private static IPersistStreams GetSourceEventStore()
	{
		return Wireup.Init()
			.UsingMongoPersistence("source", new DocumentObjectSerializer())
			.UsingSynchronousDispatcher()
				.PublishTo(new NullDispatcher())
			.Build()
			.Advanced;
	}

	private static IPersistStreams GetDestinationEventStore()
	{
		return Wireup.Init()
			.UsingSqlPersistence("destination")
				.WithDialect(new MsSqlDialect())
				.InitializeStorageEngine()
				.UsingBinarySerialization()
				.Compress()
			.UsingSynchronousDispatcher()
				.PublishTo(new NullDispatcher())
			.Build()
			.Advanced;
	}

BTW: The “source” and “destination” strings are the names of connection strings in the <connectionStrings> section of the config file.

Version 2 of the “EventStore Migrator Enterprise EditionTM” may add the ability to store the last commit DateTime migrated and then restart from there to enable incremental replication. A real-life version would also need a little exception handling and that would probably make use of the last DateTime to continue from the right point after any failure.

So, with a couple of minutes work you can easily migrate between different storage engines and also have a mechanism to incrementally keep them in sync - maybe for disaster recovery or backup where you use a lower cost / higher latency event store in an emergency (and still have a way to migrate back).

Event sourcing and immutable events makes all this possible.