最近有个项目想把c/s的代码转成mvc的,这听起来并不困难。

如果UI和业务逻辑良好分离了的话,不会花太多的功夫,应该多数的内容都能重复利用。

但在实际的操作过程中,发现业务逻辑代码和UI提示全是混在一起的,尤其里面有这样的代码很多:

public class MyLogic
{
public int DoPress(string bin)
{
if (string.IsNullOrEmpty(bin))
{
System.Windows.Forms.MessageBox.Show("数据为空,请登录后使用");
return -1;
} return 0;
}
}

这是一段伪代码,不是真实的代码内容。这段代码背后有这样的信息:

  • MyLogic类是底层的代码,有很多系统都在调用它,关系错综复杂
  • 代码内需要有合法性的检验,如果合法性校验失败,那函数会被return,错误信息需要让用户看到

现在的问题是,这个MessageBox.Show()的内容我怎么才能显示用户这一端来呢?

首先,b/s的程序,这些代码是运行在服务器端的,原来的MessageBox.Show()不会有任何的效果。

如果我们修改原先的函数签名,将 数据为空,请登录后使用 这句话传输到浏览器,再用javascript的alert来提示。技术上是可以实现的。

就像这样:

public class MyLogic
{
public Tuple<int, string> DoPress(string bin)
{
if (string.IsNullOrEmpty(bin))
{
//System.Windows.Forms.MessageBox.Show("数据为空,请登录后使用");
return new Tuple<int, string>(-1, "数据为空,请登录后使用");
} return new Tuple<int, string>(-1, null);
}
}

这个Tuple会被返回出去,最后传输到浏览器。

然而,这会修改原先的函数签名,所有使用DoPress的函数都要修改,并且,有的地方还是使用反射来调用的,要这样修改,会带来巨大的工作量,

根据这个具体的情况,我不得不去想如何在有限的时间内来完成这件事。

问题的核心是:如何不修改函数的签名,并将相关的信息输出到浏览器?

我首先浮现了第一个解决方案是SSE(Server sent event),它是HTML5里服务器向客户端推送事件的一种方式。很快我写了一个小的demo来进行测试,确实可以用,但是有问题:非常的慢,Server产生了消息之后,最长需要等待4秒才能看到提示消息。

我google了这个问题,也看到其他人的讨论:https://stackoverflow.com/questions/12297740/server-sent-events-work-but-with-a-massive-time-delay

但最后这个问题还是没有解决。

于是我转向了SignalR,很快写了另外的一个demo,这次工作良好,消息瞬时到达。

那么,之前的项目修改成什么样子呢?

public class MyLogic
{
public int DoPress(string bin)
{
if (string.IsNullOrEmpty(bin))
{
MessagePushHelper.PushSignalR("数据为空,请登录后使用");
return -1;
} return 0;
}
}

可以看到,之前的MessageBox.Show()改成了我自己写的MessagePushHelper.PushSignalR(),其他位置不变,这样应该是最小改动的解决方案了。

只不过有一点需要注意的是:要注意多个用户同时使用时的情况(你不能对外广播出错消息)

最后,简单的记录一下步骤:

若要使用SSE

  • 将输出内容标记为 text/event-stream
  • 输出你想要的内容

若要使用SignalR

  • nuget包 install-package Microsoft.AspNet.SignalR
  • 创建hub
  • 创建startup类,打上OwinStartup标记
  • 在页面引用 jquery.signalR-2.2.2.min.js和signalr/hubs
  • 启动hub并接收数据

文中提到的解决方案,可在github上查看:https://github.com/syler/Fun/tree/master/SSE-SignalR

本文地址:http://www.cnblogs.com/asis/p/signalr-sse.html

我的博客地址:https://1few.com/SSE-SignalR

