AI agents: use the documentation index at llms.txt to locate machine-readable pages. This section is indexed by https://docs.particular.net/persistence/llms.txt. The markdown version of this page is served as plain text. An MCP server at /mcp serves the same content via the search_docs and read_doc tools; it is read-only and needs no credentials. Markdown versions of documentation pages are available by appending .md to the page URL. Directory URLs use index.md. They are served as text/plain because some retrieval backends reject text/markdown.

Accessing data via NHibernate persistence

NuGet Package:
NServiceBus.NHibernate 8.x
Target Version:
NServiceBus 7.x
Standard support for version 7.x of NServiceBus has expired. For more information see our Support Policy.

NHibernate persistence supports a mechanism that allows using the same data context used by NServiceBus internals to also store business data. This ensures atomicity of changes across the handlers and sagas that process the same message. See accessing data to learn more about other ways of accessing the data in the handlers.

The NServiceBus-managed ISession instance can be accessed using the handler context through context.SynchronizedStorageSession.Session() or by using dependency injection.

Using in a handler

public class OrderHandler :
    IHandleMessages<OrderMessage>
{
    public Task Handle(OrderMessage message, IMessageHandlerContext context)
    {
        var nhibernateSession = context.SynchronizedStorageSession.Session();
        nhibernateSession.Save(new Order());
        return Task.CompletedTask;
    }
}
public class OrderHandler :
    IHandleMessages<OrderMessage>
{
    INHibernateStorageSession synchronizedStorageSession;

    public OrderHandler(INHibernateStorageSession synchronizedStorageSession)
    {
        this.synchronizedStorageSession = synchronizedStorageSession;
    }

    public Task Handle(OrderMessage message, IMessageHandlerContext context)
    {
        synchronizedStorageSession.Session.Save(new Order());
        return Task.CompletedTask;
    }
}
config.RegisterComponents(c =>
{
    c.ConfigureComponent(b =>
    {
        var session = b.Build<INHibernateStorageSession>();
        var repository = new MyRepository(session.Session);
        return repository;
    }, DependencyLifecycle.InstancePerUnitOfWork);
});

Using in a saga

If the situation is special enough to warrant going against this recommendation, the following documentation will describe how to do so.

public class OrderSaga :
    Saga<OrderSaga.SagaData>,
    IHandleMessages<OrderMessage>
{
    public Task Handle(OrderMessage message, IMessageHandlerContext context)
    {
        var nhibernateSession = context.SynchronizedStorageSession.Session();
        nhibernateSession.Save(new Order());
        return Task.CompletedTask;
    }

Regardless of how the ISession object is accessed, it is fully managed by NServiceBus according to the best practices defined by NServiceBus documentation with regard to transactions.

Related Articles