java – 如何处理Jetty异常 – 长时间运行的HTTP请求超时,但它所
发布时间:2020-12-14 17:46:36 所属栏目:Java 来源:网络整理
导读:我有一个处理长时间运行的HTTP请求的Jetty服务器 – 响应由不同的进程X生成,最终在Jetty请求定期检查的收集器哈希中. 有3例: 进程X在HTTP请求的超时时间之前完成 – 没问题 进程X在请求的超时时间结束 – 否 问题 进程X从不完成 – 发生异常 如何检测这种情
我有一个处理长时间运行的HTTP请求的Jetty服务器 – 响应由不同的进程X生成,最终在Jetty请求定期检查的收集器哈希中.
有3例: >进程X在HTTP请求的超时时间之前完成 – 如何检测这种情况(3)并防止异常,同时允许其他两种情况正常工作? 例外: 2012-06-18 00:13:31.055:WARN:oejut.QueuedThreadPool: java.lang.IllegalStateException: IDLE,initial at org.eclipse.jetty.server.AsyncContinuation.complete(AsyncContinuation.java:569) at server.AsyncHTTPRequestProcessor.run(AsyncHTTPRequestProcessor.java:72) at org.eclipse.jetty.server.handler.ContextHandler.handle(ContextHandler.java:1119) at org.eclipse.jetty.server.AsyncContinuation$1.run(AsyncContinuation.java:875) at org.eclipse.jetty.util.thread.QueuedThreadPool.runJob(QueuedThreadPool.java:599) at org.eclipse.jetty.util.thread.QueuedThreadPool$3.run(QueuedThreadPool.java:534) at java.lang.Thread.run(Thread.java:679) Jetty继续HTTP请求: public class AsyncHTTPRequestProcessor implements Runnable { private ConcurrentHashMap<String,String> collector; private Logger logger; private AsyncContext ctx; //Defined this here because of strange behaviour when running junit //tests and the response json string being empty... private String responseStr = null; public AsyncHTTPRequestProcessor(AsyncContext _ctx,ConcurrentHashMap<String,String> _collector,Logger _logger) { ctx = _ctx; collector = _collector; logger = _logger; } @Override public void run() { logger.info("AsyncContinuation start"); //if(!((AsyncContinuation)ctx).isInitial()){ String rid = (String) ctx.getRequest().getAttribute("rid"); int elapsed = 0; if(rid !=null) { logger.info("AsyncContinuation rid="+rid); while(elapsed<ctx.getTimeout()) { if(collector.containsKey(rid)){ responseStr = collector.get(rid); collector.remove(rid); logger.info("--->API http request in collector:"+responseStr); ctx.getRequest().setAttribute("status",200); ctx.getRequest().setAttribute("response",responseStr); ctx.getRequest().setAttribute("endTime",System.currentTimeMillis()); //ctx.complete(); break; } try { Thread.sleep(10); elapsed+=10; } catch (InterruptedException e) { e.printStackTrace(); } } //} logger.info("Collector in async stuff:"); for(String key:collector.keySet()){ logger.info(key+"->"+collector.get(key)); } for(Entry<String,String> x:collector.entrySet()){ logger.info(x.getKey()+"->"+x.getValue()); } ctx.complete(); <---- this line 72 } } } 解决方法
这里的问题不是您调用AsyncContext#complete(),而是代码的泛型设计.
连续性(Servlet异步同样的事情)被设计为异步的.使用内部连续超时的while循环不能在这里.通过这样做,您正在将异步设计转变为同步设计.正确的做法是使用Continuation#addContinuationListener()注册一个监听器,并实现onTimeout()方法来适当地处理超时情况. 一旦你的超时逻辑出来,我建议将过程X逻辑移到AsyncHTTPRequestProcessor类,并从需要使用收集器移出.在处理过程中,您应该假设当前线程永远不会被超时.通过这样做,您对complete()的调用会产生敏感,您将无法收集收集器上的并发故障. (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |