reply down below

Craig R. McClanahan wrote:
<snip>

>
>Being somewhat familiar with the servlet specs (I've been on the expert
>groups for 2.2, 2.3, and 2.4 :-), the following two scenarios have the
>potential to behave differently, depending on implementation-specific
>decisions inside both the servlet container and the JDK:
>
>(a) Write directly to ServletOutputStream:
>
>  public class MyServlet extends HttpServlet {
>
>    public void doGet(HttpServletRequest request,
>                      HttpServletResponse response)
>                throws IOException, ServletException {
>
>      ServletOutputStream sos = response.getOutputStream();
>      sos.print("foo");
>      // No flush on sos
>
>    }
>
>  }
>
>(b) Write to a buffered wrapper around ServletOutputStream:
>
>  public class MyServlet extends HttpServlet {
>
>    public void doGet(HttpServletRequest request,
>                      HttpServletResponse response)
>                throws IOException, ServletException {
>
>      ServletOutputStream sos = response.getOutputStream();
>      BufferedOutputStream bos = new BufferedOutputStream(sos);
>      sos.print("foo");
>      // No flush on bos or sos
>
>    }
>
>  }
>
>In scenario (a), the three characters will be written to the response --
>the container flushes the container-provided stream for you.
>
Well, it should, but it doesn't.  See below.

>
>
>In scenario (b), the three characters will *not* be written to the
>response -- they are sitting inside the buffer in the
>BufferedOutputStream, and are not accessible to the container -- it
>doesn't even know that the wrapping class is there.  You have to call
>bos.flush() in order for them to be written.  (Exactly the same issue is
>true with all of the standard Java output objects - this is not specific
>to servlet containers).
>
>Scenario (b) is also a very common problem in a servlet 2.3 environment,
>when you use a Filter to create a response wrapper (for instance, to do an
>XSLT transformation on the output generated by the servlet.  It is the
>application's responsibility to ensure that the output stream or writer it
>creates in the wrapper is indeed flushed before the filter returns.
>Usually, that's just a matter of ensuring that you flush it after the
>chain.doFilter() method returns, and before you yourself return from the
>filter.
>
>Steve, your original example in bug report 8916 is exactly analogous to
>scenario (b), because you are creating a java.io.PrintWriter wrapper
>around the ServletOutputStream provided by the container.  It is entirely
>legal for a java.io.PrintWriter implementation to buffer things up inside
>itself -- programs that rely on this *not* happening are incorrect, even
>if they happen to work in *some* environments.
>
It was just meant as example code, and does assume the same 
implementation of PrintWriter (i.e. no buffering).  Your point on some 
implementations being different is well taken.  

There is an scenario (c) which is the real crux of the issue, which is a 
slight mod to your scenario (a):

  public class MyServlet extends HttpServlet {

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

      ServletOutputStream sos = response.getOutputStream();
      sos.setStatus(299);    //   <-----  here
      sos.print("foo");
      // No flush on sos

    }

  }

Change the status to something other than 200 or 204, and you get 
Tomcat-generated body, not "foo".  That's really what I am trying to 
show, and not so much the different PrintWriter stuff.

-Steve
<snip>




--
To unsubscribe, e-mail:   <mailto:[EMAIL PROTECTED]>
For additional commands, e-mail: <mailto:[EMAIL PROTECTED]>

Reply via email to