Thanks for taking the time to look at it. I've already done what you suggest (I removed all the debug statements in this code by the way). It is only in production, where of course the load is greater (test is barely touched at this point). As I said earlier, fortunately this is pretty rare, happens maybe twice every 75,000 requests, give or take, so it's not a major hassle for anyone. Obviously I want to solve it, but I haven't even gotten any user reports on it, I just see it in my log files (it IS possible that it happens but the users don't see anything... this doesn't seem possible, and other indications tell me they are seeing the usual exception page, so I doubt this is the case).

I did check AccountFB's constructor, but on the chance I'm not seeing something, here it is in it's entirety:

public AccountFB(HttpSession inSession, Connection conn) throws ClassNotFoundException, SQLException, NamingException {
session = inSession;
dbcm = new DBConnectionManager(conn);
}


Both session and dbcm are instance variables... hmmm, as I typed that it dawned on me that maybe I have some subtle threading issue... I never considered that because all the Actions instantiate their own function beans, of which AccountFB is one, and they are always local, so I didn't think there would be any problem... However, I wonder if somewhere in the code base they are being instantiated NOT as locals... If that happened concurrently in two places, maybe the container shares the instance, and hence a difficult-to-track-down little concurrency bug. Doesn't strike me as likely, but I can do a quick scan of the code base tomorrow and see if anything turns up.

I will definitely post a solution if I find one in the next few days. I've been looking at this for probably a month now though off and on, so I'm not too confident.

--
Frank W. Zammetti
Founder and Chief Software Architect
Omnytex Technologies
http://www.omnytex.com

Barnett, Brian W. wrote:
Sorry Frank, but I don't see anything. I suspect there is nothing happening
to the session object down in the AccountFB constructor. You probably
already checked that.

Since it is not an easy to duplicate bug, I'd probably scatter some debug
print statements throughout that snippet of code that checks the state of
the session variable and outputs it to the console. Then hammer away, or let
users hammer away. Sometimes something like this isn't possible to do,
though, esp., if it only happens on a production box.

Let us know what the fix is if you are able to find it.

Good luck.

-----Original Message-----
From: Frank W. Zammetti [mailto:[EMAIL PROTECTED] Sent: Monday, November 08, 2004 4:40 PM
To: Struts Users Mailing List
Subject: Re: Session invalidation problem


Can do... Remember, this is an inherited app, so don't kill me for things done here :)

Here's the execute() method of the Action...

String path = mapping.getPath();
ActionForward af = ActionHelpers.actionStart(cat, path, mapping, request);
if (af != null) { return af; }
HttpSession session = request.getSession();
String findReceiveDate = (String)request.getParameter("findReceiveDate");
String findAccountNumber = TOAHelpers.strTrim((String)request.getParameter("findAccountNumber"));
TOAFindAccountActionForm form = new TOAFindAccountActionForm();
Connection conn = DBConnectionManager.createConnection();
AccountFB acFB = new AccountFB(session, conn);
form.setFindReceiveDate(findReceiveDate);
form.setFindAccountNumber(findAccountNumber);
session.setAttribute("TOAFindAccountActionForm", form);


... More stuff follows. Just so you can follow along a bit, this app was converted from a non-Struts framework, so they took the past of least resistance and wound up not really using some Struts constructs properly. Here, they are creating a form and putting it in session because the app has a number of screens that need to be completed before a final submission page, at which point they grab all the forms from session and process them. The AccountFB is just a business delegate, that DBConnectionManager is a class that deals with everything database-related (it's actually not such a bad design when you get to know it... at least, things are nicely segregated and organized decently, which is more than I can say for many systems I've had the displeasure of dealing with).

Anyway, back to some semblence of an on-topic discussion... the exception is ocurring on that last line.

And here's the a ActionHelpers.actionStart() method...

HttpSession session = request.getSession();
if (!command.equalsIgnoreCase("/app/logon") && !command.equalsIgnoreCase("/app/changePassword")) {
if (session == null || session.getAttribute("sessionAlive") == null) {
request.setAttribute("message", "Your session timed out. Please log on again.");
session.invalidate();
return mapping.findForward("reload"); // Global forward
}
}


... Again, more stuff follows, but I think that's the pertinent piece. command is the path passed in, so they're just basically ignoring this check when logging on or changing the password, which is logical from the app's point of view. Note that as of this afternoon I added the suggested catch of IllegalStateException here, but I wind up executing the exact same code you see here in the IF block, minus the call to session.invalidate().

So, as I was pointing out before, by the time execution returns from actionStart(), I don't see a way there wouldn't be a valid session, and hence that getAttribute() call in the Action shouldn't generate an IllegalStateException (I could see getting one BEFORE that point, but if it gets that far, as near as I can tell, it shouldn't be possible).

Spot anything Brian?  Thanks for your effort!





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



Reply via email to