incubator-jspwiki-dev mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From Andrew Jaquith <>
Subject Re: WikiContext & JCR Sessions
Date Mon, 25 Aug 2008 04:10:04 GMT
> My initial feeling would be to make the JCR Session a part of the  
> WikiContext (or, to be precise, a JCRWikiContext, which would be a  
> concrete class which would implement a WikiContext interface).  When  
> the WikiContext is created, the Session is created too, and when the  
> WikiContext expires, the Session is logged out.  We could also add a  
> method to flush all changes. This would provide  
> fairly logical lifecycle management.

Hmm. I don't think this is a good idea. WikiContexts should really  
just be simple receptacles for form properties, plus some handler  
events that do things based on user actions. That is, they should be  
JavaBeans with some additional "verb" methods. (Or in Stripes  
parlance: ActionBean property getters and setters, plus event handler  
methods.) Putting JCR functionality into WikiContexts makes these  
things heavier, in my view, than they should be.

There are two potentially better places to locate JCR functionality.  
One place might be in the WikiSession, ideally as a property of the  
WikiSession (e.g., getRepositoryManager()/setRepositoryManager()).  
This is a pretty good place, actually, because WikiSession has  
privileged access to the JAAS Subject that contains the user's  
Principal set, and the user's private credentials (which we haven't  
exploited yet).

The other place would be the ActionBeanContext, which Stripes or  
WikiActionBeanFactory associates with every WikiActionBean/ 
WikiContext. Our implementation is tentatively called the  
WikiActionBeanContext (not suprisingly), and right now it doesn't do  
much more than the standard ActionBeanContext than contain a reference  
to the WikiEngine and WikiSession. We could certainly add JCR  
functions to that, as well.

So, those are my two suggested places.

> The bad thing is that means that we need to carry WikiContext into  
> quite a few places after that.  Unless we turn WikiContext into the  
> main repository interface as well, providing things like a Search  
> interface as well.  That means that it would inherit pretty much all  
> of the functionality of the WikiEngine, which might make it a bit  
> too unwieldy.

Remember that most of the "events" a user invokes that cause  
interesting things to happen will be done through event handler  
methods. Event handler methods are where the JSP scriptlet code will  
move to, and they will do most of the heavy lifting for business logic.

Also, WikiActionBean will be guaranteed to contain references to the  
WikiSession (as is the case today), or to the WikiActionBeanContext  
(as will be the case in 3.0). It would not be much work to do an extra  
getActionBeanContext().getRepositoryManager() and then invoke the  
functions that are needed.

> My current idea is to turn WikiPages into essentially  
> representatives of Nodes.  Calling WikiPage.getContent() will return  
> the content of the page and WikiPage.setContent() will set it. This  
> provides a really neat way of managing the data, since e.g.  
> WikiPage.get/setAttribute() could be automatically persisted.  The  
> bad thing, obviously, would be that since Nodes contain a reference  
> to the Session where they came from, you *cannot* cache a WikiPage  
> across new invocations (e.g. threads).

WikiPages == Node sounds good. We'll need to have a bit more  
discussion on the degree of auto-commit you foresee. I'm thinking in  
particular of the side-effects this might have if used in combination  
with the WikiPageTypeConverter (for 3.0), which will wire up and  
automatically set the correct WikiPage for a WikiActionBean based on  
the "page" parameter set in the request.

But beyond that, WikiPage.setContent()/getContent() sound like good  
places for persistence logic. PageManager might be good too. I tend to  
prefer data objects that are fairly stupid, and Manager classes that  
are smart.

> Retaining the old WikiEngine API is problematic because the passed  
> arguments only contain Strings.  Since there is no session  
> management in that API, we would need to do Repository.login() every  
> time e.g. pageExists() is called, and *that* would become a bit too  
> rough.  So my preference would be, frankly, to dump existing  
> WikiEngine API and make something nicer.  We can have a lookalike  
> API, but that's going to be slow.

WikiEngine should go on a diet. I'd like to see something really  
simple in 3.0. WikiEngine should just contains references to the major  
Manager classes, and eliminates convenience methods like saveText()  
and pageExists(), chiefly because they don't contain have method  
signatures with the right parameters. Certainly, if JCR needs "session  
awareness" we'll need to do a different API anyhow, so ditching the  
existing WikiEngine methods would be good.

PS. One more thought on WikiSession. The WikiSession's Subject would  
be a good place to stash the JCR credentials (username and password).  
I'm thinking, in particular, of Subject.setPublicCredentials() and  

> An obvious option would be to use a ThreadLocal for a Session, but  
> that would pretty much make it a global, and the other problem is  
> that then lifecycle management becomes a bit hazy - if there are  
> unsaved changes, the session would grow uncontrollably.  So there  
> would need to be a separate flushing action at some point...  But  
> that would allow us to keep the existing API.

Well, we all know how important it is to have separate flushing  
actions. Otherwise, things would get messy indeed. <cough>

It might make sense to write a "JCR Monitor" similar to  
SessionMonitor, but for JCR sessions... perhaps something that  
"autosaves" or "autoflushes" every few minutes? This might be a good  
place to use JMX TimerMBean, too. (Actually, I'd kind of like to  
refactor the WikiBackgroundThread to be TimerMBeans, because the  
existing implementation doesn't always terminate cleanly... but that  
is another discussion...)

> Any thoughts?  Gotchas?  Obvious ideas I've ignored?  It would be a  
> good idea if others read up on the JCR documentation as well - the  
> spec is fairly well written, but it's quite long.

I wish I had the time. :)

View raw message