使用 SignalR与SSE(Sever sent event)向客户端推送提示信息的更多相关文章

  1. 实时显示数据 SignalR 及时消息提醒( 立即向其推送内容)

    实时显示数据  SignalR 及时消息提醒( 立即向其推送内容) http://www.cnblogs.com/Leo_wl/p/5634910.html  <!--Reference the ...

  2. ASP.NET SignalR 系列(四)之指定对象推送

    在上一章讲到了广播推送,即所有订阅的用户都能收到,这种适合于信息广播. 接下来介绍如何给指定的对象推送 在讲这个之前先说明一下连接创建的基础知识 1.每个页面与服务端创建连接并启动时,这时服务端会产生 ...

  3. 前端通信:SSE设计方案(二)--- 服务器推送技术的实践以及一些应用场景的demo(包括在线及时聊天系统以及线上缓存更新,代码热修复案例)

    距离上一篇博客,这篇文章的发布大概过了整整三个月.我也从饿了么度过了试用期,成为了正式员工.刚进来恰好遇到项目底层改造和迁移,将项目从angular全部迁移到vue上,所以适应这边的节奏和业务的开发任 ...

  4. SignalR 聊天室实例详解(服务器端推送版)

    翻译自:http://www.codeproject.com/Articles/562023/Asp-Net-SignalR-Chat-Room  (在这里可以下载到实例的源码) Asp.Net Si ...

  5. SignalR Self Host+MVC等多端消息推送服务(1)

    一.概述 由于项目需要,最近公司项目里有个模块功能,需要使用到即时获得审批通知:原本的设计方案是使用ajax对服务器进行定时轮询查询,刚刚开始数据量和使用量不大的时候还好,后来使用量的增加和系统中各种 ...

  6. SignalR Self Host+MVC等多端消息推送服务(2)

    一.概述 上次的文章中我们简单的实现了SignalR自托管的服务端,今天我们来实现控制台程序调用SignalR服务端来实现推送信息,由于之前我们是打算做审批消息推送,所以我们的demo方向是做指定人发 ...

  7. ASP.NET SignalR 系列(八)之跨域推送

    前面几章讲的都是同域下的推送和订阅.这种讲讲如何跨域 对于SignalR来说,默认是不允许跨域的,因为安全问题.虽如此,但同时提供了跨域方案. 两种跨域方式: 1:JSONP2:CORS JSONP的 ...

  8. ASP.NET SignalR 系列(五)之群组推送

    在上一章介绍了 一对一推送的方式,这章重点介绍下群组推送和多人推送 群组主要就是用到了方法:Groups.Add(Context.ConnectionId, groupName); 将不同的连接id加 ...

  9. asp.net使用signalr实现集群集群下面的消息推送

    1.选用Signalr的原因 Signalr内部给我们做了很多封装.当服务器或者浏览器不支持websoket协议的时候就使用长连接方式  不支持长连接再选用轮询的方式获取消息 websoket:与服务 ...

随机推荐

  1. 使用Django+MySQL+Apache+Linux创建简单的博客

    本教程基于慕课网<Django入门与实践>编写,基于CentOS 7 基础知识 什么是django? Django是一个基于Python的高级Web开发框架, 特点:高效,快速,高度集成( ...

  2. ACCESS不可识别的数据库格式!

    在Access07之前的数据库后缀名均为*.mdb 而连接字符串写成Provider=Microsoft.Jet.OLEDB.4.0;Data Source=C:\myFolder\*.mdb ;Pe ...

  3. 【vue】创建一个vue前端项目,编译,发布

    npm: Nodejs下的包管理器. webpack: 它主要的用途是通过CommonJS的语法把所有浏览器端需要发布的静态资源做相应的准备,比如资源的合并和打包. vue-cli: 用户生成Vue工 ...

  4. test20180922 交错的字符串

    题意 分析 这个数据范围容易使人想到折半搜索. 我们将字符串分为前后两部分.如果前半部分中搜得的前缀串为{S1, S2},那么后半部分中搜得的后缀串必须为{rev(S2), rev(S1)},且为有序 ...

  5. day 2 Linux Shell笔记

    ------------------------------------------------------------------- -------------------------------- ...

  6. java数据结构链表(纯面向对象的方式)

    //Node.java //LinkedList.java _____ //测试类 [lcy, haha]    1  lcy 删除的对象是 1[lcy, haha] lcy

  7. 使用systemd严格保证启动顺序

    需求: 服务B要在服务A之后启动,且由于存在强内在依赖关系,B必须在A完成初始化之后才能被启动. 解决方法: 首先使用systemd,service脚本需要配置服务B要after服务A. 其次,A服务 ...

  8. Mysql监控调优

    提升性能 1.允许情况下,调大连接数 2.开启查询缓存(看命中率,用在变化不大的表内) 3.锁(查看是否存在死锁) 4.慢查询(将执行时间过长的语句写入日志内) 5.explain(分析表结构,typ ...

  9. FP-growth算法发现频繁项集(二)——发现频繁项集

    上篇介绍了如何构建FP树,FP树的每条路径都满足最小支持度,我们需要做的是在一条路径上寻找到更多的关联关系. 抽取条件模式基 首先从FP树头指针表中的单个频繁元素项开始.对于每一个元素项,获得其对应的 ...

  10. 使用Apriori进行关联分析(二)

    书接上文(使用Apriori进行关联分析(一)),介绍如何挖掘关联规则. 发现关联规则 我们的目标是通过频繁项集挖掘到隐藏的关联规则. 所谓关联规则,指通过某个元素集推导出另一个元素集.比如有一个频繁 ...