1.使用SignalR实现页面即时刷新(服务端主动推送)
模块功能说明:
实现技术:sqlserver,MVC,WebAPI,ADO.NET,SignalR(服务器主动推送)
特殊车辆管理--->移动客户端采集数据存入数据库---->只要数据库数据有变化,服务端自动推送到Wbe页面展示(区别于传统的web请求)-->审核人员审核数据-->返回审核结果给移动客户端
在开发之前搜索了大量文档,也在QQ群咨询过群里的大牛,不少人都感觉比较懵逼的样子。有人建议使用ajax中的长连接,轮询等技术,最终还是决定使用SignalR技术实现页面刷新的效果:
搜索了不少博客园大牛有关于使用SignakR的博客,最后终于找到一个,也是我目前在项目中实现功能的Demo。
以下内容转自博客园园友杨根祥,感谢大牛提供资料,在此借鉴,如有不妥,请联系删除。
原博客中的代码在项目使用中有问题,已在下面代码中解决。
测试环境
.net 4.6
vs2015
mvc5
sqlserver2008
1.数据库
CREATE TABLE [dbo].[CarInfo](
[ID] [int] IDENTITY(1,1) NOT NULL,
[CarNo] [varchar](50) NOT NULL,
[Lng] [varchar](50) NOT NULL,
[Lat] [varchar](50) NOT NULL,
[LocDt] [datetime] NOT NULL,
CONSTRAINT [PK_CarInfo] PRIMARY KEY CLUSTERED
(
[ID] ASC
)WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON) ON [PRIMARY]
) ON [PRIMARY]
Go
数据库要使用service broker
ALTER DATABASE DBName SET NEW_BROKER WITH ROLLBACK IMMEDIATE;
ALTER DATABASE DBName SET ENABLE_BROKER;
初始化数据库
INSERT INTO CARINFO (CARNO,LNG,LAT,LOCDT) VALUES ('豫A12345','113.123','43.123',GETDATE())
2.新建MVC项目
安装SignalR包
Install-Package Microsoft.AspNet.SignalR
修改startup.cs
public partial class Startup
{
public void Configuration(IAppBuilder app)
{
ConfigureAuth(app);
app.MapSignalR();
}
}
修改web.config,增加数据库连接字符串
<add name="ConnString" connectionString="data source=.;initial catalog=MySignalR;persist security info=True;user id=sa;password=yourpass;" providerName="System.Data.SqlClient" />
增加数据模
public class CarInfo
{
public int ID { get; set; }
public string CarNo { get; set; }
public string Lng { get; set; }
public string Lat { get; set; }
public DateTime LocDt { get; set; }
}
新建类
public class CarInfoHub : Microsoft.AspNet.SignalR.Hub
{
public static void Show()
{
IHubContext context = GlobalHost.ConnectionManager.GetHubContext<CarInfoHub>();
context.Clients.All.displayStatus();
}
}
业务实现
public class CarInfoRepository
{
public CarInfo GetData(int id)
{
using (var connection = new SqlConnection(ConfigurationManager.ConnectionStrings["ConnString"].ConnectionString))
{
connection.Open();
using (SqlCommand command = new SqlCommand($"SELECT [ID],[CarNo],[Lng],[Lat],[LocDt] FROM [dbo].[CarInfo] WHERE ID = {0}", connection))
{
command.Notification = null;
SqlDependency dependency = new SqlDependency(command);
dependency.OnChange += dependency_OnChange;
if (connection.State == ConnectionState.Closed)
connection.Open();
using (var reader = command.ExecuteReader())
{
while (reader.Read())
{
return new CarInfo()
{
ID = reader.GetInt32(0),
CarNo = reader.GetString(1),
Lng = reader.GetString(2),
Lat = reader.GetString(3),
LocDt = reader.GetDateTime(4)
};
}
}
}
}
return null;
}
private void dependency_OnChange(object sender, SqlNotificationEventArgs e)
{
CarInfoHub.Show();
}
}
修改Global.asax
protected void Application_Start()
{
GlobalConfiguration.Configure(WebApiConfig.Register);
SqlDependency.Start(ConfigurationManager.ConnectionStrings["ConnString"].ConnectionString);
AreaRegistration.RegisterAllAreas();
FilterConfig.RegisterGlobalFilters(GlobalFilters.Filters);
RouteConfig.RegisterRoutes(RouteTable.Routes);
BundleConfig.RegisterBundles(BundleTable.Bundles);
}
protected void Application_End(object sender, EventArgs e)
{
SqlDependency.Stop(ConfigurationManager.ConnectionStrings["ConnString"].ConnectionString);
}
新建API
public class DefaultController : ApiController
{
readonly CarInfoRepository _repository = new CarInfoRepository();
// GET api/values
public CarInfo Get(int id)
{
return _repository.GetData(id);
}
}
修改控制器
public ActionResult Index()
{
//这里只是测试功能,指定了车辆编号
ViewBag.ID = 1;
return View();
}
修改视图
@{
Layout = null;
}
<!DOCTYPE html>
<html>
<head>
<meta name="viewport" content="width=device-width" />
<title>车辆实时跟踪</title>
<script src="~/Scripts/jQuery-1.10.2.min.js"></script>
<script src="~/Scripts/jquery.signalR-2.2.1.min.js"></script>
<script src="~/signalr/hubs" type="text/JavaScript"></script>
<script type="text/javascript">
var maxID;
$(function () {
var CarID = @ViewBag.ID;
// Proxy created on the fly
var job = $.connection.carInfoHub;
// Declare a function on the job hub so the server can invoke it
job.client.displayStatus = function () {
getData();
};
// Start the connection
$.connection.hub.start();
getData();
});
function getData() {
var $tbl = $('#tblJobInfo');
$.ajax({
url: '../api/Default/'+CarID,
type: 'GET',
datatype: 'json',
success: function (data) {
$tbl.empty();
$tbl.append(' <tr><th>ID</th><th>CarNo</th><th>Lng</th><th>Lat</th></tr>');
var str ='<tr><td>' + data.ID + '</td><td>' + data.CarNo + '</td><td>' + data.Lng + '</td><td>' + data.Lat + '</td></tr>';
$tbl.append(str);
}
});
}
</script>
</head>
<body>
<div>
<table id="tblJobInfo" style="text-align: center; margin-left: 10px">
</table>
</div>
</body>
</html>
现在测试一下
update carinfo set
Lng = CAST(Lng as float)+0.0001,
Lat = CAST(Lat as float)+0.0001,
LocDt = getdate();
面页数据可以实时发生变化。
下一步:使用 BootStrap框架中的Table展示数据,实现数据绑定,动态刷新。
1.使用SignalR实现页面即时刷新(服务端主动推送)的更多相关文章
- 使用SignalR从服务端主动推送警报日志到各种终端(桌面、移动、网页)
微信公众号:Dotnet9,网站:Dotnet9,问题或建议:请网站留言, 如果对您有所帮助:欢迎赞赏. 使用SignalR从服务端主动推送警报日志到各种终端(桌面.移动.网页) 阅读导航 本文背景 ...
- 使用SignalR实现页面即时刷新(服务端主动推送)
模块功能说明: 实现技术:sqlserver,MVC,WebAPI,ADO.NET,SignalR(服务器主动推送) 特殊车辆管理--->移动客户端采集数据存入数据库---->只要数据库数 ...
- 使用SignalR实现服务端消息推送
概述 这篇文章参考的是Server Broadcast with SignalR 2这篇教程,很不错的一篇教程,如果有兴趣的话可以查看原文,今天记录下来作为一个学习笔记,这样今后翻阅会更方便一点. 这 ...
- Asp.net SignalR 实现服务端消息推送到Web端
之前的文章介绍过Asp.net SignalR, ASP .NET SignalR是一个ASP .NET 下的类库,可以在ASP .NET 的Web项目中实现实时通信. 今天我 ...
- SignalR Self Host+MVC等多端消息推送服务(1)
一.概述 由于项目需要,最近公司项目里有个模块功能,需要使用到即时获得审批通知:原本的设计方案是使用ajax对服务器进行定时轮询查询,刚刚开始数据量和使用量不大的时候还好,后来使用量的增加和系统中各种 ...
- ASP.NET SignalR 系列(七)之服务端触发推送
前面几章讲的都是从客户端触发信息推送的,但在实际项目中,很多信息可能是由系统服务端推送的,下面2图分别展示两种通道 客户端触发推送 服务端推送 下面我们就重点介绍下服务端如何调用集线器的对象进行推送 ...
- SignalR 实现web浏览器客户端与服务端的推送功能
SignalR 是一个集成的客户端与服务器库,基于浏览器的客户端和基于 ASP.NET 的服务器组件可以借助它来进行双向多步对话. 换句话说,该对话可不受限制地进行单个无状态请求/响应数据交换:它将继 ...
- SignalR Self Host+MVC等多端消息推送服务(2)
一.概述 上次的文章中我们简单的实现了SignalR自托管的服务端,今天我们来实现控制台程序调用SignalR服务端来实现推送信息,由于之前我们是打算做审批消息推送,所以我们的demo方向是做指定人发 ...
- SSE技术详解:使用 HTTP 做服务端数据推送应用的技术
SSE ( Server-sent Events )是 WebSocket 的一种轻量代替方案,使用 HTTP 协议. 严格地说,HTTP 协议是没有办法做服务器推送的,但是当服务器向客户端声明接下来 ...
随机推荐
- css布局-多行文字垂直居中
方法一: 代码: <style> *{padding: ;margin:;font-size: 12px;} div{float: left;width: 200px;height:200 ...
- leetcode-位运算
位运算可以大大减小算法空间复杂度,提高效率,很巧妙! 先说一下位运算的简单用法 1. 按位与 & 用途:清零,取一个数中的某些指定位,保留一个数中的某些指定位 2. 按位或 | 用途:将一个数 ...
- Java XML解析器
使用Apache Xerces解析XML文档 一.技术概述 在用Java解析XML时候,一般都使用现成XML解析器来完成,自己编码解析是一件很棘手的问题,对程序员要求很高,一般也没有专业厂商或者开源组 ...
- iOS 之 编外知识点
iOS 使用github iOS 开源库介绍 iOS 优质方案 iOS 开发framework 后端数据库使用 Bomb方案 iOS 错误及解决汇总 后台 之 Bmob 申请苹果企业账号
- Java的三种代理模式
Java的三种代理模式 1.代理模式 代理(Proxy)是一种设计模式,提供了对目标对象另外的访问方式;即通过代理对象访问目标对象.这样做的好处是:可以在目标对象实现的基础上,增强额外的功能操作,即扩 ...
- c#和java中的方法覆盖——virtual、override、new
多态和覆盖 多态是面向对象编程中最为重要的概念之一,而覆盖又是体现多态最重要的方面.对于像c#和java这样的面向对象编程的语言来说,实现了在编译时只检查接口是否具备,而不需关心最终的实现,即最终的实 ...
- ceentos5.5 配置samba服务&用户&组
准备 Change Root Password passwd root 在提示下建立新密码 静态IP vi /etc/sysconfig/network-scripts/ifcfg-eth0 #网络 ...
- 2.3. 实体(Core Data 应用程序实践指南)
Entity 实体,就像是数据表的映射类.用实体就可以创建托管对象了. 实体需要做的就是设置实体名称.实体属性及属性数据类型. 还可以根据实体配置NSManagedObject的子类(可选),创建子类 ...
- 关于P,NP,NPC和NP-hard的通俗解释
这些概念以前老是犯糊涂,今天整清楚.摘要:P: Polynomial SolvableNP: Non-determinstic Polynomial Solvable 0)词语解释:Polynomia ...
- Unity游戏开发——自动为动画剪辑添加事件 之 最后几帧的事件不能被调用的问题
最近在做一个根据配置表自动生成动画剪辑clip以及controller的功能.做法是根据配置表配置的动作以及每个动作的关键帧,自动为每个clip添加事件.这样做可以把动画的事件处理在游戏运行之前就计算 ...