asp.net-mvc – 具有持久HTTP连接的IDbConnection生命周期管理

前端之家收集整理的这篇文章主要介绍了asp.net-mvc – 具有持久HTTP连接的IDbConnection生命周期管理前端之家小编觉得挺不错的,现在分享给大家,也给大家做个参考。
当我的ASP.NET MVC应用程序中存在持久HTTP连接(如SignalR集线器)时,我在管理具有作用于HttpContext的StructureMap的开放数据库连接的生命周期时遇到问题.

我的DI容器StructureMap将一个打开的IDbConnection注入到多个服务中.为确保关闭并正确处理这些数据库连接,我在EndRequest事件上调用ObjectFactory.ReleaseAndDisposeAllHttpScopedObjects().

这对于MVC控制器非常有用,直到需要数据库连接的服务注入到SignalR集线器中,从而为每个客户端保持持久的HTTP连接,并最终使连接池饱和.

如果我将IDbConnection范围限定为单例,则每个应用程序只打开一个连接,并且池不会饱和,但如果连接被锁定或超时,则为a bad idea.

那么也许有一种方法可以自定义SignalR集线器的数据库连接范围?我尝试在每个Hub方法中解析服务实例,但这仍然在HttpContext范围内实例化数据库连接,并在调用客户端的集线器连接期间保持打开状态.

当存在持久的HTTP连接时,如何在HTTP范围的上下文中管理与StructureMap的数据库连接的生命周期?

示例代码

典型服务

public class MyService
{
    private IDbConnection _con;
    public MyService(IDbConnection con)
    {
        _con = con;
    }

    public IEnumerable<string> GetStuff()
    {
        return _con.Select<string>("SELECT someString FROM SoMetable").ToList();
    }
}

典型的SignalR Hub

public class MyHub : Hub
{
    private MyService _service;
    public MyHub(MyService service)
    {
        _service = service; // Oh Noes! This will open a database connection
                            // for each Client because of HttpContext scope
    }

    public Task AddMessage()
    {
        var result = _service.GetStuff();
        // ...
    }
}

StructureMap配置

For<IDbConnection>()
    .HybridHttpOrThreadLocalScoped()
    .Use(() => BaseController.GetOpenConnection(MyConnectionString));

的Global.asax.cs

public class GlobalApplication : System.Web.HttpApplication
{
    public GlobalApplication()
    {
        EndRequest += delegate
        {
            ObjectFactory.ReleaseAndDisposeAllHttpScopedObjects();
        };
    }
    // ...
 }

解决方法

在SignalR 1.0.0 Alpha中,Hub的实现IDisposable.与HttpContext不同,SignalR Hub实例是短暂的,因此如果您在Hub的Dispose方法关闭IDbConnection,则不应该不必要地使连接池饱和.

猜你在找的asp.Net相关文章