使用Signalr,asp.net Core和sql依赖注入在浏览器上显示实时数据库更改

时间:2019-07-23 13:31:24

标签: c# asp.net-core signalr-hub sqldependency asp.net-core-signalr

嗨,我是SignalR和asp.net核心的新手,我的潜在问题是我希望用户能够实时查看对数据库所做的更改。我有一个使用signalr和asp.net框架工作代码的示例,但是当我尝试将其转换为asp内核时,由于我的集线器而失败。我很确定问题是非常直接的,但是网上的其他一些例子都超出了我目前的深度。

cushub.cs:

public class CusHub : Hub
    {
        public static void Show()
        {
           //The below code is what doesn't work in aspcore. This is what i'm struggling with.
            IHubContext context = GlobalHost.ConnectionManager.GetHubContext<CusHub>();
            context.Clients.All.displayCustomer();
        }
    }

customercontroller.cs

public JsonResult Get()
{

    using (var connection = new SqlConnection(ConfigurationManager.ConnectionStrings["MyConnectionString"].ConnectionString))
    {
        connection.Open();
        using (SqlCommand command = new SqlCommand(@"SELECT [Id],[CustId],[CustName] FROM [dbo].[ad.signalr] WHERE [Status] <> 0", connection))
        {
            command.Notification = null;

            SqlDependency dependency = new SqlDependency(command);
            dependency.OnChange += new OnChangeEventHandler(dependency_OnChange);

            if (connection.State == ConnectionState.Closed)
                connection.Open();

            SqlDataReader reader = command.ExecuteReader();

            var listCus = reader.Cast<IDataRecord>()
                    .Select(x => new
                    {
                        Id = (int)x["Id"],
                        CusId = (string)x["CustId"],
                        CusName = (string)x["CustName"],
                    }).ToList();

            return Json(new { listCus = listCus });

        }
    }
}

private void dependency_OnChange(object sender, SqlNotificationEventArgs e)
{
    CusHub.Show();
}

客户视图

@Html.Hidden("Get", Url.Action("Get", "Customer"))

<table class="table">
    <thead>
        <tr>
            <th>Id</th>
            <th>Customer Id</th>
            <th>Customer Name</th>
        </tr>
    </thead>

    <tbody id="tblInfo"></tbody>
</table>

signalr js文件

$(function () {

    var cus = $.connection.cusHub;

    cus.client.displayCustomer = function () {
        getData();
    };

    $.connection.hub.start();
    getData();
});

function getData() {
    var $tbl = $('#tblInfo');
    $.ajax({
        url: $("#Get").val(),
        type: 'GET',
        datatype: 'json',
        success: function (data) {
            $tbl.empty();

            $.each(data.listCus, function (i, model) {
                $tbl.append
                    (
                        '<tr>' +
                        '<td>' + model.Id + '</td>' +
                        '<td>' + model.CusId + '</td>' +
                        '<td>' + model.CusName + '</td>' +
                        '<tr>'
                    );
            });
        }
    });
}

代码在我的集线器中没有抛出任何异常。 与:

GlobalHost.ConnectionManager.GetHubContext<CusHub>()
context.Clients.All.displayCustomer();


Iclientproxy does not contain a definition for displayCustomer();

我知道signalrcore进行了一些更改,但是是否有一个简单的修复程序可以使它运行起来?

上面的代码在asp.net框架中工作

感谢您的帮助

1 个答案:

答案 0 :(得分:0)

如果您有displayCustomer()方法,我假设您正在使用Strongly typed hub。请查看该文档中的示例,该示例将使您走上正确的道路。但是,我立即看到了几个问题:

首先,您需要更改CusHub的声明以从Hub<T>派生,其中T是您定义SignalR客户端将接受的方法的接口。因此,如果将其称为ICusHub,那么您将拥有类似这样的内容:

public class CusHub : Hub<ICusHub>

第二,您不需要获得context。它在您的Hub类中已经可用。因此,您所需要做的就是这个:

await Clients.All.displayCustomer();