Como você garante que seu contexto de banco de dados seja descartado corretamente quando sua coleção lenta não é mais necessária?

8

Estou procurando um tipo de resposta de práticas recomendadas aqui.

Dado que as práticas recomendadas para interagir com as classes implementadas IDisposablesão Usingfeitas através da declaração - Qual é a melhor prática para usar o carregamento lento EF com MVC?

Exemplo de método do controlador:

<HttpGet>
Public Function Schedule(ByVal id As Int64) As ActionResult

    Dim model As Schedule = Nothing
    Using database As dataContext = New dataContext
        model = (From s In database.Schedules Where s.ScheduleID = id Select s).FirstOrDefault
    End Using

    Return View(theSchedule)

End Function

Este exemplo faz com que o carregamento lento não funcione porque o banco de dados [dataContext] é descartado no momento em que o modelo chega na Visualização.

Portanto, acho que a pergunta é:
Quais são as práticas recomendadas para usar o carregamento lento no MVC? Como você garante que seu contexto de banco de dados seja descartado corretamente e que você não cause vazamentos de memória?

Sam Axe
fonte

Respostas:

9

Em geral, você não precisa usar Usinginstruções com contextos de dados do Entity Framework. Coleções preguiçosas é uma das razões. Portanto, seu código seria simplesmente:

<HttpGet>
Public Function Schedule(ByVal id As Int64) As ActionResult

    Dim model As Schedule = Nothing
    Dim database As dataContext = New dataContext
    model = (From s In database.Schedules Where s.ScheduleID = id Select s).FirstOrDefault

    Return View(model)

End Function

Os contextos de dados no Entity Framework são projetados para abrir e fechar conexões, conforme necessário, e se descartam automaticamente quando o objeto de contexto de dados não é mais necessário.

O comportamento padrão do DbContext é que a conexão subjacente seja aberta automaticamente sempre que necessário e fechada quando não for mais necessária. Por exemplo, quando você executa uma consulta e itera sobre os resultados da consulta usando "foreach", a chamada para IEnumerable.GetEnumerator () fará com que a conexão seja aberta e, quando mais tarde não houver mais resultados disponíveis, "foreach" cuidará da chamada Descarte no enumerador, que fechará a conexão.

A única vez em que você precisaria ter cuidado IDisposableé se você seguir Overrideos comportamentos padrão do contexto de dados.

Leitura adicional

Eu sempre tenho que chamar Dispose no DBContext? Não.
Gerenciando o DbContext da maneira certa com o Entity Framework 6: um guia detalhado

Robert Harvey
fonte
Não tenho certeza de que a segunda metade da quarta frase esteja correta: "e eles se descartam automaticamente quando o objeto de contexto de dados sai do escopo". Como o contexto dos dados fica fora do escopo no tempo em que está na Visualização, usando o seu exemplo, o contexto ainda estaria disponível e, portanto, não se descartaria? Estou esquecendo de algo?
Sam Ax
Não. Você está certo; Eu estava um pouco desleixado na minha redação. A descrição correta é que o DBContext se descarta quando não é mais necessário; isto é, a coleção lenta é totalmente enumerada ou abandonada. Veja minhas atualizações.
Robert Harvey
Muito obrigado por responder, Robert. Isso é muito apreciado.
Sam Ax
1
Observe que ter um DBContext que seja bem comportado sem uma usinginstrução torna muito mais agradável injetar dependência no DBContext, se desejado.
Robert Harvey
O DI é algo que examinarei em um futuro próximo - por isso vou manter isso em mente.
Sam Ax