Bug 42934 - sessionDidActivate() called before contextInitialized()
Summary: sessionDidActivate() called before contextInitialized()
Status: RESOLVED FIXED
Alias: None
Product: Tomcat 6
Classification: Unclassified
Component: Catalina (show other bugs)
Version: 6.0.11
Hardware: PC Windows Vista
: P2 normal (vote)
Target Milestone: default
Assignee: Tomcat Developers Mailing List
URL:
Keywords:
Depends on:
Blocks:
 
Reported: 2007-07-18 14:40 UTC by Mike Youngstrom
Modified: 2008-06-08 05:51 UTC (History)
0 users



Attachments

Note You need to log in before you can comment on or make changes to this bug.
Description Mike Youngstrom 2007-07-18 14:40:10 UTC
I'm using Seam and a Seam app depends upon the Seam application being
initialized before you can do much of anything in Seam.

That said Seam puts some hooks into the sessionDidActivate() and
sessionDidPassivate() events.  Because of that when I start up my app
I'm getting a Seam IllegalStateException because the
contextInitialized() event is fired after sessionDidActivate() so Seam
is not yet initialized it's Session hooks are being fired.

What makes me think this is a bug is that sessionWillPassivate() is being
correctly called before contextDestroyed() so it would seem that
sessionDidActivate() being called before contextInitialized() would be
inconsistent behavior.

So to sum up I think tomcat should fire context and session events in the
following order:

contextInitialized
sessionDidActivate
sessionWillPassivate
contextDestroyed


As a side note Tomcat 5 follows what I think is the completely wrong but
consistent order by firing events in this order:

sessionDidActivate
contextInitialized
contextDestroyed
sessionWillPassivate
Comment 1 Mike Youngstrom 2007-07-18 14:45:02 UTC
Here is a link to the Seam Issue:

http://jira.jboss.com/jira/browse/JBSEAM-1681
Comment 2 Len Popp 2007-08-01 07:21:28 UTC
According to the servlet spec, the listeners are supposed to be called in the
order that they're declared in web.xml. Except at shutdown the session listeners
are supposed to be called before the context listeners.

So the question is, how are the listeners declared in web.xml?

(I don't know anything about how Seam integrates with Tomcat, but I guess there
must be a deployment descriptor somewhere with the <listener> declarations.)
Comment 3 Mike Youngstrom 2007-08-01 08:05:20 UTC
> According to the servlet spec, the listeners are supposed to be called in the
> order that they're declared in web.xml. Except at shutdown the session listeners
> are supposed to be called before the context listeners.
> 
> So the question is, how are the listeners declared in web.xml?
> 
> (I don't know anything about how Seam integrates with Tomcat, but I guess there
> must be a deployment descriptor somewhere with the <listener> declarations.)

Yes, Seam has a listener.  And at shutdown in Tomcat 6 the Session Listeners are
correctly called before the Servlet Listeners.  The problem is that at server
'startup' the session listeners are also called before the Servlet Listeners
which is causing trouble for Seam since Seam needs contextInitialized() to be
called before sessionDidActivate().

Mike

Comment 4 Len Popp 2007-08-01 08:27:14 UTC
You missed my point. The order in which the listeners are called depends (in
part) on the order in which they are declared. The behaviour that you describe
could be perfectly correct according to the servlet spec, *depending on how the
listeners are declared*. For more details, see section 10.3.3 and 10.3.4 of the
servlet specification.

Here is a concrete example. Suppose web.xml contains these declarations:

    <listener>
        <listener-class>com.example.MySessionListener</listener-class>
    </listener>
    <listener>
        <listener-class>com.example.MyContextListener</listener-class>
    </listener>

In this example, on startup the session listener will be called before the
context listener (according to section 10.3.3 of the servlet spec). On shutdown,
the session listener will again be called before the context listener (according
to section 10.3.4).

Another possibility is that a single listener class implements two listener
interfaces. In that case, the spec doesn't say what order they should be called
on startup. I guess if the listeners need to be called in a certain order, they
need to be implemented in separate classes so that you can specify the order.

So, how are the listeners declared in your case?
Please post the contents of web.xml, or just the part with the <listener>
declarations.
Comment 5 Mike Youngstrom 2007-08-01 08:41:28 UTC
I see the confusion.  When I say Session Listener I was talking about a class
that implements HttpSessionActivationListener where you were thinking I meant an
HttpSessionListener.  When HttpSessionActivationListeners are not declared in
the web.xml but are automatically called by the container when the instance
passivates and activates instances stored in the Session.

So what I'm saying is that I would expect the
ServletContextListener.contextInitialized() to be called before
HttpSessionActivationListener.sessionDidActivate().

When shutting down ServletContextListener.contextDestroyed() is currently
correctly called after HttpSessionActivationListener.sessionWillPassivate().

Does that clear things up?
Comment 6 Len Popp 2007-08-01 10:29:05 UTC
Sorry, you're right, I forgot about HttpSessionActivationListener objects being
stored in the session itself.

As far as I can see, the spec doesn't say what order these events are fired
relative to the other types of events. Your idea that contextInitialized should
come before sessionDidActivate sounds reasonable, but you may be stuck in the
trap of "Tomcat follows the spec so it doesn't need to be fixed."
Comment 7 Mike Youngstrom 2007-08-01 10:31:45 UTC
Ya, that's the trap I'm afraid of. :)  I'm hoping that because it is a Seam
problem perhaps Jboss might be able to assert some of their influence over
tomcat to get them to fix it....but I guess we'll see.  Thanks for looking at
the issue.
Comment 8 Alexander Kiel 2007-11-06 04:37:11 UTC
I really vote for this. 

My own web application needs the same functionality. I use a spring
WebApplicationContext and some of my Session Vales need beans from this context.
So I store them transient in the session values and fetch them at
sessionDidActivate. But I can not do this if my context is not up and running.
Comment 9 Mark Thomas 2008-05-08 15:18:40 UTC
Looking at this now...

Even with the latest spec things are not explicit and could be read either way. However, 1) I agree with the assessment that logically you would expect the context to be present before the sessions are activated 2) and the last paragraph SRV.16.1.7 hints in this direction as well.

I'll see how easy it is to make the change.
Comment 10 Mark Thomas 2008-05-08 15:19:11 UTC
See also bug 30344.
Comment 11 Mark Thomas 2008-05-09 13:21:57 UTC
I have committed a fix to trunk. Initial testing looks OK but I will eave it a few weeks to see if any issues arise before proposing it for 6.0.x
Comment 12 Mike Youngstrom 2008-05-10 20:21:33 UTC
Thanks tons for taking this on Mark.

Mike
Comment 13 Mark Thomas 2008-05-29 15:05:08 UTC
This is now proposed for 6.0.x
Comment 14 Mark Thomas 2008-06-08 05:51:14 UTC
This has been committed to 6.0.x and will be in 6.0.17 onwards.