tomcat-users mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From Anthony Presley <anth...@zoraptera.com>
Subject Re: response.reset() and forward() ... problematic? DBCP related?
Date Thu, 11 Dec 2003 15:41:58 GMT
Below ....

On Thu, 2003-12-11 at 00:49, Antonio Fiol BonnĂ­n wrote:
> Anthony Presley wrote:
> 
> [... reduced to a minimum, but the problem still there ...]
> 
> >  protected void forward(String s) {
> >      ServletConfig sc = null;
> >      ServletContext sContext = null;
> >      RequestDispatcher rd = null;
> >      
> >      sc = this.getServletConfig();
> >      sContext = sc.getServletContext();
> >      rd = sContext.getRequestDispatcher(s);
> >      rd.forward(req, res);
> >  
> >
> 
> Hey! Where are you getting "req" and "res" from?!! My guess at the end.

These are, as you described, declared more or less.  However, I'm
actually declaring them from a class hierarchy ... meaning that I have a
super class, which has req and res in it, and all of my servlet's derive
from it.  When they call a forward, I then do not need to (necessarily)
call it with request and response.  IE, <psuedo>

class Super {
	protected Request req;
	protected Response res;

	set (Request r1, Response r2) {
		req = r1;
		res = r2;
	}

	forward1 (String s) {
		// Get rd
		rd.forward (req, res);
	}

	forward2 (String s, Request r1, Response r2) {
		// Get rd
		rd.forward (r1, r2);
	}
}

class Sub extends Super {
	doProcess1 () {
		set (request, response);
		.....
		forward1 ("/index.jsp");
	}

	doProcess2 () {
		.....
		forward2 ("/index.jsp", request, response);
	}
}

So ..... what your telling me, is that it's a concurrency problem
created by having "object attributes"?  That if they were, in fact being
called more like:

	doProcess2 ();

than like:

	doProcess1 ();

I wouldn't have these problems?  Very interesting.

Please write back and ensure that's what you mean ..... because I'm
pretty sure it is.  Oh, fun.  Here I go to change .... some 100K lines
of code :-)

--Anthony

> 
> >3.  I've bumped the response buffer (in the servlet) from 8K to 75K
> >(75000), which reduces the errors, but they are still present.  Is there
> >a GOOD way to estimate the amount needed?
> >  
> >
> 
> No need to increase anything. It might alleviate the problem or even 
> improve performance (??), but not solve anything.
> 
> >4.  Using DBCP 1.0 .... using the latest DBCP (1.1?), seems to reduce
> >the errors further (1 in 10, approx).  I've rewritten the code to ensure
> >that connections are being opened / closed locally, and quickly.  Timing
> >it shows that the DB connection is pulled from the pool for about 2300
> >milli, and the JSP runs for about 2 milli to display.
> >  
> >
> 
> Same here. The shorter your DB connections are open, the better, but 
> this will not solve your problem.
> 
> >I'm not 100% sure yet if the problem persists in the JSP (using a simple
> >JSP and simple servlet does not cause these problems, however, the
> >greater the complexity, the higher the likelihood of getting these
> >errors .... which baffle's me, because rerequesting it shows up fine,
> >with nothing in the logs) or the servlet.
> >  
> >
> 
> But the greater the complexity, the greater your chances to get two 
> users using your servlet concurrently.
> 
> >Anyone seen this before?  I'm about at my wits end.  Been refactoring
> >for a week now, and still it persists.
> >  
> >
> 
> Yes. I found it to be a very common mistake. Now you know where the 
> problem lies, you probably already thought of a solution specific to 
> your case.
> 
> My guess:
> 
> req and res are attributes of the Servlet, like in:
> public class TestServlet extends HttpServlet {
> private HttpServletRequest req;
> private HttpServletResponse res;
> [...]
> }
> 
> So you are calling "forward(s)" for a request once req and res have been 
> overwritten by another request.
> 
> Just in case my English is too bad, and so that the archive is useful 
> for people searching it:
> 
> - NEVER use object attributes in Servlets, as a rule of thumb.
> - ALWAYS use local variables instead.
> 
> If you really cannot follow the above, then:
> 
> - Make sure that you need ONLY ONE INSTANCE of the object stored in that 
> attribute.
> - One instance for: all concurrent users, and all successive requests.
> - Make sure that this instance is THREAD SAFE.
> - A typical example of this is the use of a logger.
> - Another example are STATIC attributes, which are, in general, less 
> error-prone in this context.
> 
> If you really cannot follow any of the above, there is still one solution:
> 
> - Make sure your servlet "implements SingleThreadModel". This will 
> ensure a different instance is used for all concurrent requests, or that 
> no concurrent requests will occur.
> 
> 
> Hope that helps.
> 
> 
> Antonio Fiol


---------------------------------------------------------------------
To unsubscribe, e-mail: tomcat-user-unsubscribe@jakarta.apache.org
For additional commands, e-mail: tomcat-user-help@jakarta.apache.org


Mime
View raw message