.xhr长轮询_使用Spring 3.2的DeferredResult进行长轮询

.xhr长轮询

在我们的最后一集中 , Agile Cowboys Inc.的首席执行官刚刚雇用了Java / Spring顾问,方法是为他提供最初为女友购买的保时捷。 这位首席执行官的女友因失去保时捷而感到不安,已将其婚外恋告诉了他的妻子。 他的妻子在分拆了CEO的套房后已申请离婚。 同时,首席执行官在办公室实施了新的“休闲”着装要求,而Java / Spring顾问刚从他的保时捷换来的回程中,正坐在办公桌旁准备修理电视公司的软件……如果不这样做的话对您没有任何意义,然后看一下使用Spring的Long Polling Tomcat 。

Java / Spring顾问必须在下一个大型游戏之前解决电视公司的服务器资源问题,他知道他可以通过使用在Tomcat 7 1上实现的Servlet 3规范实现Spring的Deferred Result技术来解决此问题。

Java / Spring顾问要做的第一件事是检查 项目的pom.xml文件。 对于异步Servlet 3项目,您必须包括以下依赖项:

<dependency><groupId>javax.servlet</groupId><artifactId>javax.servlet-api</artifactId><version>3.0.1</version><scope>provided</scope></dependency>

接下来,您必须告诉Tomcat Spring DispatcherServlet支持Servlet 3异步通信。 这是通过将以下行添加到web.xml

<async-supported>true</async-supported>

完整的DispatcherServlet配置为:

<servlet><servlet-name>appServlet</servlet-name><servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class><init-param><param-name>contextConfigLocation</param-name><param-value>/WEB-INF/spring/appServlet/servlet-context.xml</param-value></init-param><load-on-startup>1</load-on-startup><async-supported>true</async-supported></servlet>

整理完项目配置后,Java / Spring ConsultantSwift进入了控制器代码。 他用新的DeferredMatchUpdateController替换了研究生培训生的SimpleMatchUpdateController

@Controller() 
public class DeferredMatchUpdateController { @Autowired private DeferredResultService updateService; @RequestMapping(value = "/matchupdate/begin" + "", method = RequestMethod.GET) @ResponseBody public String start() { updateService.subscribe(); return "OK"; } @RequestMapping("/matchupdate/deferred") @ResponseBody public DeferredResult<Message> getUpdate() { final DeferredResult<Message> result = new DeferredResult<Message>(); updateService.getUpdate(result); return result; } 
}

新的DeferredMatchUpdateController非常简单。 与SimpleMatchUpdateController一样,它包含两个方法: start()getUpdate() ,它们的功能与简单方法完全相同。 这使该控制器成为SimpleMatchUpdateController的插件替代品。 最大的不同是, getUpdate()方法创建Spring的DeferredResult的实例,该实例在将其返回给Spring之前传递给新的DeferredResultService 。 然后,Spring停放HTTP请求,使其挂起,直到DeferredResult对象具有一些要返回到浏览器的数据为止。

@Service("DeferredService") 
public class DeferredResultService implements Runnable { private static final Logger logger = LoggerFactory.getLogger(DeferredResultService.class); private final BlockingQueue<DeferredResult<Message>> resultQueue = new LinkedBlockingQueue<>(); private Thread thread; private volatile boolean start = true; @Autowired @Qualifier("theQueue") private LinkedBlockingQueue<Message> queue; @Autowired @Qualifier("BillSkyes") private MatchReporter matchReporter; public void subscribe() { logger.info("Starting server"); matchReporter.start(); startThread(); } private void startThread() { if (start) { synchronized (this) { if (start) { start = false; thread = new Thread(this, "Studio Teletype"); thread.start(); } } } } @Override public void run() { while (true) { try { DeferredResult<Message> result = resultQueue.take(); Message message = queue.take(); result.setResult(message); } catch (InterruptedException e) { throw new UpdateException("Cannot get latest update. " + e.getMessage(), e); } } } public void getUpdate(DeferredResult<Message> result) { resultQueue.add(result); } }

同样,像其对应的SimpleMatchUpdateServiceDeferredResultService包含两个方法: subscribe()getUpdate()

与处理getUpdate(...)它的作用是为新创建的添加DeferredResult对象到LinkedBlockingQueueresultQueue ,以便它可以在以后当比赛更新可用来处理。

真正的工作是通过subscribe()方法完成的。 首先,此方法启动matchReporter ,它在适当的时候将匹配更新输入到自动连接的queue实例中。 然后,它调用私有的startThread()方法来启动工作线程。 该操作仅启动一次,并使用双重检查锁定来确保高效且没有问题。

线程的run()方法首先无限循环,从resultQueue获取DeferredResult对象(如果有),然后从Message对象中获取代表来自更新queue的匹配更新的Message对象(如果有)。 然后,使用message对象作为参数调用DeferredResultsetResult(...) 。 Spring现在将接管工作,原始的长轮询请求将完成,并且数据将延迟地返回给浏览器。

