Ayende has a good example of this approach in this blog post. His example is shown below with my comments.
As the Configuration is expensive to create, it is created only once per test run. A SQLite in-memory database is used as this is the fastest way to do queries.
public class InMemoryDatabaseTest : IDisposable
{
private static Configuration Configuration;
private static ISessionFactory SessionFactory;
protected ISession session;
public InMemoryDatabaseTest(Assembly assemblyContainingMapping)
{
if (Configuration == null)
{
Configuration = new Configuration()
.SetProperty(Environment.ReleaseConnections,"on_close")
.SetProperty(Environment.Dialect, typeof (SQLiteDialect).AssemblyQualifiedName)
.SetProperty(Environment.ConnectionDriver, typeof(SQLite20Driver).AssemblyQualifiedName)
.SetProperty(Environment.ConnectionString, "data source=:memory:")
.SetProperty(Environment.ProxyFactoryFactoryClass, typeof (ProxyFactoryFactory).AssemblyQualifiedName)
.AddAssembly(assemblyContainingMapping);
SessionFactory = Configuration.BuildSessionFactory();
}
session = SessionFactory.OpenSession();
new SchemaExport(Configuration).Execute(true, true, false, true, session.Connection, Console.Out);
}
public void Dispose()
{
session.Dispose();
}
}
When using this, each test starts by creating required data.
public class BlogTestFixture : InMemoryDatabaseTest
{
public BlogTestFixture() : base(typeof(Blog).Assembly)
{
}
[Fact]
public void CanSaveAndLoadBlog()
{
object id;
using (var tx = session.BeginTransaction())
{
id = session.Save(new Blog
{
AllowsComments = true,
CreatedAt = new DateTime(2000,1,1),
Subtitle = "Hello",
Title = "World",
});
tx.Commit();
}
session.Clear();
using (var tx = session.BeginTransaction())
{
var blog = session.Get<Blog>(id);
Assert.Equal(new DateTime(2000, 1, 1), blog.CreatedAt);
Assert.Equal("Hello", blog.Subtitle);
Assert.Equal("World", blog.Title);
Assert.True(blog.AllowsComments);
tx.Commit();
}
}
}