Hi Tauren, This is probably only solved if you are using Shiro's 'native' sessions and not the Servlet container's default sessions. If you have a SessionDAO implementation that you can inject into the SecurityManager, you can store sessions to your own data store if you wish.
If that data store provides a queryable interface, like an RDBMS or many enterprise Caches (GigaSpaces, Coherence, etc), you could obtain this information very easily by querying against attributes on the session directly. For example, to see the number of open sessions (some could be timed out though and not yet validated), you could execute a query something like this: "select count(*) from Session s where s.stopTimestamp is null" That is, return the number of all Sessions that haven't been invalidated yet. But note that this could give you the number of some sessions that are technically invalid but Shiro hasn't had the opportunity to run its ValidationScheduler to 'reap' the orphan invalidated sessions. So instead, you'd have to refine your query a little bit: You could constrain it a little further to guarantee the session hasn't timed out and they are still 'active' based on their last access timestamp. This would eliminate any yet-to-be-invalidated sessions from the query results. For example: "select count(*) from Session s where s.stopTimestamp is null and s.lastAccessTime > ?", where '?' equals (current timestamp milliseconds - sessionTimeoutMilliseconds). To find all the currently logged in users, you can subclass Shiro's SimpleSession class and have an additional 'user id' field on that class. Implement a Shiro AuthenticationListener and register it with the SecurityManager to listen for successful authentication attempts, and then associate the user id onto your SimpleSession subclass instance. Then you can query against this field (along with the timestamps above) to get all currently active logged-in users, i.e. "select s.userId from Session s where s.stopTimestamp is null and s.lastAccessTime > ?". I've done these things for a few of my applications that need this kind of session-based detail, and it works well. Use an enterprise cache if you can to improve performance - if you have one that supports SQL-like queries, then that's the best possible scenario - since all active sessions would live in the enterprise cache, you could query it directly and not incur the more-expensive trip to a relational database. Finally, if you need to react to when sessions are started or stopped or expired, you can implement the SessionListener interface and register that with the SecurityManager as well. Just realize that session expiration events are only received when Shiro has the ability to expire them based on a regular time interval. Only start/stop session events are received the instant they occur. Best, Les On Mon, Jul 27, 2009 at 3:11 PM, Tauren Mills<[email protected]> wrote: > A web application I am building needs to track users who are currently > online. For instance, I want to be able to do the following: > > 1. Show the total number of currently logged in users. > 2. Show a user a list of their associates who are online (similar to > how facebook chat shows a list of your friends who are currently > online) > 3. Allow an administrator to have a live list view of all currently > logged in users > > Are there any features in Shiro that would help me with any of this? > I'm thinking this would need to be handled by my application and that > Shiro won't help. But I want to make sure this is the case before > moving forward. > > As this is a web app, I would need to somehow keep track of session > inactivity to determine if a user is "away" or if they've been > automatically logged out due to session timeout. > > Thanks! > Tauren >