请注意,在此示例代码中, run()方法包含while(true)循环。 尽管此技术简化了示例代码,但在生产代码方面并不是一个好主意。 使用不受控制的不受控制的线程的问题之一是它们会阻止Tomcat正确关闭,并且您通常必须使用良好的Unix kill命令来停止服务器。 在生产代码中,最好包含代码以正常关闭此类工作线程。

经过数小时的辛苦工作后,Java / Spring顾问将其代码推广到生活中,拿起保时捷的钥匙,然后旋转一下。 下个星期六,使用Spring的DeferredResult ,服务器可以很好地应对:用户很高兴,电视公司的总裁很高兴, Agile Cowboys Inc的首席执行官很高兴,尽管他一直怀疑自己付给顾问的钱太多了,但是,这只是金钱。

1在撰写此博客时,我使用的是Tomcat 7.0.42版

该博客随附的代码可在Github上找到: https : //github.com/roghughe/captaindebug/tree/master/long-poll

参考: Captain Debug博客博客中来自JCG合作伙伴 Roger Hughes的Spring 3.2的DeferredResult长轮询 。

翻译自: https://www.javacodegeeks.com/2013/09/long-polling-with-spring-3-2s-deferredresult.html

.xhr长轮询

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/346937.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

十进制数与八进制数互相转换(MATLAB和C版本)

