On Thu, Apr 16, 2009 at 6:27 AM, Pete Muir <pmuir(a)redhat.com> wrote:
Hi Clint,
Thanks for this! My only comment is that we should really do this as a
library that works for any 299 impl, and isn't tied to Web Beans. This is
quite easy to achieve:
(1) remove the dependence on webbeans-core
(2) extract the non-contextual injection code into a jsr299-utils library
and have both the RI and Wicket integration depend on it - this code should
basically offer a service to allow injection of non-contextual instances
using only 299 apis.
These are the things the wicket integration uses from webbeans-core:
(1) CurrentManager.rootManager(), to obtain the manager instance, i.e.
the singleton behavior
(2) WebBeansManager.injectNonContextualInstance, as you mention above
(3) ConversationContext.INSTANCE/ConversationBeanStore, as I just
store the cid in wicket and rely on the webbeans-core for threadlocal
storage of conversational data.
For (1) I could see moving this to jsr299-utils, but the singleton is
currently set directly by the bootstrap code, which won't work for
third party implementations. I could have CurrentManager observe
@Initialized Manager to set its instance.
For (2) there are a lot of dependencies on webbeans-core.
NonContextualInjector needs to be able to setup/teardown dependent
scopes, for example, and would also need almost all of
org.jboss.webbeans.injection. How would that be handled in a
jsr299-only way?
(3) If the ConversationContext were moved out of the core, all of the
AbstractMapContext related code would also have to move.
So it's all possible I think, and it's a worthwhile goal. I can take
it on, but only with a lot of guidance from the list, and it won't
make be done next week :)
-Clint
Let me know if you want me to work on (2)...
On 16 Apr 2009, at 03:14, webbeans-commits(a)lists.jboss.org wrote:
> Author: cpopetz
> Date: 2009-04-15 22:14:25 -0400 (Wed, 15 Apr 2009)
> New Revision: 2425
>
> Added:
> extensions/trunk/wicket/
> extensions/trunk/wicket/pom.xml
> extensions/trunk/wicket/src/
> extensions/trunk/wicket/src/main/
> extensions/trunk/wicket/src/main/java/
> extensions/trunk/wicket/src/main/java/org/
> extensions/trunk/wicket/src/main/java/org/jboss/
> extensions/trunk/wicket/src/main/java/org/jboss/webbeans/
> extensions/trunk/wicket/src/main/java/org/jboss/webbeans/wicket/
>
>
extensions/trunk/wicket/src/main/java/org/jboss/webbeans/wicket/WebBeansApplication.java
>
>
extensions/trunk/wicket/src/main/java/org/jboss/webbeans/wicket/WebBeansComponentInstantiationListener.java
>
>
extensions/trunk/wicket/src/main/java/org/jboss/webbeans/wicket/WebBeansMetaData.java
>
>
extensions/trunk/wicket/src/main/java/org/jboss/webbeans/wicket/WebBeansRequestCycle.java
>
>
extensions/trunk/wicket/src/main/java/org/jboss/webbeans/wicket/WebBeansWebRequestCycleProcessor.java
> Log:
> Initial commit of wicket integration.
>
>
> Added: extensions/trunk/wicket/pom.xml
> ===================================================================
> --- extensions/trunk/wicket/pom.xml (rev 0)
> +++ extensions/trunk/wicket/pom.xml 2009-04-16 02:14:25 UTC (rev 2425)
> @@ -0,0 +1,56 @@
> +<project
xmlns="http://maven.apache.org/POM/4.0.0"
>
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
>
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0
>
http://maven.apache.org/maven-v4_0_0.xsd">
> + <parent>
> + <artifactId>webbeans-parent</artifactId>
> + <groupId>org.jboss.webbeans</groupId>
> + <version>1.0.0-SNAPSHOT</version>
> + </parent>
> + <modelVersion>4.0.0</modelVersion>
> + <groupId>org.jboss.webbeans</groupId>
> + <artifactId>webbeans-wicket</artifactId>
> + <version>1.0.0-SNAPSHOT</version>
> + <name>Web Beans Wicket Integration</name>
> + <dependencies>
> +
> + <dependency>
> + <groupId>org.testng</groupId>
> + <artifactId>testng</artifactId>
> + <scope>test</scope>
> + <classifier>jdk15</classifier>
> + <exclusions>
> + <exclusion>
> + <artifactId>junit</artifactId>
> + <groupId>junit</groupId>
> + </exclusion>
> + </exclusions>
> + </dependency>
> + <dependency>
> + <groupId>org.jboss.webbeans</groupId>
> + <artifactId>jsr299-api</artifactId>
> + </dependency>
> + <dependency>
> + <groupId>org.jboss.webbeans</groupId>
> + <artifactId>webbeans-core</artifactId>
> + <scope>provided</scope>
> + </dependency>
> + <dependency>
> + <groupId>org.apache.wicket</groupId>
> + <artifactId>wicket</artifactId>
> + <version>${wicket.version}</version>
> + </dependency>
> + <dependency>
> + <groupId>javax.servlet</groupId>
> + <artifactId>servlet-api</artifactId>
> + <scope>provided</scope>
> + </dependency>
> +
> + </dependencies>
> +
> + <build>
> + <defaultGoal>install</defaultGoal>
> + </build>
> +
> + <properties>
> + <wicket.version>1.3-SNAPSHOT</wicket.version>
> + </properties>
> +
> +</project>
>
> Added:
>
extensions/trunk/wicket/src/main/java/org/jboss/webbeans/wicket/WebBeansApplication.java
> ===================================================================
> ---
>
extensions/trunk/wicket/src/main/java/org/jboss/webbeans/wicket/WebBeansApplication.java
> (rev 0)
> +++
>
extensions/trunk/wicket/src/main/java/org/jboss/webbeans/wicket/WebBeansApplication.java
> 2009-04-16 02:14:25 UTC (rev 2425)
> @@ -0,0 +1,54 @@
> +package org.jboss.webbeans.wicket;
> +
> +
> +import org.apache.wicket.Request;
> +import org.apache.wicket.RequestCycle;
> +import org.apache.wicket.Response;
> +import org.apache.wicket.protocol.http.WebApplication;
> +import org.apache.wicket.protocol.http.WebRequest;
> +import org.apache.wicket.protocol.http.WebResponse;
> +import org.apache.wicket.request.IRequestCycleProcessor;
> +
> +/**
> + * A convenience subclass of wicket's WebApplication which adds the hooks
> necessary to use JSR-299 injections
> + * in wicket components, as well as manage JSR-299 conversation scopes
> with Wicket page metadata. If you have
> + * your own WebApplication subclass, and can't subclass this class, you
> just need to do the three things that this
> + * class does, i.e. register the WebBeansComponentInstantiationListener,
> and override the two methods below to return
> + * the RequestCycle and IRequestCycleProcessor subclasses specific to
> WebBeans, or your subclasses of those classes.
> + * @author cpopetz
> + *
> + * @see WebApplication
> + * @see WebBeansWebRequestCycleProcessor
> + * @see WebBeansRequestCycle
> + */
> +public abstract class WebBeansApplication extends WebApplication
> +{
> + /**
> + * Use the constructor to add our component instantiation listener
> + * @see WebBeansComponentInstantiationListener
> + */
> + public WebBeansApplication()
> + {
> + addComponentInstantiationListener(new
> WebBeansComponentInstantiationListener());
> + }
> +
> + /**
> + * Override to return our WebBeans-specific request cycle processor
> + * @see WebBeansWebRequestCycleProcessor
> + */
> + @Override
> + protected IRequestCycleProcessor newRequestCycleProcessor()
> + {
> + return new WebBeansWebRequestCycleProcessor();
> + }
> +
> + /**
> + * Override to return our WebBeans-specific request cycle
> + * @see WebBeansRequestCycle
> + */
> + @Override
> + public RequestCycle newRequestCycle(final Request request, final
> Response response)
> + {
> + return new WebBeansRequestCycle(this, (WebRequest) request,
> (WebResponse) response);
> + }
> +}
>
>
> Property changes on:
>
extensions/trunk/wicket/src/main/java/org/jboss/webbeans/wicket/WebBeansApplication.java
> ___________________________________________________________________
> Name: svn:executable
> + *
>
> Added:
>
extensions/trunk/wicket/src/main/java/org/jboss/webbeans/wicket/WebBeansComponentInstantiationListener.java
> ===================================================================
> ---
>
extensions/trunk/wicket/src/main/java/org/jboss/webbeans/wicket/WebBeansComponentInstantiationListener.java
> (rev 0)
> +++
>
extensions/trunk/wicket/src/main/java/org/jboss/webbeans/wicket/WebBeansComponentInstantiationListener.java
> 2009-04-16 02:14:25 UTC (rev 2425)
> @@ -0,0 +1,20 @@
> +package org.jboss.webbeans.wicket;
> +
> +import org.apache.wicket.Component;
> +import org.apache.wicket.application.IComponentInstantiationListener;
> +import org.jboss.webbeans.CurrentManager;
> +import org.jboss.webbeans.manager.api.WebBeansManager;
> +
> +/**
> + * This listener uses the WebBeansManager to handle injections for all
> wicket components.
> + * @author cpopetz
> + * @see WebBeansManager
> + *
> + */
> +public class WebBeansComponentInstantiationListener implements
> IComponentInstantiationListener
> +{
> + public void onInstantiation(Component component)
> + {
> + ((WebBeansManager)
> CurrentManager.rootManager()).injectNonContextualInstance(component);
> + }
> +}
> \ No newline at end of file
>
>
> Property changes on:
>
extensions/trunk/wicket/src/main/java/org/jboss/webbeans/wicket/WebBeansComponentInstantiationListener.java
> ___________________________________________________________________
> Name: svn:executable
> + *
>
> Added:
>
extensions/trunk/wicket/src/main/java/org/jboss/webbeans/wicket/WebBeansMetaData.java
> ===================================================================
> ---
>
extensions/trunk/wicket/src/main/java/org/jboss/webbeans/wicket/WebBeansMetaData.java
> (rev 0)
> +++
>
extensions/trunk/wicket/src/main/java/org/jboss/webbeans/wicket/WebBeansMetaData.java
> 2009-04-16 02:14:25 UTC (rev 2425)
> @@ -0,0 +1,21 @@
> +package org.jboss.webbeans.wicket;
> +
> +import org.apache.wicket.MetaDataKey;
> +
> +/**
> + * Public storage for the metadata key used by the WebBeans integration
> to store
> + * conversation ids in wicket page metadata.
> + * @author cpopetz
> + *
> + */
> +public class WebBeansMetaData
> +{
> +
> + /**
> + * This is the key we will use to to store the conversation metadata
> in the
> + * wicket page.
> + */
> + public static final MetaDataKey CID = new MetaDataKey(String.class) {
> + private static final long serialVersionUID = -8788010688731927318L;
> + };
> +}
>
>
> Property changes on:
>
extensions/trunk/wicket/src/main/java/org/jboss/webbeans/wicket/WebBeansMetaData.java
> ___________________________________________________________________
> Name: svn:executable
> + *
>
> Added:
>
extensions/trunk/wicket/src/main/java/org/jboss/webbeans/wicket/WebBeansRequestCycle.java
> ===================================================================
> ---
>
extensions/trunk/wicket/src/main/java/org/jboss/webbeans/wicket/WebBeansRequestCycle.java
> (rev 0)
> +++
>
extensions/trunk/wicket/src/main/java/org/jboss/webbeans/wicket/WebBeansRequestCycle.java
> 2009-04-16 02:14:25 UTC (rev 2425)
> @@ -0,0 +1,108 @@
> +package org.jboss.webbeans.wicket;
> +
> +import javax.context.Conversation;
> +import javax.inject.manager.Manager;
> +
> +import org.apache.wicket.IRequestTarget;
> +import org.apache.wicket.Page;
> +import org.apache.wicket.Response;
> +import org.apache.wicket.protocol.http.WebApplication;
> +import org.apache.wicket.protocol.http.WebRequest;
> +import org.apache.wicket.protocol.http.WebRequestCycle;
> +import
> org.apache.wicket.request.target.component.BookmarkablePageRequestTarget;
> +import org.apache.wicket.request.target.component.IPageRequestTarget;
> +import org.jboss.webbeans.CurrentManager;
> +import org.jboss.webbeans.context.ConversationContext;
> +import org.jboss.webbeans.conversation.ConversationManager;
> +import org.jboss.webbeans.servlet.ConversationBeanStore;
> +
> +/**
> + * WebBeansRequestCycle is a subclass of the standard wicket
> WebRequestCycle which:
> + * <ul>
> + * <li>restores long-running conversations specified in wicket page
> metadata when a page target is first used.
> + * <li>propagates long running conversations to new page targets by
> specifying the above metadata
> + * <li>propagates long running conversations across redirects through the
> use of a request parameter if the
> + * redirect is handled with a BookmarkablePageRequest
> + * <li> Sets up the conversational context
> + * </ul>
> + * @see WebBeansWebRequestCycleProcessor Which handles propogation of
> conversation data for newly-started
> + * long running conversations, by storing their ids in the page metadata
> + * @author cpopetz
> + *
> + */
> +public class WebBeansRequestCycle extends WebRequestCycle
> +{
> + public WebBeansRequestCycle(WebApplication application, WebRequest
> request, Response response)
> + {
> + super(application, request, response);
> + }
> +
> + /**
> + * Override to set up the conversation context and to choose the
> conversation if a conversation id
> + * is present in target metadata.
> + */
> + @Override
> + protected void onRequestTargetSet(IRequestTarget target)
> + {
> + super.onRequestTargetSet(target);
> +
> + Page page = null;
> + if (target instanceof IPageRequestTarget)
> + {
> + page = ((IPageRequestTarget) target).getPage();
> + }
> +
> + //Two possible specifications of cid: page metadata or request url;
> the latter is used
> + //to propagate the conversation to mounted (bookmarkable) paths
> after a redirect
> +
> + String specifiedCid = null;
> + if (page != null)
> + {
> + specifiedCid = (String) page.getMetaData(WebBeansMetaData.CID);
> + }
> + else
> + {
> + specifiedCid = request.getParameter("cid");
> + }
> +
> + Manager manager = CurrentManager.rootManager();
> + Conversation conversation =
> manager.getInstanceByType(Conversation.class);
> +
> + //restore a conversation if it exists
> + if (specifiedCid != null)
> + {
> + // Restore this conversation
> +
>
manager.getInstanceByType(ConversationManager.class).beginOrRestoreConversation(specifiedCid);
> + }
> +
> + //handle propagation of existing long running converstaions to new
> targets
> + if (conversation.isLongRunning())
> + {
> + //Note that we can't propagate conversations with other redirect
> targets like
> + //RequestRedirectTarget through this mechanism, because it does
> not provide an
> + //interface to modify its target URL. If propagation with those
> targets is to be supported,
> + //it needs a custom Response subclass.
> + if (isRedirect() && target instanceof
> BookmarkablePageRequestTarget)
> + {
> + BookmarkablePageRequestTarget bookmark =
> (BookmarkablePageRequestTarget) target;
> + //if a cid has already been specified, don't override it
> + if (!bookmark.getPageParameters().containsKey("cid"))
> + bookmark.getPageParameters().add("cid",
> conversation.getId());
> + }
> +
> + //If we have a target page, propagate the conversation to the
> page's metadata
> + if (page != null)
> + {
> + page.setMetaData(WebBeansMetaData.CID, conversation.getId());
> + }
> + }
> +
> + //Now set up the conversational context if it isn't already
> + if (!ConversationContext.INSTANCE.isActive())
> + {
> + ConversationContext.INSTANCE.setBeanStore(
> + new
> ConversationBeanStore(((WebRequest)request).getHttpServletRequest().getSession(),
> conversation.getId()));
> + ConversationContext.INSTANCE.setActive(true);
> + }
> + }
> +}
> \ No newline at end of file
>
>
> Property changes on:
>
extensions/trunk/wicket/src/main/java/org/jboss/webbeans/wicket/WebBeansRequestCycle.java
> ___________________________________________________________________
> Name: svn:executable
> + *
>
> Added:
>
extensions/trunk/wicket/src/main/java/org/jboss/webbeans/wicket/WebBeansWebRequestCycleProcessor.java
> ===================================================================
> ---
>
extensions/trunk/wicket/src/main/java/org/jboss/webbeans/wicket/WebBeansWebRequestCycleProcessor.java
> (rev 0)
> +++
>
extensions/trunk/wicket/src/main/java/org/jboss/webbeans/wicket/WebBeansWebRequestCycleProcessor.java
> 2009-04-16 02:14:25 UTC (rev 2425)
> @@ -0,0 +1,44 @@
> +package org.jboss.webbeans.wicket;
> +
> +import javax.context.Conversation;
> +
> +import org.apache.wicket.Page;
> +import org.apache.wicket.RequestCycle;
> +import org.apache.wicket.protocol.http.WebRequestCycleProcessor;
> +import org.jboss.webbeans.CurrentManager;
> +import org.jboss.webbeans.context.ConversationContext;
> +import org.jboss.webbeans.conversation.ConversationManager;
> +
> +/**
> + * WebBeansWebRequestCycleProcessor is a subclass of the standard wicket
> WebRequestCycleProcessor which saves the conversation id
> + * of any long-running cornversation in wicket page metadata. It also
> cleans up the conversation context.
> + *
> + * @author cpopetz
> + *
> + */
> +
> +public class WebBeansWebRequestCycleProcessor extends
> WebRequestCycleProcessor
> +{
> + /**
> + * If a long running conversation has been started, store its id into
> page metadata
> + */
> + @Override
> + public void respond(RequestCycle requestCycle)
> + {
> + super.respond(requestCycle);
> + Conversation conversation =
> CurrentManager.rootManager().getInstanceByType(Conversation.class);
> + if (conversation.isLongRunning())
> + {
> + Page page = RequestCycle.get().getResponsePage();
> + if (page != null)
> + {
> + page.setMetaData(WebBeansMetaData.CID, conversation.getId());
> + }
> + }
> +
> + //cleanup and deactivate the conversation context
> +
> +
>
CurrentManager.rootManager().getInstanceByType(ConversationManager.class).cleanupConversation();
> + ConversationContext.INSTANCE.setActive(false);
> + }
> +}
> \ No newline at end of file
>
>
> Property changes on:
>
extensions/trunk/wicket/src/main/java/org/jboss/webbeans/wicket/WebBeansWebRequestCycleProcessor.java
> ___________________________________________________________________
> Name: svn:executable
> + *
>
> _______________________________________________
> webbeans-commits mailing list
> webbeans-commits(a)lists.jboss.org
>
https://lists.jboss.org/mailman/listinfo/webbeans-commits
--
Pete Muir
http://www.seamframework.org
http://in.relation.to/Bloggers/Pete