我刚刚在我的这个小项目上启动了servlet,所以请保持温柔。 我有一个静态HTML,后台有一些JS使用:
var xmlhttpRequest = new XMLHttpRequest();
xmlhttpRequest.onreadystatechange = function(){
if (xmlhttpRequest.readyState==4){
if (xmlhttpRequest.status == 200){
var rString = xmlhttpRequest.responseText;
alert(rString);
}
}
}
和JS servlet调用:
xmlhttpRequest.open("POST", "ServletBase", true);
xmlhttpRequest.send(this.someString);
一切都很好;在servlet上,在processResponse中我获取请求String并将该String传递给java类调用ACB:
response.setContentType("text/html;charset=UTF-8");
int requestLength = request.getContentLength();
PrintWriter pWriter = response.getWriter();
if(requestLength>1){
String inputString = /* i get the string */;
this.ACB.processPageCommand(inputString,pWriter);
}else{pWriter.write("NULL");}
现在,ACB类是处理inputString并与连接在COM3上并实现SerialPortEventListener
的ArduinoBoard通信的工作类。事情发生后,我使用ACB中的pWriter来写回东西(有时候是一个简单的String,有时候是一个JSON对象作为String):
this.pWriter.write(responseString);
问题是在JS中我收到了错误的数据。例如,我只是在ACB中将引脚32设置为HIGH并想要写回JSON {"pin":"32","state":"1"}
。我得到一个空响应(板上的引脚设置正确);如果我现在将相同的引脚设置为低电平,我应该得到{"pin":"32","state":"0"}
,但现在我得到第一个响应:{"pin":"32","state":"1"}
(电路板上的引脚设置正确)。
在我执行this.pWriter.write(responseString);
之前System.out.println(responseString)
和responseString应该是什么意味着ArduinoBoard返回了良好的数据,并且它的处理很顺利,但在JS中我得到了以前的数据'。
我敢打赌这是微不足道的,但由于我缺乏servlet的知识,我无法绕过它。还有,很抱歉很长的帖子:D
答案 0 :(得分:0)
浏览器正在缓存响应。在返回数据的servlet中设置no-cache标头。
response.setHeader("Cache-Control", "no-store, no-cache, must-revalidate, post-check=0, pre-check=0");
response.setHeader("Pragma","no-cache");
这可能会在大多数浏览器上自行解决,但不能在IE上解决,因为IE仍会尝试缓存通过Ajax收到的响应。要解决此问题,您需要在Ajax POST中添加一个时间戳或随机数的参数。您只需要发送此参数以欺骗IE正常工作(通过明确这是一个唯一的请求)。您不必在servlet端读取参数。
答案 1 :(得分:0)
是的,我现在有一个make-do解决方案(没有对所有请求进行测试):
发送需要外部硬件处理的请求后,由于PrintWriter.write(responseString)位于synchronized void serialEvent(SerialPortEvent oEvent)
的{{1}},因此我通常得到一个空响应。在JS方面,我检查可能的预期返回数据,并基于此我只是立即开始发送空请求(在发出任何有意义的请求之前),直到我得到一个有意义的响应 - 现在正好在emtpy之后的下一个响应。
我不知道我是否应该将此标记作为答案,因为我没有在所有命令和请求 - 响应组合上测试它,但是及时......