`
jayjayjaylun
  • 浏览: 90129 次
  • 性别: Icon_minigender_1
  • 来自: 广州
社区版块
存档分类
最新评论

jsp forward out.flush()

    博客分类:
  • java
阅读更多
<%@ page language="java" pageEncoding="UTF-8"  autoFlush="true" buffer="10kb" contentType="text/html; charset=UTF-8"%>
<%
String name="";
for(int i = 0 ;i<1024*10; i++){
	name+="D";
}
System.out.println(" ===========name : " +name.length());
System.out.println(" =========== buffer size : " + out.getBufferSize());

out.print(name);
//out.flush();
request.getRequestDispatcher("whoami.jsp").forward(request,response);
%>

<%--
 if (true) {
        _jspx_page_context.forward("whoami.jsp");
        return;
      }
<jsp:forward page="whoami.jsp"></jsp:forward>
--%>
<%--
	
	tomcat5.5 catalina.out  log  输出 Exception
	tomcat6.0 后台没有Exception log
ava.lang.IllegalStateException: Cannot forward after response has been committed
        at org.apache.catalina.core.ApplicationDispatcher.doForward(ApplicationDispatcher.java:313)
        at org.apache.catalina.core.ApplicationDispatcher.forward(ApplicationDispatcher.java:301)
        at org.apache.jsp.flush_jsp._jspService(org.apache.jsp.flush_jsp:54)
        at org.apache.jasper.runtime.HttpJspBase.service(HttpJspBase.java:97)
        at javax.servlet.http.HttpServlet.service(HttpServlet.java:802)
        at org.apache.jasper.servlet.JspServletWrapper.service(JspServletWrapper.java:322)
        at org.apache.jasper.servlet.JspServlet.serviceJspFile(JspServlet.java:314)
        at org.apache.jasper.servlet.JspServlet.service(JspServlet.java:264)
        at javax.servlet.http.HttpServlet.service(HttpServlet.java:802)
        at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:252)
        at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:173)
        at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:213)
        at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:178)
        at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:126)
        at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:105)
        at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:107)
        at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:148)
        at org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:868)
        at org.apache.coyote.http11.Http11BaseProtocol$Http11ConnectionHandler.processConnection(Http11BaseProtocol.java:663)
        at org.apache.tomcat.util.net.PoolTcpEndpoint.processSocket(PoolTcpEndpoint.java:527)
        at org.apache.tomcat.util.net.LeaderFollowerWorkerThread.runIt(LeaderFollowerWorkerThread.java:80)
        at org.apache.tomcat.util.threads.ThreadPool$ControlRunnable.run(ThreadPool.java:684)
        at java.lang.Thread.run(Thread.java:619)

如果在
	request.getRequestDispatcher("whoami.jsp").forward(request,response);
	或者
	<jsp:forward page="whoami.jsp"></jsp:forward>
手动调用 out.flush();
或则 buffer 已经满了 autoFlush="true"

tomcat5.5 tomcat6.0
将会直接输出 out.print(name); 字符串 而不会 forward 到指定页面


这种方式是在服务器端作的重定向。服务器往client发送数据的过程是这样的:服务器在向客户端发送数据之前,是先将数据输出到缓冲区,
然后将缓冲区中数据发送给client端。什么时候将缓冲区里的数据发送给client端呢?
(1)当对来自client的request处理完,并把所有数据输出到缓冲区,
(2)当缓冲区满,
(3)在程序中调用缓冲区的输出方法out.flush()或 response.flushbuffer(),web container才将缓冲区中的数据发送给client。

这种重定向方式是利用服务器端的缓冲区机制,在把缓冲区的数据发送到客户端之前,原来的数据不发送,将执行转向重定向页面,发送重定向页面的数据,
重定向调用页的数据将被清除。如果在<JSP:FORWORD>之前有很多输出,前面的输出已使缓冲区满,将自动输出到客户端,
那么这种重定向方式将不起作用,这一点应该特别注意。

 --%>





Servlet:

当然,在servlet中,一般跳转都发生在doGet, doPost等方法里面。

一、原理

1) redirect 方式

response.sendRedirect("/a.jsp");

页面的路径是相对路径。sendRedirect可以将页面跳转到任何页面,不一定局限于本web应用中,如:

response.sendRedirect("http://www.ycul.com");

跳转后浏览器地址栏变化。

这种方式要传值出去的话,只能在url中带parameter或者放在session中,无法使用request.setAttribute来传递。

这种方式是在客户端作的重定向处理。该方法通过修改HTTP协议的HEADER部分,对浏览器下达重定向指令的,让浏览器对在location中指定的URL提出请求,使浏览器显示重定向网页的内容。该方法可以接受绝对的或相对的URLs。如果传递到该方法的参数是一个相对的URL,那么Web container在将它发送到客户端前会把它转换成一个绝对的URL。public void doPost(HttpServletRequest request,HttpServletResponse response)    throws ServletException,IOException

{

        response.setContentType("text/html; charset=UTF-8");

        response.sendRedirect("/index.jsp");

}

2) forward方式

RequestDispatcher dispatcher = request.getRequestDispatcher("/a.jsp");

dispatcher .forward(request, response);

页面的路径是相对路径。forward方式只能跳转到本web应用中的页面上。

跳转后浏览器地址栏不会变化。

使用这种方式跳转,传值可以使用三种方法:url中带parameter,session,request.setAttribute

这种方式是在服务器端作的重定向。服务器往client发送数据的过程是这样的:服务器在向客户端发送数据之前,是先将数据输出到缓冲区,然后将缓冲区中数据发送给client端。什么时候将缓冲区里的数据发送给client端呢?(1)当对来自client的request处理完,并把所有数据输出到缓冲区,(2)当缓冲区满,(3)在程序中调用缓冲区的输出方法out.flush()或 response.flushbuffer(),web container才将缓冲区中的数据发送给client。

这种重定向方式是利用服务器端的缓冲区机制,在把缓冲区的数据发送到客户端之前,原来的数据不发送,将执行转向重定向页面,发送重定向页面的数据,重定向调用页的数据将被清除。如果在<JSP:FORWORD>之前有很多输出,前面的输出已使缓冲区满,将自动输出到客户端,那么这种重定向方式将不起作用,这一点应该特别注意。

public void doPost(HttpServletRequest request,HttpServletResponse response)   throws ServletException,IOException

{

        response.setContentType("text/html; charset=UTF-8");

        ServletContext sc = getServletContext();

        RequestDispatcher rd = null;

        rd = sc.getRequestDispatcher("/index.jsp");

        rd.forward(request, response);

}

二、区别.

1、forward重定向是在容器内部实现的同一个Web应用程序的重定向,所以 forward方法只能重定向到同一个Web应用程序中的一个资源,重定向后浏览器地址栏URL不变,而sendRedirect方法可以重定向到任何 URL, 因为这种方法是修改http头来实现的,URL没什么限制,重定向后浏览器地址栏URL改变。

2、forward重定向将原始的HTTP请求对象(request)从一个servlet实例传递到另一个实例,而采用sendRedirect方式两者不是同一个application。

3、基于第二点,参数的传递方式不一样。forward的form参数跟着传递,所以在第二个实例中可以取得HTTP请求的参数。sendRedirect只能通过链接传递参数,response.sendRedirect(“login.jsp?param1=a”)。

4、sendRedirect能够处理相对URL,自动把它们转换成绝对URL,如果地址是相对的,没有一个‘/’,那么Web container就认为它是相对于当前的请求URI的。比如,如果为response.sendRedirect("login.jsp"),则会从当前servlet 的URL路径下找login.jsp: http://10.1.18.8:8081/dms/servlet/Servlet 重定向的URL: http://10.1.18.8:8081/dms/servlet/login.jsp,如果为response.sendRedirect(" /login.jsp")则会从当前应用径下查找url:http://10.1.18.8:8081/login.jsp。而forward不能这样处理相对路径。

java

他们的区别是:

response.sendRedirect是向客户浏览器发送页面重定向指令,浏览器接收后将向web服务器重新发送页面请求,所以执行完后浏览器的url显示的是跳转后的页面。跳转页面可以是一个任意的url(本服务器的和其他服务器的均可)。

RequestDispatcher.forward则是直接在服务器中进行处理,将处理完后的信息发送给浏览器进行显示,所以完成后在url中显示的是跳转前的页面。在forward的时候将上一页面中传送的request和response 信息一同发送给下一页面(而response.sendRedirect不能将上一页面的request和response信息发送到下一页面)。由于 forward是直接在服务器中进行处理,所以forward的页面只能是本服务器的。

JSP:

1) response.sendRedirect();

和servlet的response.sendRedirect()方式一样。

此语句前不允许有out.flush(),如果有,会有异常:

java.lang.IllegalStateException: Can't sendRedirect() after data has committed to the client.

at com.caucho.server.connection.AbstractHttpResponse.sendRedirect(AbstractHttpResponse.java:558)

...

跳转后浏览器地址栏变化

如果要跳到不同主机下,跳转后,此语句后面的语句会继续执行,如同新开了线程,但是对response的操作已经无意义了;

如果要跳到相同主机下,此语句后面的语句执行完成后才会跳转;

2) response.setHeader("Location","");

此语句前不允许有out.flush(),如果有,页面不会跳转。

跳转后浏览器地址栏变化

此语句后面的语句执行完成后才会跳转

3) <jsp:forward page="" />

此语句前不允许有out.flush(),如果有,会有异常:

java.lang.IllegalStateException: forward() not allowed after buffer has committed.

at com.caucho.server.webapp.RequestDispatcherImpl.forward(RequestDispatcherImpl.java:134)

at com.caucho.server.webapp.RequestDispatcherImpl.forward(RequestDispatcherImpl.java:101)

at com.caucho.jsp.PageContextImpl.forward(PageContextImpl.java:836)

...

跳转后浏览器地址栏不变,但是只能跳到当前主机下

此语句后面的语句执行完成后才会跳转

分享到:
评论

相关推荐

    JSP教案大纲.

    - **&lt;jsp:forward&gt;**:将请求转发到其他页面或Servlet,如 `&lt;jsp:forward page="newPage.jsp" /&gt;`,可以配合`&lt;jsp:param&gt;`传递参数。 - **&lt;jsp:useBean&gt;**:创建或查找JavaBean并将其绑定到JSP页面的特定范围...

    jsp的跳转方式总结

    * 不能在 &lt;jsp:forward page/&gt; 之前使用 out.flush(),否则将抛出 java.lang.IllegalStateException 异常。 * 跳转后,浏览器地址栏不变。 * &lt;jsp:forward page/&gt; 之后的语句将在跳转完成后执行。 * 只能跳转到当前...

    jsp经典语法.rar_jsp

    5. **动作(Actions)**:如`&lt;jsp:include&gt;`, `&lt;jsp:forward&gt;`, `&lt;jsp:useBean&gt;`等,用于控制页面流程。例如,包含一个文件: ```jsp &lt;jsp:include page="header.jsp" flush="true" /&gt; ``` **JSP中的内置对象**...

    JSP基本语法.doc

    &lt;jsp:include page="footer.jsp" flush="true"&gt; &lt;jsp:param name="param1" value="value1" /&gt; &lt;/jsp:include&gt; ``` 2. **jsp:forward**: 将请求转发到其他Web资源。类似于`RequestDispatcher.forward()`。例如:...

    jsp基础技术.doc

    - 动态包含:`&lt;jsp:include page="..." flush="true"&gt;` - 转发:`&lt;jsp:forward page="..."&gt;` **十一、静态包含与动态包含的区别** 静态包含在编译时完成,而动态包含在运行时决定,后者更灵活,可以传递参数。 **...

    Jsp面试题目.doc

    跳转方式有两种:&lt;jsp:include page = “included.jsp” flush = “true”&gt; 和 &lt;jsp:forward page = “nextPage.jsp”/&gt;。前者页面不会转向 include 所指的页面,只是显示该页面的结果,主页面还是原来的页面。后者...

    JSPJSP.doc

    `后,应当在`out.flush();`和`out.close();`后不再进行任何输出操作。这是因为关闭流后,任何进一步的写入尝试都将抛出异常。正确做法是在关闭流之后,结束响应并确保所有数据已发送到客户端。 总结起来,这些知识...

    JSP高级编程.rar

    **JSP的缓存机制** 通过`&lt;jsp:include&gt;`的`flush`属性或`pageContext.include()`的`flush`参数,可以控制是否清空缓冲区,优化性能。 通过深入理解这些概念和技术,开发者可以有效地利用JSP进行高效、灵活的Web应用...

    jsp内置对象编程

    本文详细介绍了 JSP 内置对象编程的基本概念和技术要点,包括 `out` 对象的使用、变量与函数的定义、JSP 指令的使用以及 `response` 对象的高级应用。通过学习这些知识点,开发人员可以更高效地使用 JSP 技术来构建...

    分享JSP学习经验总结

    - 调用`out.flush()`或`response.flushBuffer()` 可以通过`response.setBufferSize()`设置缓冲区大小,或者检查`response.isCommitted()`来判断数据是否已发送到客户端。 ### 三、服务端输出重定向 1. **`...

    web项目,实战经验

    (1)当对来自client的request处理完,并把所有数据输出到缓冲区,(2)当缓冲区满,(3)在程序中调用缓冲区的输出方法 out.flush()或response.flushbuffer(),web container才将缓冲区中的数据发送给client。...

    关于JSP的学习经验总结

    - 调用`out.flush()`或`response.flushBuffer()` 可以通过`response.setBufferSize(size)`来设置缓冲区大小,`size`以字节为单位。设置为0表示禁用缓冲,而`response.getBufferSize()`则用于获取当前缓冲区大小。`...

    JSP填空题和判断题.doc

    24. out对象的out.flush()方法,功能是输出缓冲的容。 25. JSP的session对象用来保存单个用户访问时的一些信息。 26. response对象的sendRedirect(URL url)方法可以将当前客户端的请求转到其他页面去。 27. 当...

    jsp实现文件下载功能

    System.out.println("Error!"); e.printStackTrace(); } ``` - 使用`FileInputStream`读取文件内容,并通过`OutputStream`将其输出到客户端。 - 需要注意关闭资源,避免资源泄露。 #### 四、总结 本文详细...

    JSP学习经验小结分享

    这个缓冲区只有在以下三种情况下才会将内容输出给客户端:调用out.flush()或response.flushBuffer();缓冲区满了;或缓冲区大小被设置为0,即不使用缓冲区。 第三部分介绍了服务端输出重定向的三种方法:使用...

    jsp页面下载的方式

    System.out.println("Error!"); e.printStackTrace(); } finally { // 关闭流 } %&gt; ``` 在这两种方法中,`RequestDispatcher`的方式更加简洁,因为它依赖于容器来处理文件的读取和传输。而文件流输出的方式...

    jsp 的一些基本资料

    与 `jsp:include` 不同,`jsp:forward` 会导致当前页面的执行终止,并将控制权转移至指定的页面。 **示例代码**: ```jsp &lt;jsp:forward page="nextPage.jsp" /&gt; ``` `jsp:forward` 也支持 `&lt;jsp:param&gt;` 标签来传递...

    servlet跳转的几种情况

    * 需要注意的是,JSP 跳转前不能有 out.flush(),否则会出现异常。 Servlet 跳转可以分为 Redirect 跳转和 Forward 跳转两种,JSP 跳转也可以使用这两种方式,但是需要注意 JSP 的特殊性。了解 Servlet 跳转的几种...

Global site tag (gtag.js) - Google Analytics