sam*_*sam 1 java servlets java-ee requestdispatcher
有人请帮助我.
 private void forward(String address,
                    HttpServletRequest  request,
                    HttpServletResponse response)
                        throws ServletException, IOException{
    getServletContext()
        .getRequestDispatcher("/" + address)
        .forward(request, response);
}
private void include(String address,
                    HttpServletRequest  request,
                    HttpServletResponse response)
                        throws ServletException, IOException{
    getServletContext()
        .getRequestDispatcher("/" + address)
        .include(request, response);
}
这两个函数已经编写在我的项目中的每个servlet中,问题是当我在servlet中首先使用这两个函数时包含("servlet/abc",request.response); 之后它使用了forward("servlet/def",request.response); 所以使用Netbeans 7我一步一步地看着前进不是转发servlet的控制但是当我在转发前不使用include时它转发控件.
所以我想知道为什么会发生这种情况,原因是什么以及如何在包含任何servlet后继续前进.
请有人帮助我...这是一个有趣的问题.
include("servlet/abc",request, response);
forward("servlet/def",request, response);   //HERE IS PROBLEM NOT FORWRDING AFTER INCLUDE
无论你为什么看起来如此观察这种行为,你所尝试的将永远不会奏效.根据RequestDispatcher.forward()的合同,"如果响应已经提交,则此方法抛出IllegalStateException",并且"在转发之前自动清除响应缓冲区中的未提交输出".
因此,无论转发是否成功,您都无法在转发之前和之后成功地将内容发送回用户.这是因为转发的目的是允许"一个servlet对请求进行初步处理而另一个资源生成响应",而不是让两个不同的servlet生成响应的不同部分.在Servlet模型中,生成响应始终只属于一个servlet.
如果您不知道"已提交"和"未提交"的含义,则表示响应状态和标头是否已发送给用户.当您编写响应时,您实际上是在写入本地缓冲区.什么都不会立即发送.只要您写的所有内容仍然是本地的,您就可以自由地做任何事情,包括重置缓冲区并重新开始,就像转发一样,但只要发送了一些内容,您就会承诺并且不再改变你要做的事.响应可以通过几种方式提交(即全部或部分发送给用户),包括填充缓冲区以便必须发送它以腾出更多内容空间,手动刷新缓冲区,或刷新Writer或OutputStream的响应.
最终,在你的情况下可能发生的事情是你正在使用include编写一些东西,并且它导致响应被提交,要么是因为你填充了缓冲区,要么因为我似乎记得包含通常导致自动flush(不确定这个文档).然后当你尝试转发时,它会抛出所需的IllegalStateException,你应该在你的日志中看到它,但是不会引起典型的500响应状态,因为正如我所讨论的那样,你已经提交了其他一些状态码.