StructureMap не использует контекст данных при использовании HttpContextScoped()

Моя цель - иметь один контекст данных (MainDbContext) для HTTP-запроса в ASP.NET MVC и распоряжаться контекстом данных, когда запрос заканчивается.

Я использую следующую конфигурацию StructureMap:

public static class ContainerConfigurer
{
    public static void Configure()
    {
        ObjectFactory.Initialize(x =>
        {
            x.For<MainDbContext>().HttpContextScoped();
        });
    }
}

Всякий раз, когда мне нужно MainDbContextЯ использую этот код:

var dbContext = ObjectFactory.GetInstance<MainDbContext>();

Это работает должным образом: для каждого HTTP-запроса создается только один контекст данных. Проблема в, MainDbContext не удаляется в конце запроса.

Как я могу настроить свой ObjectFactory для удаления контекста данных после завершения HTTP-запроса? Или это просто то, что мне нужно сделать вручную, используя Application_EndRequest() в Global.asax.

Обновить

Я просто попытался добавить следующий код в Global.asax:

protected virtual void Application_EndRequest()
{
    ObjectFactory.GetInstance<MainDbContext>().Dispose();
}

Как и ожидалось, это решает проблему. Мне все еще интересно, есть ли способ сделать это автоматически с StructureMap, как бы то ни было.

2 ответа

Решение

Вместо:

x.For<MainDbContext>().HttpContextScoped();

Пытаться:

x.For<MainDbContext>().HttpContextScoped().Use(() => new MainDbContext());

Также обычно это классы репозитория, которые нуждаются в контексте БД. Так что вместо ObjectFactory.GetInstance<MainDbContext>(); пусть ваши репозитории берут некоторый интерфейс БД интерфейса и настраивают StructureMap для внедрения MainDbContextв них. Затем заставьте StructureMap внедрить репозитории в контроллеры,...

В Application_EndRequest:

protected void Application_EndRequest()
{
    ObjectFactory.ReleaseAndDisposeAllHttpScopedObjects();
}

Использование вложенного контейнера - единственный способ получить Карту структуры для автоматической утилизации объектов. Если вы не используете эту технику, единственный способ состоит в том, чтобы самостоятельно расположить объекты, используя описанный OP-метод (вытащить объект из контейнера и утилизировать его; см. Этот пример NHibernate, чтобы узнать, как это сделать) или расширить область действия объекта. объект HttpRequest и вызов ReleaseAndDisposeAllHttpScopedObjects, как описано Дарином.

Другие вопросы по тегам