一、八进制数转十进制数 C语言实现 实现思路和参数: /* Function: ConvertOctaltoDecimal* Abstract: Convert an octal number to its equivalent decimal value** - First compute the number of digits in the octal number* - Then perform the conversion, one …

Java正成为COBOL的一部分-它将成为COBOL的一部分吗?

任何从大学&#xff0c;技术学校或社区学院毕业的计算机科学专业都接受过培训。 每个身材高大的公司都使用该语言&#xff0c;并拥有一批具备此能力的程序员。 通用语言可以推动业务发展。 1985年是COBOL。今天是Java。 尽管存在差异&#xff0c;但这两种语言在行为轨迹上都具…

VS2010附加进程调试DLL时断点无法断下的解决方法

系统版本&#xff1a;Win10 x64 1809 VS版本&#xff1a;VS2017 企业版 问题一 在动态链接库(DLL)附加到进程调试时&#xff0c;用VS2017附加后单步调试&#xff0c;结果发现总是在调试过程中卡死&#xff0c;VS2017无响应&#xff1b; 解决办法是&#xff1a;强制结束VS2017…

MATLAB库函数polly2trellis(卷积码生成多项式转网格图描述)的实现过程详解

关注公号【逆向通信猿】更精彩!!! 生成多项式转网格图 在MATLAB中,卷积码的维特比(Viterbi)译码实现通常需要先将生成多项式转换成网格图描述,然后才能利用网格图进行维特比译码 生成多项式转网格图描述的built-in函数为poly2trellis,在MATLAB中,改函数为通信工具箱…

java反射api研究_深入研究Java 8中的可选类API

java反射api研究作为Java程序员&#xff0c;我们所有人都经历了以下情况&#xff1a;我们调用一个方法来获取某个值&#xff0c;然后代替直接对返回值调用某些方法&#xff0c;我们首先必须检查返回值是否不为null&#xff0c;然后在返回值。 这是像Guava这样的外部API试图解决…

【卷积码系列1】(n,k,m)卷积码的编码原理详解及MATLAB实现

关注公号【逆向通信猿】更精彩!!! 原理 编码电路图 ( n , k , m ) (n,k,m) (n,k,

用于SaaS和NoSQL的Jdbi

一个自然的接口&#xff0c;用于与CRM&#xff0c;ERP&#xff0c;会计&#xff0c;营销自动化&#xff0c;NoSQL&#xff0c;平面文件等基于Java的数据集成 Jdbi是Java的SQL便利库&#xff0c;它为JDBC提供更自然的Java数据库接口&#xff0c;该接口易于绑定到域数据类型。 该…

【卷积码系列2】(n,k,m)卷积码的生成多项式矩阵系数转网格图描述(不使用MATLAB库函数)

关注公号【逆向通信猿】更精彩!!! 回顾 之前关于(3,1,3)卷积码的维特比译码仿真写过一篇文章(基于C语言实现): 卷积码Viterbi译码算法基本原理及C语言实现 文中从概率的角度出发,对卷积码的基于硬判决和软判决维特比译码原理进行了阐述,最后以(3,1,3)系统卷积码为例…

【卷积码系列3】(n,k,m)卷积码的维特比译码实现(不使用MATLAB库函数)及性能对比(vitdec函数不使用MATLAB库函数【全部代码需私信另外付费获取】)

理论基础 MATLAB库函数polly2trellis(卷积码生成多项式转网格图描述)的实现过程详解 上面这篇仅作为了解!!! 【卷积码系列1】(n,k,m)卷积码的编码原理详解及MATLAB实现 【卷积码系列2】(n,k,m)卷积码的生成多项式矩阵系数转网格图描述(不使用MATLAB库函数) 维特比译码曲…

【数字信号处理】基于DFT的滤波系列1

一、引言 离散傅立叶变换(DFT)是很多数字信号处理(DSP)层面的核心,因此我们从这块开始。 我们首先快速回顾一下 DFT 的一些要点。 该模块这一部分的完整内容列表是: DFT 回顾 – 实数和复数形式一维(例如时间序列)数据的 DFT 滤波DFT 滤波的非理想行为窗口化二维图像的D…

udt java_Java DB中的Java用户定义类型(UDT)

udt javaJava DB是基于Java编程语言和SQL的关系数据库管理系统。 这是Apache软件基金会的开源Derby项目的Oracle版本。 Java SE 7 SDK中包含Java DB。 用户定义类型&#xff08;UDT&#xff09;是Java类&#xff0c;其实例&#xff08;对象&#xff09;存储在数据库表列中。 U…

【自适应盲均衡9】基于判决反馈的多径衰落信道的盲均衡与MATLAB仿真(CMA-DFE)

关注公号【逆向通信猿】更精彩!!! 关于基于常模准则的盲均衡(即CMA)的基础知识,首先可参考本人博客 【自适应盲均衡2】多径衰落信道的复数常模算法(CMA)的理论推导与MATLAB仿真 引言——判决反馈均衡器(DFE)的引入 线性FIR均衡器一直作为克服信道失真的主要手段。它对…

Java批处理教程

在当今世界&#xff0c;互联网已经改变了我们的生活方式&#xff0c;其主要原因之一是大多数日常琐事都使用互联网。 这导致可用于处理的大量数据。 其中涉及大量数据的一些示例是处理工资单&#xff0c;银行对帐单&#xff0c;利息计算等。因此&#xff0c;请设想一下&#x…

【自适应盲均衡10】基于判决引导(Decision Directed)的多径衰落信道双模式盲均衡算法与MATLAB仿真(DD-CMA)

关注公号【逆向通信猿】更精彩!!! 引言 判决反馈均衡器(Decision Feedback Equalizer, DFE)虽然能够避免线性FIR均衡器的噪声增强,适用于具有深度谱零点的信道均衡;但是容易产生误收敛情况,针对该问题有人提出了预测判决反馈均衡器(PDFE),这个后续再说。 此次要讨论…

【数字信号处理】基于DFT的滤波系列2(含MATLAB代码)

关注公号【逆向通信猿】更精彩!!! 三、时频域的“数” 在该节的大部分内容中,我们将使用无量纲数字序列的数据。然而,对于现实世界的数据,这些数字将具有基础单位。在本节中,将解释时域和频域之间的联系。 假设有N个采样频率为 f s f_s f

编写junit 测试_使用JUnit和Repeat注​​释编写有效的负载测试

编写junit 测试EasyTest最近推出了一组新的注释&#xff0c;可帮助其用户编写有效的测试用例。 进入EasyTest的两个主要注释是&#xff1a; 重复 持续时间 今天&#xff0c;我们将讨论重复标注。 一种新的方法级别注释 重复已添加到EasyTest Framework。 此批注可用于重复…

【数字信号处理】基于DFT的滤波系列3之插值滤波(含MATLAB代码)

四、基于DFT的(理想)滤波 例2:一个“警告” “理想DFT滤波器”虽然简单、有效,但可能会导致意想不到的问题。在博客 【数字信号处理】基于DFT的滤波系列2(含MATLAB代码) 中,数据本身是理想的,由完美的谐波组成,这些谐波在频域中以单一频率理想地表示(无频谱泄漏),这…

Java 9中的无限集

一套 甲Set是元素的集合&#xff0c;从而在任何给定的元件Set只出现一次。 更正式地说&#xff0c;集合不包含元素e1和e2对&#xff0c;因此e1.equals(e2) 。 我们可以像这样在Java 9中轻松创建Set &#xff1a; final Set<Integer> s Set.of(1, 2, 3); System.out.p…

json文件读取之reader.onload中的定义的变量在其函数外部进行处理

采用FileReader读取json文件时,发现只能在reader.onload函数内部获取文件数据,且无法在函数外部访问其内部定义的变量,在网上查阅资料,发现也有博客提到这个问题,如下: VUE的reader.onload方法怎么把值抛出去 在reader.onload中的定义的变量如何在外部调用 … 网上其他…

【数字信号处理】基于DFT的滤波系列4之加窗(含MATLAB代码)

四、基于DFT的(理想)滤波 加窗以减少频谱泄漏 在上面的例子中,整数次谐波被用来产生理想中的示例。这意味着一个完整的整数周期适合正在使用的样本数。一个明显的问题是,如果使用非整数周期数(以及谐波)会怎样?答案是远没有那么有效。 在现实世界中,从这个意义上说,数…