[jboss-svn-commits] JBL Code SVN: r36709 - in labs/jbossrules/tags/5.2.0.M1: drools-persistence-jpa and 23 other directories.

jboss-svn-commits at lists.jboss.org jboss-svn-commits at lists.jboss.org
Thu Feb 24 12:26:50 EST 2011


Author: ge0ffrey
Date: 2011-02-24 12:26:49 -0500 (Thu, 24 Feb 2011)
New Revision: 36709

Added:
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/.gitignore
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/build.properties
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/pom.xml
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/ApplicationScopedPersistenceContext.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/PersistenceContext.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/PersistenceContextManager.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/SessionMarshallingHelper.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/SingleSessionCommandService.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/TransactionManager.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/TransactionSynchronization.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/TransactionSynchronizationRegistryHelper.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/TransactionablePersistentContext.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/info/
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/info/SessionInfo.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/info/WorkItemInfo.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jpa/
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jpa/JpaJDKTimerService.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jpa/JpaPersistenceContext.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jpa/JpaPersistenceContextManager.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jpa/KnowledgeStoreServiceImpl.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jpa/marshaller/
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jpa/marshaller/JPAPlaceholderResolverStrategy.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jpa/processinstance/
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jpa/processinstance/JPAWorkItemManager.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jpa/processinstance/JPAWorkItemManagerFactory.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jta/
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jta/JtaTransactionManager.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jta/JtaTransactionSynchronizationAdapter.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/map/
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/map/EnvironmentBuilder.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/map/KnowledgeSessionStorage.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/map/KnowledgeSessionStorageEnvironmentBuilder.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/map/ManualTransactionManager.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/map/MapBasedPersistenceContext.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/map/MapPersistenceContextManager.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/map/NonTransactionalPersistentSession.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/osgi/
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/osgi/Activator.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/java/
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/java/org/
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/java/org/drools/
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/java/org/drools/persistence/
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/java/org/drools/persistence/map/
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/java/org/drools/persistence/map/impl/
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/java/org/drools/persistence/map/impl/Buddy.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/java/org/drools/persistence/map/impl/JpaBasedPersistenceTest.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/java/org/drools/persistence/map/impl/MapBasedPersistenceTest.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/java/org/drools/persistence/map/impl/MapPersistenceTest.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/java/org/drools/persistence/session/
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/java/org/drools/persistence/session/JpaPersistentStatefulSessionTest.java
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/resources/
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/resources/META-INF/
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/resources/META-INF/orm.xml
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/resources/META-INF/persistence.xml
   labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/resources/jndi.properties
Log:
All monolothic build versions (<= 5.2.0.M1) stay in subversion

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/.gitignore
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/.gitignore	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/.gitignore	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,13 @@
+/target
+/local
+
+# Eclipse, Netbeans and IntelliJ files
+/.*
+!.gitignore
+/nbproject
+/*.ipr
+/*.iws
+/*.iml
+
+# The META-INF directory is generated by the maven-felix-plugin
+META-INF

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/build.properties
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/build.properties	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/build.properties	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,12 @@
+src.includes = .,\
+               build.properties,\
+               META-INF/,\
+               src/,\
+               pom.xml
+bin.includes = .,\
+               META-INF/,\
+               build.properties               
+source.. = src/main/java/,\
+           src/main/resources/
+output.. = target/classes/     
+jars.compile.order = .          

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/pom.xml
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/pom.xml	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/pom.xml	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,196 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<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">
+
+  <modelVersion>4.0.0</modelVersion>
+  <parent>
+    <groupId>org.drools</groupId>
+    <artifactId>drools</artifactId>
+    <version>5.2.0.M1</version>
+  </parent>
+
+  <artifactId>drools-persistence-jpa</artifactId>
+  <packaging>jar</packaging>
+  <name>Drools :: Persistence :: JPA</name>
+
+  <build>
+    <plugins>
+      <plugin>
+        <artifactId>maven-jar-plugin</artifactId>
+        <configuration>
+          <archive>
+            <manifestFile>META-INF/MANIFEST.MF</manifestFile>
+          </archive>
+        </configuration>
+      </plugin>
+      <plugin>
+        <groupId>org.apache.felix</groupId>
+        <artifactId>maven-bundle-plugin</artifactId>
+        <extensions>true</extensions>
+        <executions>
+          <execution>
+            <id>manifest</id>
+            <phase>process-classes</phase>
+            <goals>
+              <goal>manifest</goal>
+            </goals>
+          </execution>
+        </executions>
+        <configuration>
+          <manifestLocation>META-INF</manifestLocation>
+          <instructions>
+            <_removeheaders>Ignore-Package</_removeheaders>
+            <Require-Bundle>org.drools.core;bundle-version="5.2.0.M1", org.drools.compiler;bundle-version="5.2.0.M1"</Require-Bundle>
+            <Import-Package>!org.drools.*, *</Import-Package>
+            <Export-Package>org.drools.*</Export-Package>
+            <DynamicImport-Package>*</DynamicImport-Package>
+            <!--Bundle-Activator>org.drools.osgi.core.Activator</Bundle-Activator-->
+          </instructions>
+        </configuration>
+      </plugin>
+    </plugins>
+  </build>
+
+  <dependencies>
+    <dependency>
+      <groupId>org.drools</groupId>
+      <artifactId>drools-api</artifactId>
+    </dependency>
+
+    <dependency>
+      <groupId>org.drools</groupId>
+      <artifactId>drools-core</artifactId>
+    </dependency>
+
+    <dependency>
+      <groupId>org.drools</groupId>
+      <artifactId>drools-compiler</artifactId>
+    </dependency>
+
+    <dependency>
+      <groupId>org.slf4j</groupId>
+      <artifactId>slf4j-api</artifactId>
+    </dependency>
+
+    <dependency>
+      <groupId>org.slf4j</groupId>
+      <artifactId>slf4j-log4j12</artifactId>
+      <scope>test</scope>
+    </dependency>
+
+    <dependency>
+      <groupId>com.sun.xml.bind</groupId>
+      <artifactId>jaxb-impl</artifactId>
+      <scope>provided</scope>
+    </dependency>
+    <dependency>
+      <groupId>com.sun.xml.bind</groupId>
+      <artifactId>jaxb-xjc</artifactId>
+      <scope>provided</scope>
+    </dependency>
+
+    <dependency>
+      <groupId>org.apache.felix</groupId>
+      <artifactId>org.osgi.core</artifactId>
+      <scope>provided</scope>
+    </dependency>
+    <dependency>
+      <groupId>org.apache.felix</groupId>
+      <artifactId>org.osgi.compendium</artifactId>
+      <scope>provided</scope>
+    </dependency>
+
+    <!-- Hibernate -->
+    <dependency>
+      <groupId>org.hibernate</groupId>
+      <artifactId>hibernate-entitymanager</artifactId>
+    </dependency>
+
+    <dependency>
+      <groupId>org.hibernate</groupId>
+      <artifactId>hibernate-annotations</artifactId>
+    </dependency>
+
+    <dependency>
+      <groupId>org.hibernate</groupId>
+      <artifactId>hibernate-commons-annotations</artifactId>
+    </dependency>
+
+    <dependency>
+      <groupId>org.hibernate</groupId>
+      <artifactId>hibernate-core</artifactId>
+    </dependency>
+
+    <!-- HSQLDB -->
+    <dependency>
+      <groupId>com.h2database</groupId>
+      <artifactId>h2</artifactId>
+      <scope>test</scope>
+    </dependency>
+
+    <dependency>
+      <groupId>javax.persistence</groupId>
+      <artifactId>persistence-api</artifactId>
+    </dependency>
+
+    <dependency>
+      <groupId>dom4j</groupId>
+      <artifactId>dom4j</artifactId>
+    </dependency>
+
+    <dependency>
+      <groupId>javassist</groupId>
+      <artifactId>javassist</artifactId>
+    </dependency>
+
+    <dependency>
+      <groupId>javax.transaction</groupId>
+      <artifactId>jta</artifactId>
+    </dependency>
+
+    <dependency>
+      <groupId>org.codehaus.btm</groupId>
+      <artifactId>btm</artifactId>
+      <scope>test</scope>
+    </dependency>
+
+    <!--dependency>
+         <groupId>org.objectweb.jotm</groupId>
+         <artifactId>com.springsource.org.objectweb.jotm</artifactId>
+         <version>2.0.10</version>
+      </dependency>
+
+      <dependency>
+         <groupId>com.experlog.xapool</groupId>
+         <artifactId>com.springsource.org.enhydra.jdbc</artifactId>
+         <version>1.5.0</version>
+     </dependency>
+
+    <dependency>
+       <groupId>org.apache.directory</groupId>
+       <artifactId>com.springsource.org.apache.directory.server.jndi</artifactId>
+       <version>1.0.2</version>
+    </dependency>
+
+    <dependency>
+        <groupId>javax.resource</groupId>
+        <artifactId>com.springsource.javax.resource</artifactId>
+        <version>1.5.0</version>
+    </dependency-->
+    <dependency>
+      <groupId>org.eclipse.jdt.core.compiler</groupId>
+      <artifactId>ecj</artifactId>
+      <scope>test</scope>
+    </dependency>
+    <dependency>
+      <groupId>antlr</groupId>
+      <artifactId>antlr</artifactId>
+      <scope>test</scope>
+    </dependency>
+    <dependency>
+      <groupId>org.antlr</groupId>
+      <artifactId>antlr-runtime</artifactId>
+      <scope>test</scope>
+    </dependency>    
+  </dependencies>
+
+</project>

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/ApplicationScopedPersistenceContext.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/ApplicationScopedPersistenceContext.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/ApplicationScopedPersistenceContext.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,18 @@
+package org.drools.persistence;
+
+import org.drools.runtime.Environment;
+import org.drools.runtime.KnowledgeSessionConfiguration;
+import org.drools.runtime.StatefulKnowledgeSession;
+
+public interface ApplicationScopedPersistenceContext {
+
+    StatefulKnowledgeSession loadStatefulKnowledgeSession(long sessionId,
+            KnowledgeSessionConfiguration kconf,
+            Environment env);
+
+    void save(StatefulKnowledgeSession internalKnowledgeSession);
+
+    void update(StatefulKnowledgeSession internalKnowledgeSession);
+
+    void setLastModificationDate(long sessionId);
+}

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/PersistenceContext.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/PersistenceContext.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/PersistenceContext.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,26 @@
+package org.drools.persistence;
+
+import org.drools.persistence.info.SessionInfo;
+import org.drools.persistence.info.WorkItemInfo;
+
+public interface PersistenceContext {
+
+    void persist(SessionInfo entity);
+
+    public SessionInfo findSessionInfo(Integer id);
+
+    boolean isOpen();
+
+    void joinTransaction();
+
+    void close();
+
+    void persist(WorkItemInfo workItemInfo);
+
+    WorkItemInfo findWorkItemInfo(Long id);
+
+    void remove(WorkItemInfo workItemInfo);
+
+    WorkItemInfo merge(WorkItemInfo workItemInfo);
+
+}

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/PersistenceContextManager.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/PersistenceContextManager.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/PersistenceContextManager.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,13 @@
+package org.drools.persistence;
+
+public interface PersistenceContextManager {
+    PersistenceContext getApplicationScopedPersistenceContext();
+    
+    PersistenceContext getCommandScopedPersistenceContext();
+    
+    void beginCommandScopedEntityManager();
+    
+    void endCommandScopedEntityManager();
+
+    void dispose();
+}

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/SessionMarshallingHelper.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/SessionMarshallingHelper.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/SessionMarshallingHelper.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,116 @@
+package org.drools.persistence;
+
+import java.io.ByteArrayInputStream;
+import java.io.ByteArrayOutputStream;
+import java.io.IOException;
+
+import org.drools.KnowledgeBase;
+import org.drools.marshalling.Marshaller;
+import org.drools.marshalling.MarshallerFactory;
+import org.drools.marshalling.ObjectMarshallingStrategy;
+import org.drools.runtime.Environment;
+import org.drools.runtime.EnvironmentName;
+import org.drools.runtime.KnowledgeSessionConfiguration;
+import org.drools.runtime.StatefulKnowledgeSession;
+
+public class SessionMarshallingHelper {
+
+    private KnowledgeBase                 kbase;
+    private KnowledgeSessionConfiguration conf;
+    private StatefulKnowledgeSession      ksession;
+    private Marshaller                    marshaller;
+    private Environment                   env;
+
+    /**
+     * Exist Info, so load session from here
+     * @param info
+     * @param ruleBase
+     * @param conf
+     * @param marshallingConfiguration
+     */
+    public SessionMarshallingHelper(KnowledgeBase kbase,
+                                       KnowledgeSessionConfiguration conf,
+                                       Environment env) {
+        this.kbase = kbase;
+        this.conf = conf;
+        this.env = env;
+        ObjectMarshallingStrategy[] strategies = (ObjectMarshallingStrategy[]) env.get( EnvironmentName.OBJECT_MARSHALLING_STRATEGIES );
+        if (strategies  != null ) {
+            // use strategies if provided in the environment
+            this.marshaller = MarshallerFactory.newMarshaller( kbase, strategies );
+        } else {
+            this.marshaller = MarshallerFactory.newMarshaller( kbase ) ;  
+        }
+    }
+
+    /** 
+     * new session, don't write now as info will request it on update callback
+     * @param info
+     * @param session
+     * @param conf
+     * @param marshallingConfiguration
+     */
+    public SessionMarshallingHelper(StatefulKnowledgeSession ksession,
+                                       KnowledgeSessionConfiguration conf) {
+        this.ksession = ksession;
+        this.kbase = ksession.getKnowledgeBase();
+        this.conf = conf;
+        this.env = ksession.getEnvironment();
+        ObjectMarshallingStrategy[] strategies = (ObjectMarshallingStrategy[]) this.env.get( EnvironmentName.OBJECT_MARSHALLING_STRATEGIES );
+        if (strategies  != null ) {
+            // use strategies if provided in the environment
+            this.marshaller = MarshallerFactory.newMarshaller( kbase, strategies );
+        } else {
+            this.marshaller = MarshallerFactory.newMarshaller( kbase ) ;  
+        }
+        
+    }
+
+    public byte[] getSnapshot() {
+        ByteArrayOutputStream baos = new ByteArrayOutputStream();
+        try {
+            marshaller.marshall( baos,
+                                 ksession );
+        } catch ( IOException e ) {
+            throw new RuntimeException( "Unable to get session snapshot",
+                                        e );
+        }
+
+        return baos.toByteArray();
+    }
+
+    public StatefulKnowledgeSession loadSnapshot(byte[] bytes,
+                                                 StatefulKnowledgeSession ksession) {
+        this.ksession = ksession;
+        ByteArrayInputStream bais = new ByteArrayInputStream( bytes );
+        try {
+            if ( this.ksession != null ) {
+                this.marshaller.unmarshall( bais,
+                                            this.ksession );                
+            } else {
+                this.ksession = this.marshaller.unmarshall( bais,
+                                                            this.conf,
+                                                            this.env );                
+            }
+        } catch ( Exception e ) {
+            throw new RuntimeException( "Unable to load session snapshot",
+                                        e );
+        }
+        return this.ksession;
+    }
+
+
+    public StatefulKnowledgeSession getObject() {
+        return ksession;
+    }
+
+    public KnowledgeBase getKbase() {
+        return kbase;
+    }
+
+    public KnowledgeSessionConfiguration getConf() {
+        return conf;
+    }
+
+    
+}

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/SingleSessionCommandService.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/SingleSessionCommandService.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/SingleSessionCommandService.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,381 @@
+package org.drools.persistence;
+
+import java.lang.reflect.Constructor;
+import java.util.Collections;
+import java.util.Date;
+import java.util.IdentityHashMap;
+import java.util.Map;
+
+import org.drools.KnowledgeBase;
+import org.drools.RuleBase;
+import org.drools.SessionConfiguration;
+import org.drools.command.Command;
+import org.drools.command.Context;
+import org.drools.command.impl.ContextImpl;
+import org.drools.command.impl.GenericCommand;
+import org.drools.command.impl.KnowledgeCommandContext;
+import org.drools.command.runtime.DisposeCommand;
+import org.drools.common.EndOperationListener;
+import org.drools.common.InternalKnowledgeRuntime;
+import org.drools.impl.KnowledgeBaseImpl;
+import org.drools.persistence.info.SessionInfo;
+import org.drools.persistence.jpa.JpaJDKTimerService;
+import org.drools.persistence.jpa.JpaPersistenceContextManager;
+import org.drools.persistence.jpa.processinstance.JPAWorkItemManager;
+import org.drools.persistence.jta.JtaTransactionManager;
+import org.drools.runtime.Environment;
+import org.drools.runtime.EnvironmentName;
+import org.drools.runtime.KnowledgeSessionConfiguration;
+import org.drools.runtime.StatefulKnowledgeSession;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+public class SingleSessionCommandService
+    implements
+    org.drools.command.SingleSessionCommandService {
+    
+    Logger                               logger                                            = LoggerFactory.getLogger( getClass() );    
+
+    private SessionInfo                 sessionInfo;
+    private SessionMarshallingHelper marshallingHelper;
+
+    private StatefulKnowledgeSession    ksession;
+    private Environment                 env;
+    private KnowledgeCommandContext     kContext;
+
+    private TransactionManager          txm;
+    private PersistenceContextManager                  jpm;
+    
+    private volatile boolean  doRollback;
+    
+    private static Map<Object, Object> synchronizations = Collections.synchronizedMap( new IdentityHashMap<Object, Object>() );
+    
+    public static Map<Object, Object> txManagerClasses = Collections.synchronizedMap( new IdentityHashMap<Object, Object>() );
+
+    public void checkEnvironment(Environment env) {
+        if ( env.get( EnvironmentName.ENTITY_MANAGER_FACTORY ) == null &&
+             env.get( EnvironmentName.PERSISTENCE_CONTEXT_MANAGER ) == null  ) {
+            throw new IllegalArgumentException( "Environment must have an EntityManagerFactory " +
+            		                            "or a PersistenceContextManager instance" );
+        }
+
+        // @TODO log a warning that all transactions will be locally scoped using the EntityTransaction
+        //        if ( env.get( EnvironmentName.TRANSACTION_MANAGER ) == null ) {
+        //            throw new IllegalArgumentException( "Environment must have an EntityManagerFactory" );
+        //        }        
+    }
+
+    public SingleSessionCommandService(RuleBase ruleBase,
+                                       SessionConfiguration conf,
+                                       Environment env) {
+        this( new KnowledgeBaseImpl( ruleBase ),
+              conf,
+              env );
+    }
+
+    public SingleSessionCommandService(Integer sessionId,
+                                       RuleBase ruleBase,
+                                       SessionConfiguration conf,
+                                       Environment env) {
+        this( sessionId,
+              new KnowledgeBaseImpl( ruleBase ),
+              conf,
+              env );
+    }
+
+    public SingleSessionCommandService(KnowledgeBase kbase,
+                                       KnowledgeSessionConfiguration conf,
+                                       Environment env) {
+        if ( conf == null ) {
+            conf = new SessionConfiguration();
+        }
+        this.env = env;        
+        
+        checkEnvironment( this.env );        
+        
+        this.sessionInfo = new SessionInfo();
+
+        initTransactionManager( this.env );
+        
+        // create session but bypass command service
+        this.ksession = kbase.newStatefulKnowledgeSession(conf, this.env);
+        
+        this.kContext = new KnowledgeCommandContext( new ContextImpl( "ksession",
+                                                                      null ),
+                                                     null,
+                                                     null,
+                                                     this.ksession,
+                                                     null );
+
+        ((JpaJDKTimerService) ((InternalKnowledgeRuntime) ksession).getTimerService()).setCommandService( this );
+        
+        this.marshallingHelper = new SessionMarshallingHelper( this.ksession,
+                                                                  conf );
+        this.sessionInfo.setJPASessionMashallingHelper( this.marshallingHelper );
+        ((InternalKnowledgeRuntime) this.ksession).setEndOperationListener( new EndOperationListenerImpl( this.sessionInfo ) );        
+        
+        // Use the App scoped EntityManager if the user has provided it, and it is open.
+
+        try {
+            this.txm.begin();
+ 
+            //this.appScopedEntityManager.joinTransaction();
+            registerRollbackSync();
+
+            jpm.getApplicationScopedPersistenceContext().persist( this.sessionInfo );
+
+            this.txm.commit();
+
+        } catch ( Exception t1 ) {
+            try {
+                this.txm.rollback();
+            } catch ( Throwable t2 ) {
+                throw new RuntimeException( "Could not commit session or rollback",
+                                            t2 );
+            }
+            throw new RuntimeException( "Could not commit session",
+                                        t1 );
+        }
+
+        // update the session id to be the same as the session info id
+        ((InternalKnowledgeRuntime) ksession).setId( this.sessionInfo.getId() );
+
+    }
+
+    public SingleSessionCommandService(Integer sessionId,
+                                       KnowledgeBase kbase,
+                                       KnowledgeSessionConfiguration conf,
+                                       Environment env) {
+        if ( conf == null ) {
+            conf = new SessionConfiguration();
+        }
+                
+
+        this.env = env;
+        
+        checkEnvironment( this.env );
+        
+        initTransactionManager( this.env );
+
+        initKsession( sessionId,
+                      kbase,
+                      conf );
+    }
+
+    public void initKsession(Integer sessionId,
+                             KnowledgeBase kbase,
+                             KnowledgeSessionConfiguration conf) {
+        if ( !doRollback && this.ksession != null ) {
+            return;
+            // nothing to initialise
+        }
+        
+        this.doRollback = false;       
+
+        try {
+            this.sessionInfo = jpm.getApplicationScopedPersistenceContext().findSessionInfo( sessionId );
+        } catch ( Exception e ) {
+            throw new RuntimeException( "Could not find session data for id " + sessionId,
+                                        e );
+        }
+
+        if ( sessionInfo == null ) {
+            throw new RuntimeException( "Could not find session data for id " + sessionId );
+        }
+
+        if ( this.marshallingHelper == null ) {
+            // this should only happen when this class is first constructed
+            this.marshallingHelper = new SessionMarshallingHelper( kbase,
+                                                                      conf,
+                                                                      env );
+        }
+
+        this.sessionInfo.setJPASessionMashallingHelper( this.marshallingHelper );
+
+        // if this.ksession is null, it'll create a new one, else it'll use the existing one
+        this.ksession = this.marshallingHelper.loadSnapshot( this.sessionInfo.getData(),
+                                                             this.ksession );
+
+        // update the session id to be the same as the session info id
+        ((InternalKnowledgeRuntime) ksession).setId( this.sessionInfo.getId() );
+
+        ((InternalKnowledgeRuntime) this.ksession).setEndOperationListener( new EndOperationListenerImpl( this.sessionInfo ) );
+
+        ((JpaJDKTimerService) ((InternalKnowledgeRuntime) ksession).getTimerService()).setCommandService( this );
+        
+        if ( this.kContext == null ) {
+            // this should only happen when this class is first constructed
+            this.kContext = new KnowledgeCommandContext( new ContextImpl( "ksession",
+                                                                          null ),
+                                                         null,
+                                                         null,
+                                                         this.ksession,
+                                                         null );
+        }
+
+    }
+    
+    public void initTransactionManager(Environment env) {
+        Object tm = env.get( EnvironmentName.TRANSACTION_MANAGER );
+        if ( env.get( EnvironmentName.PERSISTENCE_CONTEXT_MANAGER ) != null &&
+             env.get( EnvironmentName.TRANSACTION_MANAGER ) != null ) {
+            this.txm = (TransactionManager) tm;
+            this.jpm = (PersistenceContextManager) env.get( EnvironmentName.PERSISTENCE_CONTEXT_MANAGER );
+        } else {
+            if ( tm != null && tm.getClass().getName().startsWith( "org.springframework" ) ) {
+                try {
+                    Class<?> cls = Class.forName( "org.drools.container.spring.beans.persistence.DroolsSpringTransactionManager" );
+                    Constructor<?> con = cls.getConstructors()[0];
+                    this.txm = (TransactionManager) con.newInstance( tm );
+                    logger.debug( "Instantiating  DroolsSpringTransactionManager" );
+                    
+                    if ( tm.getClass().getName().toLowerCase().contains( "jpa" ) ) {
+                        // configure spring for JPA and local transactions
+                        cls = Class.forName( "org.drools.container.spring.beans.persistence.DroolsSpringJpaManager" );
+                        con = cls.getConstructors()[0];
+                        this.jpm =  ( PersistenceContextManager) con.newInstance( new Object[] { this.env } );
+                    } else {
+                        // configure spring for JPA and distributed transactions 
+                    }
+                } catch ( Exception e ) {
+                    logger.warn( "Could not instatiate DroolsSpringTransactionManager" );
+                    throw new RuntimeException( "Could not instatiate org.drools.container.spring.beans.persistence.DroolsSpringTransactionManager", e );
+                }
+            } else {
+                logger.debug( "Instantiating  JtaTransactionManager" );
+                this.txm = new JtaTransactionManager( env.get( EnvironmentName.TRANSACTION ),
+                                                      env.get( EnvironmentName.TRANSACTION_SYNCHRONIZATION_REGISTRY ),
+                                                      tm ); 
+                try {
+                    Class<?> jpaPersistenceCtxMngrClass = Class.forName( "org.jbpm.persistence.JpaProcessPersistenceContextManager" );
+                    Constructor<?> jpaPersistenceCtxMngrCtor = jpaPersistenceCtxMngrClass.getConstructors()[0];
+                    this.jpm =  ( PersistenceContextManager) jpaPersistenceCtxMngrCtor.newInstance( new Object[] { this.env } );
+                } catch ( ClassNotFoundException e ) {
+                    this.jpm = new JpaPersistenceContextManager(this.env);
+                } catch ( Exception e ) {
+                    throw new RuntimeException("Error creating JpaProcessPersistenceContextManager", e);
+                }
+            }
+            env.set( EnvironmentName.PERSISTENCE_CONTEXT_MANAGER, this.jpm );
+            env.set( EnvironmentName.TRANSACTION_MANAGER, this.txm );
+        }
+    }
+
+    public static class EndOperationListenerImpl
+        implements
+        EndOperationListener {
+        private SessionInfo info;
+
+        public EndOperationListenerImpl(SessionInfo info) {
+            this.info = info;
+        }
+
+        public void endOperation(InternalKnowledgeRuntime kruntime) {
+            this.info.setLastModificationDate( new Date( kruntime.getLastIdleTimestamp() ) );
+        }
+    }
+
+    public Context getContext() {
+        return this.kContext;
+    }
+
+    public synchronized <T> T execute(Command<T> command) {
+        try {
+            txm.begin();
+            
+            initKsession( this.sessionInfo.getId(),
+                          this.marshallingHelper.getKbase(),
+                          this.marshallingHelper.getConf() );
+            
+            this.jpm.beginCommandScopedEntityManager();
+
+            //this.appScopedEntityManager.joinTransaction();
+            registerRollbackSync();
+
+            T result = ((GenericCommand<T>) command).execute( this.kContext );
+
+            txm.commit();
+
+            return result;
+
+        }catch (RuntimeException re){
+            rollbackTransaction(re);
+            throw re;
+        } catch ( Exception t1 ) {
+            rollbackTransaction(t1);
+            throw new RuntimeException("Wrapped exception see cause", t1);
+        } finally {
+            if ( command instanceof DisposeCommand ) {
+                this.jpm.dispose();
+            }
+        }
+    }
+
+    private void rollbackTransaction(Exception t1) {
+        try {
+            logger.error( "Could not commit session", t1 );
+            txm.rollback();
+        } catch ( Exception t2 ) {
+            logger.error( "Could not rollback", t2 );
+            throw new RuntimeException( "Could not commit session or rollback", t2 );
+        }
+    }
+
+    public void dispose() {
+        if ( ksession != null ) {
+            ksession.dispose();
+        }
+    }
+
+    public int getSessionId() {
+        return sessionInfo.getId();
+    }
+
+    private void registerRollbackSync() {
+        if ( synchronizations.get( this ) == null ) {
+            txm.registerTransactionSynchronization( new SynchronizationImpl( this ) );
+            synchronizations.put( this,
+                                  this );
+        }
+
+    }
+
+    private static class SynchronizationImpl
+        implements
+        TransactionSynchronization {
+
+        SingleSessionCommandService service;
+
+        public SynchronizationImpl(SingleSessionCommandService service) {
+            this.service = service;
+        }
+
+        public void afterCompletion(int status) {
+            if ( status != TransactionManager.STATUS_COMMITTED ) {
+                this.service.rollback();                
+            }
+
+            // always cleanup thread local whatever the result
+            SingleSessionCommandService.synchronizations.remove( this.service );
+            
+            this.service.jpm.endCommandScopedEntityManager();
+
+            StatefulKnowledgeSession ksession = this.service.ksession;
+            // clean up cached process and work item instances
+            if ( ksession != null ) {
+                ((InternalKnowledgeRuntime) ksession).getProcessRuntime().clearProcessInstances();
+                ((JPAWorkItemManager) ksession.getWorkItemManager()).clearWorkItems();
+            }
+
+        }
+
+        public void beforeCompletion() {
+
+        }
+
+    }
+
+    private void rollback() {
+        this.doRollback = true;
+    }
+}
\ No newline at end of file

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/TransactionManager.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/TransactionManager.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/TransactionManager.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,30 @@
+package org.drools.persistence;
+
+
+public interface TransactionManager {
+    /** Completion status in case of proper commit */
+    int STATUS_COMMITTED      = 0;
+
+    /** Completion status in case of proper rollback */
+    int STATUS_ROLLEDBACK     = 1;
+
+    /** Completion status in case of heuristic mixed completion or system errors */
+    int STATUS_UNKNOWN        = 2;
+
+    /** No existing transaction is associated with this threat */
+    int STATUS_NO_TRANSACTION = 3;
+
+    /** Transaction is Active */
+    int STATUS_ACTIVE         = 4;
+
+    int getStatus();
+
+    void begin();
+
+    void commit();
+
+    void rollback();
+
+    void registerTransactionSynchronization(TransactionSynchronization ts);
+
+}

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/TransactionSynchronization.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/TransactionSynchronization.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/TransactionSynchronization.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,8 @@
+package org.drools.persistence;
+
+public interface TransactionSynchronization {    
+    
+    void beforeCompletion();
+    
+    void afterCompletion(int status);
+}

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/TransactionSynchronizationRegistryHelper.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/TransactionSynchronizationRegistryHelper.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/TransactionSynchronizationRegistryHelper.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,12 @@
+package org.drools.persistence;
+
+import javax.transaction.TransactionSynchronizationRegistry;
+
+import org.drools.persistence.jta.JtaTransactionSynchronizationAdapter;
+
+public class TransactionSynchronizationRegistryHelper {
+    public static void registerTransactionSynchronization(final Object tsro, final TransactionSynchronization ts) {
+        TransactionSynchronizationRegistry tsr = ( TransactionSynchronizationRegistry ) tsro;
+        tsr.registerInterposedSynchronization( new JtaTransactionSynchronizationAdapter( ts ) );
+    }
+}

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/TransactionablePersistentContext.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/TransactionablePersistentContext.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/TransactionablePersistentContext.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,10 @@
+package org.drools.persistence;
+
+public interface TransactionablePersistentContext {
+
+    boolean isOpen();
+
+    void joinTransaction();
+
+    void close();
+}

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/info/SessionInfo.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/info/SessionInfo.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/info/SessionInfo.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,88 @@
+package org.drools.persistence.info;
+
+import java.util.Date;
+
+import javax.persistence.Column;
+import javax.persistence.Entity;
+import javax.persistence.GeneratedValue;
+import javax.persistence.GenerationType;
+import javax.persistence.Id;
+import javax.persistence.Lob;
+import javax.persistence.PrePersist;
+import javax.persistence.PreUpdate;
+import javax.persistence.Transient;
+import javax.persistence.Version;
+
+import org.drools.persistence.SessionMarshallingHelper;
+
+ at Entity
+public class SessionInfo {
+    private @Id
+    @GeneratedValue(strategy = GenerationType.AUTO)
+    Integer                        id;
+
+    @Version
+    @Column(name = "OPTLOCK")     
+    private int                version;
+
+    private Date               startDate;
+    private Date               lastModificationDate;    
+    
+    @Lob
+    private byte[]             rulesByteArray;
+
+    @Transient
+    SessionMarshallingHelper helper;
+    
+    public SessionInfo() {
+        this.startDate = new Date();
+    }
+
+    public Integer getId() {
+        return this.id;
+    }
+    
+    public int getVersion() {
+        return this.version;
+    }
+
+    public void setJPASessionMashallingHelper(SessionMarshallingHelper helper) {
+        this.helper = helper;
+    }
+
+    public SessionMarshallingHelper getJPASessionMashallingHelper() {
+        return helper;
+    }
+    
+    public void setData( byte[] data) {
+        this.rulesByteArray = data;
+    }
+    
+    public byte[] getData() {
+        return this.rulesByteArray;
+    }
+    
+    public Date getStartDate() {
+        return this.startDate;
+    }
+
+    public Date getLastModificationDate() {
+        return this.lastModificationDate;
+    }
+
+    public void setLastModificationDate(Date date) {
+        this.lastModificationDate = date;
+    }
+    
+
+    @PrePersist 
+    @PreUpdate 
+    public void update() {
+        this.rulesByteArray  = this.helper.getSnapshot();
+    }
+
+    public void setId(Integer ksessionId) {
+        this.id = ksessionId;
+    }
+
+}

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/info/WorkItemInfo.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/info/WorkItemInfo.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/info/WorkItemInfo.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,130 @@
+package org.drools.persistence.info;
+
+import java.io.ByteArrayInputStream;
+import java.io.ByteArrayOutputStream;
+import java.io.IOException;
+import java.util.Date;
+
+import javax.persistence.Column;
+import javax.persistence.Entity;
+import javax.persistence.GeneratedValue;
+import javax.persistence.GenerationType;
+import javax.persistence.Id;
+import javax.persistence.Lob;
+import javax.persistence.PreUpdate;
+import javax.persistence.Transient;
+import javax.persistence.Version;
+
+import org.drools.marshalling.impl.InputMarshaller;
+import org.drools.marshalling.impl.MarshallerReaderContext;
+import org.drools.marshalling.impl.MarshallerWriteContext;
+import org.drools.marshalling.impl.OutputMarshaller;
+import org.drools.process.instance.WorkItem;
+import org.drools.runtime.Environment;
+
+ at Entity
+public class WorkItemInfo  {
+
+    @Id
+    @GeneratedValue(strategy = GenerationType.AUTO)
+    private Long   workItemId;
+
+    @Version
+    @Column(name = "OPTLOCK")
+    private int    version;
+
+    private String name;
+    private Date   creationDate;
+    private long   processInstanceId;
+    private long   state;
+    private @Lob
+    byte[]         workItemByteArray;
+    private @Transient
+    WorkItem       workItem;
+
+    private @Transient
+    Environment                               env;
+    
+    protected WorkItemInfo() {
+    }
+
+    public WorkItemInfo(WorkItem workItem, Environment env) {
+        this.workItem = workItem;
+        this.name = workItem.getName();
+        this.creationDate = new Date();
+        this.processInstanceId = workItem.getProcessInstanceId();
+        this.env = env;
+    }
+
+    public Long getId() {
+        return workItemId;
+    }
+    
+    public int getVersion() {
+        return this.version;
+    }    
+
+    public String getName() {
+        return name;
+    }
+
+    public Date getCreationDate() {
+        return creationDate;
+    }
+
+    public long getProcessInstanceId() {
+        return processInstanceId;
+    }
+
+    public long getState() {
+        return state;
+    }
+
+    public WorkItem getWorkItem(Environment env) {
+        this.env = env;
+        if ( workItem == null ) {
+            try {
+                ByteArrayInputStream bais = new ByteArrayInputStream( workItemByteArray );
+                MarshallerReaderContext context = new MarshallerReaderContext( bais,
+                                                                               null,
+                                                                               null,
+                                                                               null,
+                                                                               env);
+                workItem = InputMarshaller.readWorkItem( context );
+                context.close();
+            } catch ( IOException e ) {
+                e.printStackTrace();
+                throw new IllegalArgumentException( "IOException while loading process instance: " + e.getMessage() );
+            }
+        }
+        return workItem;
+    }
+
+     
+
+    @PreUpdate
+    public void update() {
+        this.state = workItem.getState();
+        ByteArrayOutputStream baos = new ByteArrayOutputStream();
+        try {
+            MarshallerWriteContext context = new MarshallerWriteContext( baos,
+                                                                         null,
+                                                                         null,
+                                                                         null,
+                                                                         null,
+                                                                         this.env);
+            
+            OutputMarshaller.writeWorkItem( context,
+                                                 workItem );
+
+            context.close();
+            this.workItemByteArray = baos.toByteArray();
+        } catch ( IOException e ) {
+            throw new IllegalArgumentException( "IOException while storing workItem " + workItem.getId() + ": " + e.getMessage() );
+        }
+    }
+    
+    public void setId(Long id){
+        this.workItemId = id;
+    }
+}

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jpa/JpaJDKTimerService.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jpa/JpaJDKTimerService.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jpa/JpaJDKTimerService.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,106 @@
+/**
+ * Copyright 2010 JBoss Inc
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.drools.persistence.jpa;
+
+import java.util.concurrent.Callable;
+import java.util.concurrent.ScheduledThreadPoolExecutor;
+
+import org.drools.command.CommandService;
+import org.drools.command.Context;
+import org.drools.command.impl.GenericCommand;
+import org.drools.time.Job;
+import org.drools.time.JobContext;
+import org.drools.time.Trigger;
+import org.drools.time.impl.JDKTimerService;
+
+/**
+ * A default Scheduler implementation that uses the
+ * JDK built-in ScheduledThreadPoolExecutor as the
+ * scheduler and the system clock as the clock.
+ * 
+ */
+public class JpaJDKTimerService extends JDKTimerService {
+    
+	private CommandService commandService;
+
+    public void setCommandService(CommandService commandService) {
+    	this.commandService = commandService;
+    }
+    
+    public JpaJDKTimerService() {
+        this(1);
+    }
+
+    public JpaJDKTimerService(int size) {
+        super(size);
+    }
+
+    protected Callable<Void> createCallableJob(Job job,
+									           JobContext ctx,
+									           Trigger trigger,
+									           JDKJobHandle handle,
+									           ScheduledThreadPoolExecutor scheduler) {
+    	return new JpaJDKCallableJob( job,
+                ctx,
+                trigger,
+                handle,
+                this.scheduler );
+    }
+
+	public class JpaJDKCallableJob extends JDKCallableJob {
+
+		public JpaJDKCallableJob(Job job,
+					             JobContext ctx,
+					             Trigger trigger,
+					             JDKJobHandle handle,
+					             ScheduledThreadPoolExecutor scheduler) {
+			super(job, ctx, trigger, handle, scheduler);
+		}
+
+        public Void call() throws Exception {
+        	JDKCallableJobCommand command = new JDKCallableJobCommand(this);
+        	commandService.execute(command);
+        	return null;
+        }
+        
+        private Void internalCall() throws Exception {
+        	return super.call();
+        }
+    }
+    
+    public static class JDKCallableJobCommand implements GenericCommand<Void> {
+
+		private static final long serialVersionUID = 4L;
+		
+		private JpaJDKCallableJob job;
+    	
+    	public JDKCallableJobCommand(JpaJDKCallableJob job) {
+    		this.job = job;
+    	}
+    	
+    	public Void execute(Context context) {
+    		try {
+    			return job.internalCall();
+    		} catch (Exception e) {
+    			e.printStackTrace();
+    		}
+    		return null;
+    	}
+    	
+    }
+
+}

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jpa/JpaPersistenceContext.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jpa/JpaPersistenceContext.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jpa/JpaPersistenceContext.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,55 @@
+package org.drools.persistence.jpa;
+
+import javax.persistence.EntityManager;
+
+import org.drools.persistence.PersistenceContext;
+import org.drools.persistence.info.SessionInfo;
+import org.drools.persistence.info.WorkItemInfo;
+
+public class JpaPersistenceContext implements PersistenceContext {
+    private EntityManager em;
+    
+    public JpaPersistenceContext(EntityManager em) {
+        this.em = em;
+    }
+
+    public void persist(SessionInfo entity) {
+        this.em.persist( entity );
+    }
+
+    public SessionInfo findSessionInfo(Integer id) {
+        return this.em.find( SessionInfo.class, id );
+    }
+
+    public boolean isOpen() {
+        return this.em.isOpen();
+    }
+
+    public void joinTransaction() {
+        this.em.joinTransaction();
+    }
+
+    public void close() {
+        this.em.close();
+    }
+
+    public void persist(WorkItemInfo workItemInfo) {
+        em.persist( workItemInfo );
+    }
+
+    public WorkItemInfo findWorkItemInfo(Long id) {
+        return em.find( WorkItemInfo.class, id );
+    }
+
+    public void remove(WorkItemInfo workItemInfo) {
+        em.remove( workItemInfo );
+    }
+
+    public WorkItemInfo merge(WorkItemInfo workItemInfo) {
+        return em.merge( workItemInfo );
+    }
+    
+    protected EntityManager getEntityManager() {
+        return this.em;
+    }
+}

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jpa/JpaPersistenceContextManager.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jpa/JpaPersistenceContextManager.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jpa/JpaPersistenceContextManager.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,97 @@
+package org.drools.persistence.jpa;
+
+import javax.persistence.EntityManager;
+import javax.persistence.EntityManagerFactory;
+
+import org.drools.persistence.PersistenceContext;
+import org.drools.persistence.PersistenceContextManager;
+import org.drools.runtime.Environment;
+import org.drools.runtime.EnvironmentName;
+
+public class JpaPersistenceContextManager
+    implements
+    PersistenceContextManager {
+    Environment                  env;
+
+    private EntityManagerFactory emf;
+
+    private EntityManager        appScopedEntityManager;
+    protected EntityManager        cmdScopedEntityManager;
+
+    private boolean              internalAppScopedEntityManager;
+    private boolean              internalCmdScopedEntityManager;
+
+    public JpaPersistenceContextManager(Environment env) {
+        this.env = env;
+        this.emf = ( EntityManagerFactory ) env.get( EnvironmentName.ENTITY_MANAGER_FACTORY );
+    }    
+    
+    public PersistenceContext getApplicationScopedPersistenceContext() {
+        if ( this.appScopedEntityManager == null ) {
+            // Use the App scoped EntityManager if the user has provided it, and it is open.
+            this.appScopedEntityManager = (EntityManager) this.env.get( EnvironmentName.APP_SCOPED_ENTITY_MANAGER );
+            if ( this.appScopedEntityManager != null && !this.appScopedEntityManager.isOpen() ) {
+                throw new RuntimeException("Provided APP_SCOPED_ENTITY_MANAGER is not open");
+            }
+            
+            if ( this.appScopedEntityManager == null ) {
+                internalAppScopedEntityManager = true;
+                this.appScopedEntityManager = this.emf.createEntityManager();
+
+                this.env.set( EnvironmentName.APP_SCOPED_ENTITY_MANAGER,
+                              this.appScopedEntityManager );
+            } else {
+                internalAppScopedEntityManager = false;
+            }            
+        }
+        return new JpaPersistenceContext( appScopedEntityManager );
+    }
+
+    public PersistenceContext getCommandScopedPersistenceContext() {
+        return new JpaPersistenceContext( this.cmdScopedEntityManager );
+    }    
+
+    public void beginCommandScopedEntityManager() {
+        EntityManager cmdScopedEntityManager = (EntityManager) env.get( EnvironmentName.CMD_SCOPED_ENTITY_MANAGER );
+        if ( cmdScopedEntityManager == null || 
+           ( this.cmdScopedEntityManager != null && !this.cmdScopedEntityManager.isOpen() )) {
+            internalCmdScopedEntityManager = true;
+            this.cmdScopedEntityManager = this.emf.createEntityManager(); // no need to call joinTransaction as it will do so if one already exists
+            this.env.set( EnvironmentName.CMD_SCOPED_ENTITY_MANAGER,
+                          this.cmdScopedEntityManager );
+            cmdScopedEntityManager = this.cmdScopedEntityManager;
+        } else {
+            internalCmdScopedEntityManager = false;
+        }
+        cmdScopedEntityManager.joinTransaction();
+        appScopedEntityManager.joinTransaction();
+    }
+
+    public void endCommandScopedEntityManager() {
+        if ( this.internalCmdScopedEntityManager ) {
+            this.env.set( EnvironmentName.CMD_SCOPED_ENTITY_MANAGER, 
+                          null );
+        }
+    }
+
+    public void dispose() {
+        if ( this.internalAppScopedEntityManager ) {
+            if (  this.appScopedEntityManager != null && this.appScopedEntityManager.isOpen() ) {
+                this.appScopedEntityManager.close();
+            }
+            this.internalAppScopedEntityManager = false;
+            this.env.set( EnvironmentName.APP_SCOPED_ENTITY_MANAGER, null );
+            this.appScopedEntityManager = null;
+        }
+        
+        if ( this.internalCmdScopedEntityManager ) {
+            if (  this.cmdScopedEntityManager != null && this.cmdScopedEntityManager.isOpen() ) {
+                this.cmdScopedEntityManager.close();
+            }
+            this.internalCmdScopedEntityManager = false;
+            this.env.set( EnvironmentName.CMD_SCOPED_ENTITY_MANAGER, null );            
+            this.cmdScopedEntityManager = null;
+        }
+    }
+
+}

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jpa/KnowledgeStoreServiceImpl.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jpa/KnowledgeStoreServiceImpl.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jpa/KnowledgeStoreServiceImpl.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,192 @@
+package org.drools.persistence.jpa;
+
+import java.lang.reflect.Constructor;
+import java.lang.reflect.InvocationTargetException;
+import java.util.Properties;
+
+import org.drools.KnowledgeBase;
+import org.drools.SessionConfiguration;
+import org.drools.command.CommandService;
+import org.drools.command.impl.CommandBasedStatefulKnowledgeSession;
+import org.drools.persistence.SingleSessionCommandService;
+import org.drools.persistence.jpa.KnowledgeStoreService;
+import org.drools.persistence.jpa.processinstance.JPAWorkItemManagerFactory;
+import org.drools.process.instance.WorkItemManagerFactory;
+import org.drools.runtime.CommandExecutor;
+import org.drools.runtime.Environment;
+import org.drools.runtime.KnowledgeSessionConfiguration;
+import org.drools.runtime.StatefulKnowledgeSession;
+import org.drools.time.TimerService;
+
+public class KnowledgeStoreServiceImpl
+    implements
+    KnowledgeStoreService {
+
+    private Class< ? extends CommandExecutor>               commandServiceClass;
+    private Class< ? extends WorkItemManagerFactory>        workItemManagerFactoryClass;
+    private Class< ? extends TimerService>                  timerServiceClass;
+
+    private Properties                                      configProps = new Properties();
+
+    public KnowledgeStoreServiceImpl() {
+        setDefaultImplementations();
+    }
+
+    protected void setDefaultImplementations() {
+        setCommandServiceClass( SingleSessionCommandService.class );
+        setProcessInstanceManagerFactoryClass( "org.jbpm.persistence.processinstance.JPAProcessInstanceManagerFactory" );
+        setWorkItemManagerFactoryClass( JPAWorkItemManagerFactory.class );
+        setProcessSignalManagerFactoryClass( "org.jbpm.persistence.processinstance.JPASignalManagerFactory" );
+        setTimerServiceClass( JpaJDKTimerService.class );
+    }
+
+    public StatefulKnowledgeSession newStatefulKnowledgeSession(KnowledgeBase kbase,
+                                                                KnowledgeSessionConfiguration configuration,
+                                                                Environment environment) {
+        if ( configuration == null ) {
+            configuration = new SessionConfiguration();
+        }
+
+        if ( environment == null ) {
+            throw new IllegalArgumentException( "Environment cannot be null" );
+        }
+
+        return new CommandBasedStatefulKnowledgeSession( (CommandService) buildCommanService( kbase,
+                                                                             mergeConfig( configuration ),
+                                                                             environment ) );
+    }
+
+    public StatefulKnowledgeSession loadStatefulKnowledgeSession(int id,
+                                                                 KnowledgeBase kbase,
+                                                                 KnowledgeSessionConfiguration configuration,
+                                                                 Environment environment) {
+        if ( configuration == null ) {
+            configuration = new SessionConfiguration();
+        }
+
+        if ( environment == null ) {
+            throw new IllegalArgumentException( "Environment cannot be null" );
+        }
+
+        return new CommandBasedStatefulKnowledgeSession( (CommandService) buildCommanService( id,
+                                                                                              kbase,
+                                                                                              mergeConfig( configuration ),
+                                                                                              environment ) );
+    }
+
+    private CommandExecutor buildCommanService(Integer sessionId,
+                                              KnowledgeBase kbase,
+                                              KnowledgeSessionConfiguration conf,
+                                              Environment env) {
+
+        try {
+            Class< ? extends CommandExecutor> serviceClass = getCommandServiceClass();
+            Constructor< ? extends CommandExecutor> constructor = serviceClass.getConstructor( Integer.class,
+                                                                                              KnowledgeBase.class,
+                                                                                              KnowledgeSessionConfiguration.class,
+                                                                                              Environment.class );
+            return constructor.newInstance( sessionId,
+                                            kbase,
+                                            conf,
+                                            env );
+        } catch ( SecurityException e ) {
+            throw new IllegalStateException( e );
+        } catch ( NoSuchMethodException e ) {
+            throw new IllegalStateException( e );
+        } catch ( IllegalArgumentException e ) {
+            throw new IllegalStateException( e );
+        } catch ( InstantiationException e ) {
+            throw new IllegalStateException( e );
+        } catch ( IllegalAccessException e ) {
+            throw new IllegalStateException( e );
+        } catch ( InvocationTargetException e ) {
+            throw new IllegalStateException( e );
+        }
+    }
+
+    private CommandExecutor buildCommanService(KnowledgeBase kbase,
+                                              KnowledgeSessionConfiguration conf,
+                                              Environment env) {
+
+        Class< ? extends CommandExecutor> serviceClass = getCommandServiceClass();
+        try {
+            Constructor< ? extends CommandExecutor> constructor = serviceClass.getConstructor( KnowledgeBase.class,
+                                                                                              KnowledgeSessionConfiguration.class,
+                                                                                              Environment.class );
+            return constructor.newInstance( kbase,
+                                            conf,
+                                            env );
+        } catch ( SecurityException e ) {
+            throw new IllegalStateException( e );
+        } catch ( NoSuchMethodException e ) {
+            throw new IllegalStateException( e );
+        } catch ( IllegalArgumentException e ) {
+            throw new IllegalStateException( e );
+        } catch ( InstantiationException e ) {
+            throw new IllegalStateException( e );
+        } catch ( IllegalAccessException e ) {
+            throw new IllegalStateException( e );
+        } catch ( InvocationTargetException e ) {
+            throw new IllegalStateException( e );
+        }
+    }
+
+    private KnowledgeSessionConfiguration mergeConfig(KnowledgeSessionConfiguration configuration) {
+        ((SessionConfiguration) configuration).addProperties( configProps );
+        return configuration;
+    }
+
+    public long getStatefulKnowledgeSessionId(StatefulKnowledgeSession ksession) {
+        if ( ksession instanceof CommandBasedStatefulKnowledgeSession ) {
+            SingleSessionCommandService commandService = (SingleSessionCommandService) ((CommandBasedStatefulKnowledgeSession) ksession).getCommandService();
+            return commandService.getSessionId();
+        }
+        throw new IllegalArgumentException( "StatefulKnowledgeSession must be an a CommandBasedStatefulKnowledgeSession" );
+    }
+
+    public void setCommandServiceClass(Class< ? extends CommandExecutor> commandServiceClass) {
+        if ( commandServiceClass != null ) {
+            this.commandServiceClass = commandServiceClass;
+            configProps.put( "drools.commandService",
+                             commandServiceClass.getName() );
+        }
+    }
+
+    public Class< ? extends CommandExecutor> getCommandServiceClass() {
+        return commandServiceClass;
+    }
+
+    public void setTimerServiceClass(Class< ? extends TimerService> timerServiceClass) {
+        if ( timerServiceClass != null ) {
+            this.timerServiceClass = timerServiceClass;
+            configProps.put( "drools.timerService",
+            		         timerServiceClass.getName() );
+        }
+    }
+
+    public Class< ? extends TimerService> getTimerServiceClass() {
+        return timerServiceClass;
+    }
+
+    public void setProcessInstanceManagerFactoryClass(String processInstanceManagerFactoryClass) {
+        configProps.put( "drools.processInstanceManagerFactory",
+                         processInstanceManagerFactoryClass );
+    }
+
+    public void setWorkItemManagerFactoryClass(Class< ? extends WorkItemManagerFactory> workItemManagerFactoryClass) {
+        if ( workItemManagerFactoryClass != null ) {
+            this.workItemManagerFactoryClass = workItemManagerFactoryClass;
+            configProps.put( "drools.workItemManagerFactory",
+                             workItemManagerFactoryClass.getName() );
+        }
+    }
+
+    public Class< ? extends WorkItemManagerFactory> getWorkItemManagerFactoryClass() {
+        return workItemManagerFactoryClass;
+    }
+
+    public void setProcessSignalManagerFactoryClass(String processSignalManagerFactoryClass) {
+        configProps.put( "drools.processSignalManagerFactory",
+                         processSignalManagerFactoryClass );
+    }
+}

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jpa/marshaller/JPAPlaceholderResolverStrategy.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jpa/marshaller/JPAPlaceholderResolverStrategy.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jpa/marshaller/JPAPlaceholderResolverStrategy.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,138 @@
+/*
+ * Copyright 2010 salaboy.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * under the License.
+ */
+package org.drools.persistence.jpa.marshaller;
+
+import java.io.IOException;
+import java.io.ObjectInputStream;
+import java.io.ObjectOutputStream;
+import java.io.Serializable;
+import java.lang.reflect.Field;
+import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.Method;
+import javax.persistence.EntityManager;
+import javax.persistence.EntityManagerFactory;
+import javax.persistence.Id;
+import org.drools.marshalling.ObjectMarshallingStrategy;
+import org.drools.runtime.Environment;
+import org.drools.runtime.EnvironmentName;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+/**
+ *
+ * @author salaboy
+ */
+public class JPAPlaceholderResolverStrategy implements ObjectMarshallingStrategy {
+    private static Logger log = LoggerFactory.getLogger(JPAPlaceholderResolverStrategy.class);
+    private Environment env;
+    
+    public JPAPlaceholderResolverStrategy(Environment env) {
+        this.env = env;
+    }
+    
+    public boolean accept(Object object) {
+        return isEntity(object);
+    }
+
+    public void write(ObjectOutputStream os, Object object) throws IOException {
+        
+        
+            os.writeUTF(object.getClass().getCanonicalName());
+            os.writeObject(getClassIdValue(object));
+       
+    }
+
+    public Object read(ObjectInputStream is) throws IOException, ClassNotFoundException {
+        String canonicalName = is.readUTF();
+        Object id = is.readObject();
+        EntityManagerFactory emf = (EntityManagerFactory) env.get(EnvironmentName.ENTITY_MANAGER_FACTORY);
+        EntityManager em = emf.createEntityManager();
+        return em.find(Class.forName(canonicalName), id);
+    }
+
+    public static Serializable getClassIdValue(Object o)  {
+        Class<? extends Object> varClass = o.getClass();
+        Serializable idValue = null;
+        try{
+            do {
+                Field[] fields = varClass.getDeclaredFields();
+                for (int i = 0; i < fields.length && idValue == null; i++) {
+                    Field field = fields[i];
+                    Id id = field.getAnnotation(Id.class);
+                    if (id != null) {
+                        try {
+                            idValue = callIdMethod(o, "get"
+                                    + Character.toUpperCase(field.getName().charAt(0))
+                                    + field.getName().substring(1));
+                        } catch (NoSuchMethodException e) {
+                            idValue = (Serializable) field.get(o);
+                        }
+                    }
+                }
+            } while ((varClass = varClass.getSuperclass()) != null && idValue == null);
+            if (idValue == null) {
+                varClass = o.getClass();
+                do {
+                    Method[] methods = varClass.getMethods();
+                    for (int i = 0; i < methods.length && idValue == null; i++) {
+                        Method method = methods[i];
+                        Id id = method.getAnnotation(Id.class);
+                        if (id != null) {
+                            idValue = (Serializable) method.invoke(o);
+                        }
+                    }
+                } while ((varClass = varClass.getSuperclass()) != null && idValue == null);
+            }
+        }
+        catch(Exception ex){
+            log.error(ex.getMessage());
+        }
+        return idValue;
+    }
+
+    private static Serializable callIdMethod(Object target, String methodName) throws IllegalArgumentException,
+            SecurityException, IllegalAccessException, InvocationTargetException, NoSuchMethodException {
+        return (Serializable) target.getClass().getMethod(methodName, (Class[]) null).invoke(target, new Object[]{});
+    }
+    
+    private static boolean isEntity(Object o){
+        Class<? extends Object> varClass = o.getClass();
+        do {
+                Field[] fields = varClass.getDeclaredFields();
+                for (int i = 0; i < fields.length; i++) {
+                    Field field = fields[i];
+                    Id id = field.getAnnotation(Id.class);
+                    if (id != null) {
+                       return true;
+                    }
+                }
+        } while ((varClass = varClass.getSuperclass()) != null);
+        varClass = o.getClass();
+        do {
+                    Method[] methods = varClass.getMethods();
+                    for (int i = 0; i < methods.length; i++) {
+                        Method method = methods[i];
+                        Id id = method.getAnnotation(Id.class);
+                        if (id != null) {
+                            return true;
+                        }
+                    }
+        } while ((varClass = varClass.getSuperclass()) != null );
+        
+        return false;
+    }
+}

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jpa/processinstance/JPAWorkItemManager.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jpa/processinstance/JPAWorkItemManager.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jpa/processinstance/JPAWorkItemManager.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,197 @@
+package org.drools.persistence.jpa.processinstance;
+
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.Map;
+import java.util.Set;
+
+import javax.persistence.EntityManager;
+
+import org.drools.WorkItemHandlerNotFoundException;
+import org.drools.common.InternalKnowledgeRuntime;
+import org.drools.persistence.PersistenceContext;
+import org.drools.persistence.PersistenceContextManager;
+import org.drools.persistence.info.WorkItemInfo;
+import org.drools.process.instance.WorkItem;
+import org.drools.process.instance.WorkItemManager;
+import org.drools.process.instance.impl.WorkItemImpl;
+import org.drools.runtime.Environment;
+import org.drools.runtime.EnvironmentName;
+import org.drools.runtime.process.ProcessInstance;
+import org.drools.runtime.process.WorkItemHandler;
+
+public class JPAWorkItemManager implements WorkItemManager {
+
+    private InternalKnowledgeRuntime kruntime;
+	private Map<String, WorkItemHandler> workItemHandlers = new HashMap<String, WorkItemHandler>();
+    private transient Map<Long, WorkItemInfo> workItems;
+    
+    public JPAWorkItemManager(InternalKnowledgeRuntime kruntime) {
+    	this.kruntime = kruntime;
+    }
+    
+	public void internalExecuteWorkItem(WorkItem workItem) {
+        Environment env = this.kruntime.getEnvironment();
+//        EntityManager em = (EntityManager) env.get(EnvironmentName.CMD_SCOPED_ENTITY_MANAGER);
+	    
+        WorkItemInfo workItemInfo = new WorkItemInfo(workItem, env);
+//        em.persist(workItemInfo);
+        
+        PersistenceContext context = ((PersistenceContextManager) env.get( EnvironmentName.PERSISTENCE_CONTEXT_MANAGER )).getCommandScopedPersistenceContext();
+        context.persist( workItemInfo );
+
+        ((WorkItemImpl) workItem).setId(workItemInfo.getId());
+        workItemInfo.update();
+        
+		if (this.workItems == null) {
+        	this.workItems = new HashMap<Long, WorkItemInfo>();
+        }
+		workItems.put(workItem.getId(), workItemInfo);
+        
+        WorkItemHandler handler = (WorkItemHandler) this.workItemHandlers.get(workItem.getName());
+	    if (handler != null) {
+	        handler.executeWorkItem(workItem, this);
+	    } else {
+	        throwWorkItemNotFoundException( workItem );
+	    }
+	}
+
+    private void throwWorkItemNotFoundException(WorkItem workItem) {
+        throw new WorkItemHandlerNotFoundException( "Could not find work item handler for " + workItem.getName(),
+                                                    workItem.getName() );
+	}
+
+	public void internalAbortWorkItem(long id) {
+        Environment env = this.kruntime.getEnvironment();
+        //EntityManager em = (EntityManager) env.get(EnvironmentName.CMD_SCOPED_ENTITY_MANAGER);
+        PersistenceContext context = ((PersistenceContextManager) env.get( EnvironmentName.PERSISTENCE_CONTEXT_MANAGER )).getCommandScopedPersistenceContext();
+
+        
+        WorkItemInfo workItemInfo = context.findWorkItemInfo( id );
+        // work item may have been aborted
+        if (workItemInfo != null) {
+            WorkItemImpl workItem = (WorkItemImpl) workItemInfo.getWorkItem(env);
+            WorkItemHandler handler = (WorkItemHandler) this.workItemHandlers.get(workItem.getName());
+            if (handler != null) {
+                handler.abortWorkItem(workItem, this);
+            } else {
+                if ( workItems != null ) {
+                    workItems.remove( id );
+                    throwWorkItemNotFoundException( workItem );
+                }
+            }
+            if (workItems != null) {
+            	workItems.remove(id);
+            }
+            context.remove(workItemInfo);
+        }
+	}
+
+	public void internalAddWorkItem(WorkItem workItem) {
+	}
+
+    public void completeWorkItem(long id, Map<String, Object> results) {
+        Environment env = this.kruntime.getEnvironment();
+//        EntityManager em = (EntityManager) env.get(EnvironmentName.CMD_SCOPED_ENTITY_MANAGER);
+        PersistenceContext context = ((PersistenceContextManager) env.get( EnvironmentName.PERSISTENCE_CONTEXT_MANAGER )).getCommandScopedPersistenceContext();
+
+        
+        WorkItemInfo workItemInfo = null;
+        if (this.workItems != null) {
+	    	workItemInfo = this.workItems.get(id);
+	    	if (workItemInfo != null) {
+	    		workItemInfo = context.merge(workItemInfo);
+	    	}
+    	}
+        
+        if (workItemInfo == null) {
+        	workItemInfo = context.findWorkItemInfo( id );
+        }
+        
+    	// work item may have been aborted
+        if (workItemInfo != null) {
+            WorkItem workItem = (WorkItemImpl) workItemInfo.getWorkItem(env);
+            workItem.setResults(results);
+            ProcessInstance processInstance = kruntime.getProcessInstance(workItem.getProcessInstanceId());
+            workItem.setState(WorkItem.COMPLETED);
+            // process instance may have finished already
+            if (processInstance != null) {
+                processInstance.signalEvent("workItemCompleted", workItem);
+            }
+            context.remove(workItemInfo);
+            if (workItems != null) {
+            	this.workItems.remove(workItem.getId());
+            }
+    	}
+    }
+
+    public void abortWorkItem(long id) {
+        Environment env = this.kruntime.getEnvironment();
+//        EntityManager em = (EntityManager) env.get(EnvironmentName.CMD_SCOPED_ENTITY_MANAGER);
+        PersistenceContext context = ((PersistenceContextManager) env.get( EnvironmentName.PERSISTENCE_CONTEXT_MANAGER )).getCommandScopedPersistenceContext();
+
+        WorkItemInfo workItemInfo = null;
+        if (this.workItems != null) {
+	    	workItemInfo = this.workItems.get(id);
+	    	context.merge(workItemInfo);
+    	}
+        
+        if (workItemInfo == null) {
+        	workItemInfo = context.findWorkItemInfo( id );
+        }
+        
+    	// work item may have been aborted
+        if (workItemInfo != null) {
+            WorkItem workItem = (WorkItemImpl) workItemInfo.getWorkItem(env);
+            ProcessInstance processInstance = kruntime.getProcessInstance(workItem.getProcessInstanceId());
+            workItem.setState(WorkItem.ABORTED);
+            // process instance may have finished already
+            if (processInstance != null) {
+                processInstance.signalEvent("workItemAborted", workItem);
+            }
+            context.remove(workItemInfo);
+            if (workItems != null) {
+            	workItems.remove(workItem.getId());
+            }
+        }
+    }
+
+	public WorkItem getWorkItem(long id) {
+        Environment env = this.kruntime.getEnvironment();
+//        EntityManager em = (EntityManager) env.get(EnvironmentName.CMD_SCOPED_ENTITY_MANAGER);
+        PersistenceContext context = ((PersistenceContextManager) env.get( EnvironmentName.PERSISTENCE_CONTEXT_MANAGER )).getCommandScopedPersistenceContext();
+        
+        WorkItemInfo workItemInfo = null;
+        if (this.workItems != null) {
+	    	workItemInfo = this.workItems.get(id);
+    	}
+        
+        if (workItemInfo == null && context != null) {
+
+        	workItemInfo = context.findWorkItemInfo( id );
+        }
+
+        if (workItemInfo == null) {
+            return null;
+        }
+        return workItemInfo.getWorkItem(env);
+	}
+
+	public Set<WorkItem> getWorkItems() {
+		return new HashSet<WorkItem>();
+	}
+
+	public void registerWorkItemHandler(String workItemName, WorkItemHandler handler) {
+        this.workItemHandlers.put(workItemName, handler);
+	}
+
+    public void clearWorkItems() {
+    	if (workItems != null) {
+    		workItems.clear();
+    	}
+    }
+
+	public void clear() {
+		clearWorkItems();
+	}
+}

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jpa/processinstance/JPAWorkItemManagerFactory.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jpa/processinstance/JPAWorkItemManagerFactory.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jpa/processinstance/JPAWorkItemManagerFactory.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,13 @@
+package org.drools.persistence.jpa.processinstance;
+
+import org.drools.common.InternalKnowledgeRuntime;
+import org.drools.process.instance.WorkItemManager;
+import org.drools.process.instance.WorkItemManagerFactory;
+
+public class JPAWorkItemManagerFactory implements WorkItemManagerFactory {
+
+	public WorkItemManager createWorkItemManager(InternalKnowledgeRuntime kruntime) {
+		return new JPAWorkItemManager(kruntime);
+	}
+
+}

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jta/JtaTransactionManager.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jta/JtaTransactionManager.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jta/JtaTransactionManager.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,229 @@
+package org.drools.persistence.jta;
+
+import javax.naming.InitialContext;
+import javax.naming.NamingException;
+import javax.transaction.Status;
+import javax.transaction.SystemException;
+import javax.transaction.UserTransaction;
+
+import org.drools.persistence.TransactionManager;
+import org.drools.persistence.TransactionSynchronization;
+import org.drools.persistence.TransactionSynchronizationRegistryHelper;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+public class JtaTransactionManager
+    implements
+    TransactionManager {
+
+    Logger                               logger                                            = LoggerFactory.getLogger( getClass() );
+
+    public static final String           DEFAULT_USER_TRANSACTION_NAME                     = "java:comp/UserTransaction";
+
+    public static final String[]         FALLBACK_TRANSACTION_MANAGER_NAMES                = new String[]{"java:comp/TransactionManager", "java:appserver/TransactionManager", "java:pm/TransactionManager", "java:/TransactionManager"};
+
+    /**
+     * Standard Java EE 5 JNDI location for the JTA TransactionSynchronizationRegistry.
+     * Autodetected when available.
+     */
+    public static final String           DEFAULT_TRANSACTION_SYNCHRONIZATION_REGISTRY_NAME = "java:comp/TransactionSynchronizationRegistry";
+
+    private static final String          TRANSACTION_SYNCHRONIZATION_REGISTRY_CLASS_NAME   = "javax.transaction.TransactionSynchronizationRegistry";
+
+    private static Class< ? >            transactionSynchronizationRegistryClass;
+
+    static {
+        ClassLoader cl = JtaTransactionManager.class.getClassLoader();
+        try {
+            transactionSynchronizationRegistryClass = cl.loadClass( TRANSACTION_SYNCHRONIZATION_REGISTRY_CLASS_NAME );
+        } catch ( ClassNotFoundException e ) {
+            // JTA 1.1 API not available... simply proceed the JTA 1.0 way.
+        }
+    }
+
+    UserTransaction                      ut;
+    Object                               tsr;
+    javax.transaction.TransactionManager tm;
+    
+    private boolean localTransaction;
+
+    public JtaTransactionManager(Object ut,
+                                 Object tsr,
+                                 Object tm) {
+        if ( ut instanceof UserTransaction ) {
+            this.ut = ( UserTransaction ) ut;
+        } else {
+            this.ut = ( UserTransaction ) ( (ut != null) ? ut : findUserTransaction() );    
+        }
+        
+        if ( tm instanceof javax.transaction.TransactionManager ) {
+            this.tm = ( javax.transaction.TransactionManager ) tm;
+        } else {
+            this.tm = ( javax.transaction.TransactionManager ) ( (tm != null) ? tm : findTransactionManager( this.ut ) );
+        }
+        this.tsr = (tsr != null) ? tsr : findTransactionSynchronizationRegistry( this.ut,
+                                                                                 this.tm );
+    }
+
+    protected javax.transaction.TransactionManager findTransactionManager(UserTransaction ut) {
+        if ( ut instanceof TransactionManager ) {
+            logger.debug( "JTA UserTransaction object [{}] implements TransactionManager",
+                          ut );
+            return (javax.transaction.TransactionManager) ut;
+        }
+
+        InitialContext context = null;
+
+        try {
+            context = new InitialContext();
+        } catch ( NamingException ex ) {
+            logger.debug( "Could not initialise JNDI InitialContext",
+                          ex );
+            return null;
+        }
+
+        // Check fallback JNDI locations.
+        for ( String jndiName : FALLBACK_TRANSACTION_MANAGER_NAMES ) {
+            try {
+                javax.transaction.TransactionManager tm = (javax.transaction.TransactionManager) context.lookup( jndiName );
+                logger.debug( "JTA TransactionManager found at fallback JNDI location [{}]",
+                              jndiName );
+                return tm;
+            } catch ( NamingException ex ) {
+                logger.debug( "No JTA TransactionManager found at fallback JNDI location [{}]",
+                              jndiName,
+                              ex );
+            }
+        }
+
+        // OK, so no JTA TransactionManager is available...
+        return null;
+    }
+
+    protected UserTransaction findUserTransaction() {
+        try {
+            InitialContext context = new InitialContext();
+            return (UserTransaction) context.lookup( DEFAULT_USER_TRANSACTION_NAME );
+        } catch ( NamingException ex ) {
+            logger.debug( "No UserTransaction found at JNDI location [{}]",
+                          DEFAULT_USER_TRANSACTION_NAME,
+                          ex );
+            return null;
+        }
+    }
+
+    protected Object findTransactionSynchronizationRegistry(UserTransaction ut,
+                                                            javax.transaction.TransactionManager tm) {
+
+        if ( transactionSynchronizationRegistryClass == null ) {
+            // JTA 1.1 API not present - skip.
+            logger.debug( "JTA 1.1 [{}] API not available",
+                          TRANSACTION_SYNCHRONIZATION_REGISTRY_CLASS_NAME );
+            return null;
+        }
+
+        String jndiName = DEFAULT_TRANSACTION_SYNCHRONIZATION_REGISTRY_NAME;
+        try {
+            InitialContext context = new InitialContext();
+            context.lookup( jndiName );
+            logger.debug( "JTA TransactionSynchronizationRegistry found at default JNDI location [{}]",
+                          jndiName );
+            return tsr;
+        } catch ( NamingException ex ) {
+            logger.debug( "No JTA TransactionSynchronizationRegistry found at default JNDI location [{}]",
+                          jndiName,
+                          ex );
+        }
+        // Check whether the UserTransaction or TransactionManager implements it...
+        if ( transactionSynchronizationRegistryClass.isInstance( ut ) ) {
+            return ut;
+        }
+        if ( transactionSynchronizationRegistryClass.isInstance( tm ) ) {
+            return tm;
+        }
+        // OK, so no JTA 1.1 TransactionSynchronizationRegistry is available,
+        // despite the API being present...
+        return null;
+    }
+
+    public void begin() {
+        if ( getStatus() == TransactionManager.STATUS_NO_TRANSACTION ) {
+            this.localTransaction = true;
+            try {
+                this.ut.begin();
+            } catch ( Exception e ) {
+                logger.warn( "Unable to begin transaction", e);
+                throw new RuntimeException( "Unable to begin transaction",
+                                            e );
+            }
+        } else {
+            this.localTransaction = false;
+        }
+    }
+
+    public void commit() {
+        if ( this.localTransaction ) {
+            try {
+                this.ut.commit();
+            } catch ( Exception e ) {
+                logger.warn( "Unable to commit transaction", e);
+                throw new RuntimeException( "Unable to commit transaction",
+                                            e );
+            }
+        } else {
+            localTransaction = false;   
+        }
+    }
+    
+    public void rollback() {
+        localTransaction = false;
+        try {
+            this.ut.rollback();
+        } catch ( Exception e ) {
+            logger.warn( "Unable to rollback transaction", e);
+            throw new RuntimeException( "Unable to rollback transaction",
+                                        e );
+        }
+    }    
+
+    public int getStatus() {
+        int s;
+        try {
+            s = this.ut.getStatus();
+        } catch ( SystemException e ) {
+            throw new RuntimeException( "Unable to get status for transaction",
+                                        e );
+        }
+
+        switch ( s ) {
+            case Status.STATUS_COMMITTED :
+                return TransactionManager.STATUS_COMMITTED;
+            case Status.STATUS_ROLLEDBACK :
+                return TransactionManager.STATUS_ROLLEDBACK;
+            case Status.STATUS_NO_TRANSACTION :
+                return TransactionManager.STATUS_NO_TRANSACTION;
+            default :
+                return TransactionManager.STATUS_UNKNOWN;
+        }
+    }
+
+    public void registerTransactionSynchronization(final TransactionSynchronization ts) {
+        if ( this.tsr != null ) {
+            TransactionSynchronizationRegistryHelper.registerTransactionSynchronization( this.tsr,
+                                                                                         ts );
+        } else if ( this.tm != null ) {
+            try {
+                this.tm.getTransaction().registerSynchronization( new JtaTransactionSynchronizationAdapter( ts ) );
+            } catch ( Exception e ) {
+                // No JTA TransactionManager available - log a warning.
+                logger.warn( "Participating in existing JTA transaction, but no JTA TransactionManager or TransactionSychronizationRegistry available: ",
+                             e );
+
+            }
+        } else {
+            // No JTA TransactionManager available - log a warning.
+            logger.warn( "Participating in existing JTA transaction, but no JTA TransactionManager or TransactionSychronizationRegistry available: " );
+        }
+    }
+
+}

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jta/JtaTransactionSynchronizationAdapter.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jta/JtaTransactionSynchronizationAdapter.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/jta/JtaTransactionSynchronizationAdapter.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,41 @@
+package org.drools.persistence.jta;
+
+import javax.transaction.Status;
+import javax.transaction.Synchronization;
+
+import org.drools.persistence.TransactionManager;
+import org.drools.persistence.TransactionSynchronization;
+
+public class JtaTransactionSynchronizationAdapter
+    implements
+    Synchronization {
+    TransactionSynchronization ts;
+
+    public JtaTransactionSynchronizationAdapter(TransactionSynchronization ts) {
+        super();
+        this.ts = ts;
+    }
+
+    public void afterCompletion(int status) {
+        switch ( status ) {
+            case Status.STATUS_COMMITTED :
+                this.ts.afterCompletion( TransactionManager.STATUS_COMMITTED );
+                break;
+            case Status.STATUS_ROLLEDBACK :
+                this.ts.afterCompletion( TransactionManager.STATUS_ROLLEDBACK );
+                break;
+            case Status.STATUS_NO_TRANSACTION :
+                this.ts.afterCompletion(  TransactionManager.STATUS_NO_TRANSACTION );
+                break;
+            case Status.STATUS_ACTIVE :
+                this.afterCompletion( TransactionManager.STATUS_ACTIVE );
+                break;
+            default :
+                this.ts.afterCompletion( TransactionManager.STATUS_UNKNOWN );
+        }
+    }
+
+    public void beforeCompletion() {
+        this.ts.beforeCompletion();
+    }
+}

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/map/EnvironmentBuilder.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/map/EnvironmentBuilder.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/map/EnvironmentBuilder.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,12 @@
+package org.drools.persistence.map;
+
+import org.drools.persistence.PersistenceContextManager;
+import org.drools.persistence.TransactionManager;
+
+public interface EnvironmentBuilder {
+
+    PersistenceContextManager getPersistenceContextManager();
+
+    TransactionManager getTransactionManager();
+
+}
\ No newline at end of file

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/map/KnowledgeSessionStorage.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/map/KnowledgeSessionStorage.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/map/KnowledgeSessionStorage.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,22 @@
+package org.drools.persistence.map;
+
+import org.drools.persistence.info.SessionInfo;
+import org.drools.persistence.info.WorkItemInfo;
+
+public interface KnowledgeSessionStorage {
+
+    SessionInfo findSessionInfo(Integer sessionId);
+
+    void saveOrUpdate(SessionInfo storedObject);
+
+    void saveOrUpdate(WorkItemInfo workItemInfo);
+
+    Long getNextWorkItemId();
+
+    WorkItemInfo findWorkItemInfo(Long id);
+
+    void remove(WorkItemInfo workItemInfo);
+
+    Integer getNextStatefulKnowledgeSessionId();
+
+}

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/map/KnowledgeSessionStorageEnvironmentBuilder.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/map/KnowledgeSessionStorageEnvironmentBuilder.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/map/KnowledgeSessionStorageEnvironmentBuilder.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,29 @@
+package org.drools.persistence.map;
+
+import org.drools.persistence.PersistenceContextManager;
+import org.drools.persistence.TransactionManager;
+
+public class KnowledgeSessionStorageEnvironmentBuilder implements EnvironmentBuilder {
+
+    private MapBasedPersistenceContext persistenceContext;
+    private KnowledgeSessionStorage storage;
+
+    public KnowledgeSessionStorageEnvironmentBuilder(KnowledgeSessionStorage storage) {
+        this.storage = storage;
+        this.persistenceContext = new MapBasedPersistenceContext( storage );
+    }
+    
+    /* (non-Javadoc)
+     * @see org.drools.persistence.map.EnvironmentBuilder#getPersistenceContextManager()
+     */
+    public PersistenceContextManager getPersistenceContextManager(){
+        return new MapPersistenceContextManager( persistenceContext );
+    }
+    
+    /* (non-Javadoc)
+     * @see org.drools.persistence.map.EnvironmentBuilder#getTransactionManager()
+     */
+    public TransactionManager getTransactionManager(){
+        return new ManualTransactionManager( persistenceContext, storage );
+    }
+}

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/map/ManualTransactionManager.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/map/ManualTransactionManager.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/map/ManualTransactionManager.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,58 @@
+package org.drools.persistence.map;
+
+import org.drools.persistence.TransactionManager;
+import org.drools.persistence.TransactionSynchronization;
+import org.drools.persistence.info.SessionInfo;
+import org.drools.persistence.info.WorkItemInfo;
+
+public class ManualTransactionManager
+    implements
+    TransactionManager {
+    
+    private NonTransactionalPersistentSession session;
+    private KnowledgeSessionStorage storage;
+    private TransactionSynchronization transactionSynchronization;
+    
+    public ManualTransactionManager(NonTransactionalPersistentSession session,
+                                    KnowledgeSessionStorage storage) {
+        this.session = session;
+        this.storage = storage;
+    }
+    
+    public int getStatus() {
+        return 0;
+    }
+
+    public void begin() {
+    }
+
+    public void commit() {
+        try{
+            for(SessionInfo sessionInfo : session.getStoredKnowledgeSessions()){
+                sessionInfo.update();
+                storage.saveOrUpdate(sessionInfo);
+            }
+            
+            for(WorkItemInfo workItemInfo : session.getStoredWorkItems()){
+                workItemInfo.update();
+                storage.saveOrUpdate( workItemInfo );
+            }
+            try{
+                transactionSynchronization.afterCompletion(TransactionManager.STATUS_COMMITTED);
+            } catch (RuntimeException re){
+                //FIXME log error
+            }
+        } catch (RuntimeException re) {
+            transactionSynchronization.afterCompletion(TransactionManager.STATUS_ROLLEDBACK);
+        }
+        //we shouldn't clear session here b/c doing so we lose the track of this objects on successive
+        //interactions
+    }
+
+    public void rollback() {
+    }
+
+    public void registerTransactionSynchronization(TransactionSynchronization ts) {
+        this.transactionSynchronization = ts;
+    }
+}

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/map/MapBasedPersistenceContext.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/map/MapBasedPersistenceContext.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/map/MapBasedPersistenceContext.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,99 @@
+package org.drools.persistence.map;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import org.drools.persistence.PersistenceContext;
+import org.drools.persistence.info.SessionInfo;
+import org.drools.persistence.info.WorkItemInfo;
+
+public class MapBasedPersistenceContext
+    implements
+    PersistenceContext,
+    NonTransactionalPersistentSession {
+    
+    private Map<Integer, SessionInfo> ksessions;
+    private Map<Long, WorkItemInfo> workItems;
+    private boolean open;
+    private KnowledgeSessionStorage storage;
+    
+    public MapBasedPersistenceContext(KnowledgeSessionStorage storage) {
+        open = true;
+        this.storage = storage;
+        this.ksessions = new HashMap<Integer, SessionInfo>();
+        this.workItems = new HashMap<Long, WorkItemInfo>();
+    }
+    
+    public void persist(SessionInfo entity) {
+        if( entity.getId() == null ) {
+            entity.setId(storage.getNextStatefulKnowledgeSessionId());
+        }
+        ksessions.put( entity.getId(), entity );
+    }
+
+    public SessionInfo findSessionInfo(Integer sessionId) {
+        SessionInfo sessionInfo = ksessions.get( sessionId );
+        if(sessionInfo == null){
+            sessionInfo = storage.findSessionInfo( sessionId );
+            ksessions.put( sessionId, sessionInfo );
+        }
+        return sessionInfo;
+    }
+
+    public boolean isOpen() {
+        return open;
+    }
+
+    public void joinTransaction() {
+    }
+
+    public void close() {
+        open = false;
+        clear();
+    }
+
+    public void clear() {
+        clearAll();
+    }
+
+    private void clearAll() {
+        ksessions.clear();
+        workItems.clear();
+    }
+
+    public List<SessionInfo> getStoredKnowledgeSessions() {
+        return Collections.unmodifiableList( new ArrayList<SessionInfo>(ksessions.values()) );
+    }
+    
+    public void persist(WorkItemInfo workItemInfo) {
+        if( workItemInfo.getId() == null){
+            workItemInfo.setId( storage.getNextWorkItemId() );
+        }
+        workItems.put( workItemInfo.getId(), workItemInfo );
+    }
+
+    public List<WorkItemInfo> getStoredWorkItems() {
+        return Collections.unmodifiableList( new ArrayList<WorkItemInfo>(workItems.values()) );
+    }
+
+    public WorkItemInfo findWorkItemInfo(Long id) {
+        WorkItemInfo workItemInfo = workItems.get( id );
+        if(workItemInfo == null)
+            workItemInfo = storage.findWorkItemInfo( id );
+        return workItemInfo;
+    }
+
+    public void remove(WorkItemInfo workItemInfo) {
+        if( !(workItems.remove( workItemInfo.getId() ) == null) ){
+            storage.remove( workItemInfo );
+        }
+    }
+
+    public WorkItemInfo merge(WorkItemInfo workItemInfo) {
+        return workItemInfo;
+    }
+
+}

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/map/MapPersistenceContextManager.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/map/MapPersistenceContextManager.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/map/MapPersistenceContextManager.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,34 @@
+package org.drools.persistence.map;
+
+import org.drools.persistence.PersistenceContext;
+import org.drools.persistence.PersistenceContextManager;
+
+public class MapPersistenceContextManager
+    implements
+    PersistenceContextManager {
+
+    private PersistenceContext persistenceContext;
+    
+    public MapPersistenceContextManager(PersistenceContext persistenceContext) {
+        this.persistenceContext = persistenceContext;
+    }
+    
+    public PersistenceContext getApplicationScopedPersistenceContext() {
+        return persistenceContext;
+    }
+
+    public PersistenceContext getCommandScopedPersistenceContext() {
+        return persistenceContext;
+    }
+
+    public void beginCommandScopedEntityManager() {
+    }
+
+    public void endCommandScopedEntityManager() {
+    }
+
+    public void dispose() {
+        persistenceContext.close();
+    }
+
+}

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/map/NonTransactionalPersistentSession.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/map/NonTransactionalPersistentSession.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/map/NonTransactionalPersistentSession.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,15 @@
+package org.drools.persistence.map;
+
+import java.util.List;
+
+import org.drools.persistence.info.SessionInfo;
+import org.drools.persistence.info.WorkItemInfo;
+
+public interface NonTransactionalPersistentSession {
+
+    void clear();
+
+    List<SessionInfo> getStoredKnowledgeSessions();
+    
+    List<WorkItemInfo> getStoredWorkItems();
+}

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/osgi/Activator.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/osgi/Activator.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/main/java/org/drools/persistence/osgi/Activator.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,16 @@
+package org.drools.persistence.osgi;
+
+import org.osgi.framework.BundleActivator;
+import org.osgi.framework.BundleContext;
+
+public class Activator
+    implements
+    BundleActivator {
+
+    public void start(BundleContext bc) throws Exception {
+    }
+
+    public void stop(BundleContext bc) throws Exception {
+    }
+
+}

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/java/org/drools/persistence/map/impl/Buddy.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/java/org/drools/persistence/map/impl/Buddy.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/java/org/drools/persistence/map/impl/Buddy.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,43 @@
+package org.drools.persistence.map.impl;
+
+import java.io.Serializable;
+
+public class Buddy implements Serializable{
+
+    private String name;
+
+    public Buddy() {
+    }
+
+    public Buddy(String string) {
+        this.name = string;
+    }
+
+    public String getName() {
+        return name;
+    }
+
+    public void setName(String name) {
+        this.name = name;
+    }
+
+    @Override
+    public int hashCode() {
+        final int prime = 31;
+        int result = 1;
+        result = prime * result + ((name == null) ? 0 : name.hashCode());
+        return result;
+    }
+
+    @Override
+    public boolean equals(Object obj) {
+        if ( this == obj ) return true;
+        if ( obj == null ) return false;
+        if ( getClass() != obj.getClass() ) return false;
+        Buddy other = (Buddy) obj;
+        if ( name == null ) {
+            if ( other.name != null ) return false;
+        } else if ( !name.equals( other.name ) ) return false;
+        return true;
+    }
+}

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/java/org/drools/persistence/map/impl/JpaBasedPersistenceTest.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/java/org/drools/persistence/map/impl/JpaBasedPersistenceTest.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/java/org/drools/persistence/map/impl/JpaBasedPersistenceTest.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,79 @@
+package org.drools.persistence.map.impl;
+
+import javax.persistence.EntityManager;
+import javax.persistence.EntityManagerFactory;
+import javax.persistence.Persistence;
+
+import org.drools.KnowledgeBase;
+import org.drools.KnowledgeBaseFactory;
+import org.drools.base.MapGlobalResolver;
+import org.drools.persistence.jpa.JPAKnowledgeService;
+import org.drools.runtime.Environment;
+import org.drools.runtime.EnvironmentName;
+import org.drools.runtime.StatefulKnowledgeSession;
+import org.junit.After;
+import org.junit.AfterClass;
+import org.junit.Before;
+import org.junit.BeforeClass;
+
+import bitronix.tm.TransactionManagerServices;
+import bitronix.tm.resource.jdbc.PoolingDataSource;
+
+public class JpaBasedPersistenceTest extends MapPersistenceTest {
+
+    private  PoolingDataSource ds1;
+    private EntityManagerFactory emf;
+    
+    @Before
+    public void setUp() throws Exception {
+        ds1 = new PoolingDataSource();
+        ds1.setUniqueName( "jdbc/testDS1" );
+        ds1.setClassName( "org.h2.jdbcx.JdbcDataSource" );
+        ds1.setMaxPoolSize( 3 );
+        ds1.setAllowLocalTransactions( true );
+        ds1.getDriverProperties().put( "user",
+                                       "sa" );
+        ds1.getDriverProperties().put( "password",
+                                       "sasa" );
+        ds1.getDriverProperties().put( "URL",
+                                       "jdbc:h2:mem:mydb" );
+        ds1.init();
+        emf = Persistence.createEntityManagerFactory( "org.drools.persistence.jpa" );
+    }
+    
+    @After
+    public void tearDown() throws Exception {
+        emf.close();
+        ds1.close();
+    }
+    
+    @Override
+    protected StatefulKnowledgeSession createSession(KnowledgeBase kbase) {
+        return JPAKnowledgeService.newStatefulKnowledgeSession( kbase, null, createEnvironment() );
+    }
+
+    @Override
+    protected StatefulKnowledgeSession disposeAndReloadSession(StatefulKnowledgeSession ksession,
+                                                               KnowledgeBase kbase) {
+        int ksessionId = ksession.getId();
+        ksession.dispose();
+        return JPAKnowledgeService.loadStatefulKnowledgeSession( ksessionId, kbase, null, createEnvironment() );
+    }
+
+    @Override
+    protected long getSavedSessionsCount() {
+        System.out.println("quering");
+        return emf.createEntityManager().createQuery( "FROM SessionInfo" ).getResultList().size();
+    }
+
+    private Environment createEnvironment(){
+        Environment env = KnowledgeBaseFactory.newEnvironment();
+        env.set( EnvironmentName.ENTITY_MANAGER_FACTORY,
+                 emf );
+        env.set( EnvironmentName.TRANSACTION_MANAGER,
+                 TransactionManagerServices.getTransactionManager() );
+        env.set( EnvironmentName.GLOBALS, new MapGlobalResolver() );
+        
+        return env;
+    }
+}

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/java/org/drools/persistence/map/impl/MapBasedPersistenceTest.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/java/org/drools/persistence/map/impl/MapBasedPersistenceTest.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/java/org/drools/persistence/map/impl/MapBasedPersistenceTest.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,100 @@
+package org.drools.persistence.map.impl;
+
+import java.util.HashMap;
+import java.util.Map;
+
+import org.drools.KnowledgeBase;
+import org.drools.KnowledgeBaseFactory;
+import org.drools.persistence.info.SessionInfo;
+import org.drools.persistence.info.WorkItemInfo;
+import org.drools.persistence.jpa.JPAKnowledgeService;
+import org.drools.persistence.map.EnvironmentBuilder;
+import org.drools.persistence.map.KnowledgeSessionStorage;
+import org.drools.persistence.map.KnowledgeSessionStorageEnvironmentBuilder;
+import org.drools.runtime.Environment;
+import org.drools.runtime.EnvironmentName;
+import org.drools.runtime.StatefulKnowledgeSession;
+import org.junit.Before;
+
+public class MapBasedPersistenceTest extends MapPersistenceTest{
+    
+    private SimpleKnowledgeSessionStorage storage;
+    
+    @Before
+    public void createStorage(){
+        storage = new SimpleKnowledgeSessionStorage();
+    }
+    
+    @Override
+    protected StatefulKnowledgeSession createSession(KnowledgeBase kbase) {
+        
+        EnvironmentBuilder envBuilder = new KnowledgeSessionStorageEnvironmentBuilder( storage );
+        Environment env = KnowledgeBaseFactory.newEnvironment();
+        env.set( EnvironmentName.TRANSACTION_MANAGER,
+                 envBuilder.getTransactionManager() );
+        env.set( EnvironmentName.PERSISTENCE_CONTEXT_MANAGER,
+                 envBuilder.getPersistenceContextManager() );
+
+        return JPAKnowledgeService.newStatefulKnowledgeSession( kbase,
+                                                                null,
+                                                                env );
+    }
+    
+    @Override
+    protected StatefulKnowledgeSession disposeAndReloadSession(StatefulKnowledgeSession ksession,
+                                                             KnowledgeBase kbase) {
+        int sessionId = ksession.getId();
+        ksession.dispose();
+        EnvironmentBuilder envBuilder = new KnowledgeSessionStorageEnvironmentBuilder( storage );
+        Environment env = KnowledgeBaseFactory.newEnvironment();
+        env.set( EnvironmentName.TRANSACTION_MANAGER,
+                 envBuilder.getTransactionManager() );
+        env.set( EnvironmentName.PERSISTENCE_CONTEXT_MANAGER,
+                 envBuilder.getPersistenceContextManager() );
+        
+        return JPAKnowledgeService.loadStatefulKnowledgeSession( sessionId, kbase, null, env );
+    }
+    
+    @Override
+    protected long getSavedSessionsCount() {
+        return storage.ksessions.size();
+    }
+    
+    private static class SimpleKnowledgeSessionStorage
+        implements
+        KnowledgeSessionStorage {
+
+        public Map<Integer, SessionInfo>  ksessions = new HashMap<Integer, SessionInfo>();
+        public Map<Long, WorkItemInfo> workItems = new HashMap<Long, WorkItemInfo>();
+
+        public SessionInfo findSessionInfo(Integer id) {
+            return ksessions.get( id );
+        }
+
+        public void saveOrUpdate(SessionInfo storedObject) {
+            ksessions.put( storedObject.getId(),
+                           storedObject );
+        }
+
+        public void saveOrUpdate(WorkItemInfo workItemInfo) {
+            workItems.put( workItemInfo.getId(),
+                           workItemInfo );
+        }
+
+        public Long getNextWorkItemId() {
+            return new Long( workItems.size() + 1 );
+        }
+
+        public WorkItemInfo findWorkItemInfo(Long id) {
+            return workItems.get( id );
+        }
+
+        public void remove(WorkItemInfo workItemInfo) {
+            workItems.remove( workItemInfo.getId() );
+        }
+
+        public Integer getNextStatefulKnowledgeSessionId() {
+            return ksessions.size() + 1 ;
+        }
+    }
+}

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/java/org/drools/persistence/map/impl/MapPersistenceTest.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/java/org/drools/persistence/map/impl/MapPersistenceTest.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/java/org/drools/persistence/map/impl/MapPersistenceTest.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,126 @@
+package org.drools.persistence.map.impl;
+
+import org.drools.KnowledgeBase;
+import org.drools.KnowledgeBaseFactory;
+import org.drools.builder.KnowledgeBuilder;
+import org.drools.builder.KnowledgeBuilderError;
+import org.drools.builder.KnowledgeBuilderErrors;
+import org.drools.builder.KnowledgeBuilderFactory;
+import org.drools.builder.ResourceType;
+import org.drools.io.impl.ByteArrayResource;
+import org.drools.runtime.StatefulKnowledgeSession;
+import org.drools.runtime.rule.FactHandle;
+import org.junit.Assert;
+import org.junit.Test;
+
+public abstract class MapPersistenceTest {
+
+    @Test
+    public void createPersistentSession() {
+        KnowledgeBase kbase = KnowledgeBaseFactory.newKnowledgeBase();
+        
+        StatefulKnowledgeSession crmPersistentSession = createSession( kbase );
+        crmPersistentSession.fireAllRules();
+
+        crmPersistentSession = createSession( kbase );
+        Assert.assertNotNull( crmPersistentSession );
+    }
+
+
+    @Test
+    public void createPersistentSessionWithRules() {
+        KnowledgeBuilder kbuilder = KnowledgeBuilderFactory
+                .newKnowledgeBuilder();
+
+        String rule = "package org.drools.persistence.map.impl\n";
+        rule += "import org.drools.persistence.map.impl.Buddy;\n";
+        rule += "rule \"echo2\" \n";
+        rule += "dialect \"mvel\"\n";
+        rule += "when\n";
+        rule += "    $m : Buddy()\n";
+        rule += "then\n";
+        rule += "    System.out.println(\"buddy inserted\")";
+        rule += "end\n";
+        kbuilder.add( new ByteArrayResource( rule.getBytes() ),
+                      ResourceType.DRL );
+        KnowledgeBuilderErrors errors = kbuilder.getErrors();
+        if ( errors != null && errors.size() > 0 ) {
+            for ( KnowledgeBuilderError error : errors ) {
+                System.out.println( "Error: " + error.getMessage() );
+            }
+            Assert.fail( "KnowledgeBase did not build" );
+        }
+
+        KnowledgeBase kbase = KnowledgeBaseFactory.newKnowledgeBase();
+        kbase.addKnowledgePackages( kbuilder.getKnowledgePackages() );
+
+        StatefulKnowledgeSession ksession = createSession( kbase );
+
+        FactHandle buddyFactHandle = ksession.insert( new Buddy() );
+        ksession.fireAllRules();
+
+        Assert.assertEquals( 1,
+                             ksession.getObjects().size() );
+
+        ksession = disposeAndReloadSession( ksession,
+                                            kbase );
+
+        Assert.assertNotNull( ksession );
+
+        Assert.assertEquals( 1,
+                             ksession.getObjects().size() );
+
+        Assert.assertNull( "An object can't be retrieved with a FactHandle from a disposed session",
+                           ksession.getObject( buddyFactHandle ) );
+
+    }
+
+    @Test
+    public void dontCreateMoreSessionsThanNecessary() {
+        KnowledgeBase kbase = KnowledgeBaseFactory.newKnowledgeBase();
+
+        StatefulKnowledgeSession crmPersistentSession = createSession(kbase);
+
+        long ksessionId = crmPersistentSession.getId();
+        crmPersistentSession.fireAllRules();
+
+        crmPersistentSession = disposeAndReloadSession(crmPersistentSession, kbase);
+
+        Assert.assertEquals(ksessionId, crmPersistentSession.getId());
+
+        ksessionId = crmPersistentSession.getId();
+        crmPersistentSession.fireAllRules();
+
+        crmPersistentSession = disposeAndReloadSession(crmPersistentSession, kbase);
+
+        crmPersistentSession.fireAllRules();
+
+        Assert.assertEquals(1, getSavedSessionsCount());
+        crmPersistentSession.dispose();
+    }
+
+
+    @Test
+    public void insertObjectIntoKsessionAndRetrieve() {
+        KnowledgeBase kbase = KnowledgeBaseFactory.newKnowledgeBase();
+        
+        StatefulKnowledgeSession crmPersistentSession = createSession(kbase);
+        Buddy bestBuddy = new Buddy("john");
+        crmPersistentSession.insert(bestBuddy);
+
+        crmPersistentSession = disposeAndReloadSession(crmPersistentSession, kbase);
+        Object obtainedBuddy = crmPersistentSession
+                .getObjects().iterator().next();
+        Assert.assertNotSame( bestBuddy, obtainedBuddy );
+        Assert.assertEquals(bestBuddy, obtainedBuddy);
+
+        crmPersistentSession.dispose();
+    }
+
+    protected abstract StatefulKnowledgeSession createSession(KnowledgeBase kbase);
+    
+    protected abstract StatefulKnowledgeSession disposeAndReloadSession(StatefulKnowledgeSession crmPersistentSession,
+                                                                        KnowledgeBase kbase);
+
+    protected abstract long getSavedSessionsCount();
+}

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/java/org/drools/persistence/session/JpaPersistentStatefulSessionTest.java
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/java/org/drools/persistence/session/JpaPersistentStatefulSessionTest.java	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/java/org/drools/persistence/session/JpaPersistentStatefulSessionTest.java	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,757 @@
+package org.drools.persistence.session;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import javax.naming.InitialContext;
+import javax.persistence.EntityManagerFactory;
+import javax.persistence.Persistence;
+import javax.transaction.UserTransaction;
+
+import junit.framework.TestCase;
+
+import org.drools.KnowledgeBase;
+import org.drools.KnowledgeBaseFactory;
+import org.drools.base.MapGlobalResolver;
+import org.drools.builder.KnowledgeBuilder;
+import org.drools.builder.KnowledgeBuilderError;
+import org.drools.builder.KnowledgeBuilderFactory;
+import org.drools.builder.ResourceType;
+import org.drools.event.process.ProcessCompletedEvent;
+import org.drools.event.process.ProcessEvent;
+import org.drools.event.process.ProcessEventListener;
+import org.drools.event.process.ProcessNodeLeftEvent;
+import org.drools.event.process.ProcessNodeTriggeredEvent;
+import org.drools.event.process.ProcessStartedEvent;
+import org.drools.io.ResourceFactory;
+import org.drools.io.impl.ClassPathResource;
+import org.drools.persistence.jpa.JPAKnowledgeService;
+import org.drools.runtime.Environment;
+import org.drools.runtime.EnvironmentName;
+import org.drools.runtime.StatefulKnowledgeSession;
+import org.drools.runtime.process.ProcessInstance;
+import org.drools.runtime.process.WorkItem;
+
+import bitronix.tm.TransactionManagerServices;
+import bitronix.tm.resource.jdbc.PoolingDataSource;
+
+public class JpaPersistentStatefulSessionTest extends TestCase {
+
+    PoolingDataSource ds1;
+
+    @Override
+    protected void setUp() throws Exception {
+        ds1 = new PoolingDataSource();
+        ds1.setUniqueName( "jdbc/testDS1" );
+        ds1.setClassName( "org.h2.jdbcx.JdbcDataSource" );
+        ds1.setMaxPoolSize( 3 );
+        ds1.setAllowLocalTransactions( true );
+        ds1.getDriverProperties().put( "user",
+                                       "sa" );
+        ds1.getDriverProperties().put( "password",
+                                       "sasa" );
+        ds1.getDriverProperties().put( "URL",
+                                       "jdbc:h2:mem:mydb" );
+        ds1.init();
+
+    }
+
+    @Override
+    protected void tearDown() throws Exception {
+        ds1.close();
+    }
+
+    public void testLocalTransactionPerStatement() {
+        String str = "";
+        str += "package org.drools.test\n";
+        str += "global java.util.List list\n";
+        str += "rule rule1\n";
+        str += "when\n";
+        str += "  Integer(intValue > 0)\n";
+        str += "then\n";
+        str += "  list.add( 1 );\n";
+        str += "end\n";
+        str += "\n";
+
+        KnowledgeBuilder kbuilder = KnowledgeBuilderFactory.newKnowledgeBuilder();
+        kbuilder.add( ResourceFactory.newByteArrayResource( str.getBytes() ),
+                      ResourceType.DRL );
+        KnowledgeBase kbase = KnowledgeBaseFactory.newKnowledgeBase();
+
+        if ( kbuilder.hasErrors() ) {
+            fail( kbuilder.getErrors().toString() );
+        }
+
+        kbase.addKnowledgePackages( kbuilder.getKnowledgePackages() );
+
+        EntityManagerFactory emf = Persistence.createEntityManagerFactory( "org.drools.persistence.jpa" );
+        Environment env = KnowledgeBaseFactory.newEnvironment();
+        env.set( EnvironmentName.ENTITY_MANAGER_FACTORY,
+                 emf );
+        env.set( EnvironmentName.TRANSACTION_MANAGER,
+                 TransactionManagerServices.getTransactionManager() );
+        env.set( EnvironmentName.GLOBALS, new MapGlobalResolver() );
+
+        StatefulKnowledgeSession ksession = JPAKnowledgeService.newStatefulKnowledgeSession( kbase, null, env );
+        List<?> list = new ArrayList<Object>();
+
+        ksession.setGlobal( "list",
+                            list );
+
+        ksession.insert( 1 );
+        ksession.insert( 2 );
+        ksession.insert( 3 );
+
+        ksession.fireAllRules();
+
+        assertEquals( 3,
+                      list.size() );
+
+    }
+
+    public void testUserTransactions() throws Exception {
+        String str = "";
+        str += "package org.drools.test\n";
+        str += "global java.util.List list\n";
+        str += "rule rule1\n";
+        str += "when\n";
+        str += "  $i : Integer(intValue > 0)\n";
+        str += "then\n";
+        str += "  list.add( $i );\n";
+        str += "end\n";
+        str += "\n";
+
+        KnowledgeBuilder kbuilder = KnowledgeBuilderFactory.newKnowledgeBuilder();
+        kbuilder.add( ResourceFactory.newByteArrayResource( str.getBytes() ),
+                      ResourceType.DRL );
+        KnowledgeBase kbase = KnowledgeBaseFactory.newKnowledgeBase();
+
+        if ( kbuilder.hasErrors() ) {
+            fail( kbuilder.getErrors().toString() );
+        }
+
+        kbase.addKnowledgePackages( kbuilder.getKnowledgePackages() );
+
+        EntityManagerFactory emf = Persistence.createEntityManagerFactory( "org.drools.persistence.jpa" );
+        Environment env = KnowledgeBaseFactory.newEnvironment();
+        env.set( EnvironmentName.ENTITY_MANAGER_FACTORY,
+                 emf );
+        env.set( EnvironmentName.TRANSACTION_MANAGER,
+                 TransactionManagerServices.getTransactionManager() );
+        env.set( EnvironmentName.GLOBALS, new MapGlobalResolver() );
+
+        UserTransaction ut = (UserTransaction) new InitialContext().lookup( "java:comp/UserTransaction" );
+        ut.begin();
+        StatefulKnowledgeSession ksession = JPAKnowledgeService.newStatefulKnowledgeSession( kbase, null, env );
+        ut.commit();
+
+        //      EntityManager em = emf.createEntityManager();
+        //      SessionInfo sInfo = em.find( SessionInfo.class, 1 );
+        //      assertNotNull( sInfo );
+        //      //System.out.println( "session creation : " + sInfo.getVersion() );
+        //      em.close();
+
+        List<?> list = new ArrayList<Object>();
+
+        // insert and commit
+        ut = (UserTransaction) new InitialContext().lookup( "java:comp/UserTransaction" );
+        ut.begin();
+        ksession.setGlobal( "list",
+                            list );
+        ksession.insert( 1 );
+        ksession.insert( 2 );
+        ut.commit();
+//
+        // insert and rollback
+        ut = (UserTransaction) new InitialContext().lookup( "java:comp/UserTransaction" );
+        ut.begin();
+        ksession.insert( 3 );
+        ut.rollback();
+
+        // check we rolled back the state changes from the 3rd insert
+        ut = (UserTransaction) new InitialContext().lookup( "java:comp/UserTransaction" );
+        ut.begin();        
+        ksession.fireAllRules();
+        ut.commit();
+        assertEquals( 2,
+                      list.size() );
+
+//        // insert and commit
+        ut = (UserTransaction) new InitialContext().lookup( "java:comp/UserTransaction" );
+        ut.begin();
+        ksession.insert( 3 );
+        ksession.insert( 4 );
+        ut.commit();
+
+        // rollback again, this is testing that we can do consecutive rollbacks and commits without issue
+        ut = (UserTransaction) new InitialContext().lookup( "java:comp/UserTransaction" );
+        ut.begin();
+        ksession.insert( 5 );
+        ksession.insert( 6 );
+        ut.rollback();
+
+        ksession.fireAllRules();
+
+        assertEquals( 4,
+                      list.size() );
+        
+        // now load the ksession
+        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( ksession.getId(), kbase, null, env );
+        
+        ut = (UserTransaction) new InitialContext().lookup( "java:comp/UserTransaction" );
+        ut.begin();
+        ksession.insert( 7 );
+        ksession.insert( 8 );
+        ut.commit();
+
+        ksession.fireAllRules();
+
+        assertEquals( 6,
+                      list.size() );
+    }
+
+    public void test1() {
+        
+    }
+    
+//    public void testPersistenceWorkItems() {
+//        KnowledgeBuilder kbuilder = KnowledgeBuilderFactory.newKnowledgeBuilder();
+//        kbuilder.add( new ClassPathResource( "WorkItemsProcess.rf" ),
+//                      ResourceType.DRF );
+//        KnowledgeBase kbase = KnowledgeBaseFactory.newKnowledgeBase();
+//        kbase.addKnowledgePackages( kbuilder.getKnowledgePackages() );
+//
+//        EntityManagerFactory emf = Persistence.createEntityManagerFactory( "org.drools.persistence.jpa" );
+//        Environment env = KnowledgeBaseFactory.newEnvironment();
+//        env.set( EnvironmentName.ENTITY_MANAGER_FACTORY,
+//                 emf );
+//
+//        env.set( EnvironmentName.GLOBALS, new MapGlobalResolver() );
+//
+//        StatefulKnowledgeSession ksession = JPAKnowledgeService.newStatefulKnowledgeSession( kbase, null, env );
+//        int id = ksession.getId();
+//        
+//        ProcessInstance processInstance = ksession.startProcess( "org.drools.test.TestProcess" );
+//        ksession.insert( "TestString" );
+//        System.out.println( "Started process instance " + processInstance.getId() );
+//
+//        TestWorkItemHandler handler = TestWorkItemHandler.getInstance();
+//        WorkItem workItem = handler.getWorkItem();
+//        assertNotNull( workItem );
+//
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        processInstance = ksession.getProcessInstance( processInstance.getId() );
+//        assertNotNull( processInstance );
+//
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        ksession.getWorkItemManager().completeWorkItem( workItem.getId(),
+//                                                       null );
+//
+//        workItem = handler.getWorkItem();
+//        assertNotNull( workItem );
+//
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        processInstance = ksession.getProcessInstance( processInstance.getId() );
+//        assertNotNull( processInstance );
+//
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        ksession.getWorkItemManager().completeWorkItem( workItem.getId(),
+//                                                       null );
+//
+//        workItem = handler.getWorkItem();
+//        assertNotNull( workItem );
+//
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        processInstance = ksession.getProcessInstance( processInstance.getId() );
+//        assertNotNull( processInstance );
+//
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        ksession.getWorkItemManager().completeWorkItem( workItem.getId(),
+//                                                       null );
+//
+//        workItem = handler.getWorkItem();
+//        assertNull( workItem );
+//
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        processInstance = ksession.getProcessInstance( processInstance.getId() );
+//        assertEquals( 1,
+//                      ksession.getObjects().size() );
+//        for ( Object o : ksession.getObjects() ) {
+//            System.out.println( o );
+//        }
+//        assertNull( processInstance );
+//
+//    }
+//    
+//    public void testPersistenceWorkItems2() throws Exception {
+//        KnowledgeBuilder kbuilder = KnowledgeBuilderFactory.newKnowledgeBuilder();
+//        kbuilder.add( new ClassPathResource( "WorkItemsProcess.rf" ),
+//                      ResourceType.DRF );
+//        KnowledgeBase kbase = KnowledgeBaseFactory.newKnowledgeBase();
+//        kbase.addKnowledgePackages( kbuilder.getKnowledgePackages() );
+//
+//        EntityManagerFactory emf = Persistence.createEntityManagerFactory( "org.drools.persistence.jpa" );
+//        Environment env = KnowledgeBaseFactory.newEnvironment();
+//        env.set( EnvironmentName.ENTITY_MANAGER_FACTORY,
+//                 emf );
+//
+//        env.set( EnvironmentName.GLOBALS, new MapGlobalResolver() );
+//
+//        StatefulKnowledgeSession ksession = JPAKnowledgeService.newStatefulKnowledgeSession( kbase, null, env );
+//        int id = ksession.getId();
+//        
+//        UserTransaction ut = (UserTransaction) new InitialContext().lookup( "java:comp/UserTransaction" );
+//        ut.begin();
+//        
+//        ProcessInstance processInstance = ksession.startProcess( "org.drools.test.TestProcess" );
+//        ksession.insert( "TestString" );
+//        System.out.println( "Started process instance " + processInstance.getId() );
+//
+//        TestWorkItemHandler handler = TestWorkItemHandler.getInstance();
+//        WorkItem workItem = handler.getWorkItem();
+//        assertNotNull( workItem );
+//
+//        ksession.getWorkItemManager().completeWorkItem( workItem.getId(),
+//                                                       null );
+//        
+//        workItem = handler.getWorkItem();
+//        assertNotNull( workItem );
+//
+//        ut.commit();
+//
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        processInstance = ksession.getProcessInstance( processInstance.getId() );
+//        assertNotNull( processInstance );
+//
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        ksession.getWorkItemManager().completeWorkItem( workItem.getId(),
+//                                                       null );
+//
+//        workItem = handler.getWorkItem();
+//        assertNotNull( workItem );
+//
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        processInstance = ksession.getProcessInstance( processInstance.getId() );
+//        assertNotNull( processInstance );
+//
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        ksession.getWorkItemManager().completeWorkItem( workItem.getId(),
+//                                                       null );
+//
+//        workItem = handler.getWorkItem();
+//        assertNull( workItem );
+//
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        processInstance = ksession.getProcessInstance( processInstance.getId() );
+//        assertEquals( 1,
+//                      ksession.getObjects().size() );
+//        for ( Object o : ksession.getObjects() ) {
+//            System.out.println( o );
+//        }
+//        assertNull( processInstance );
+//
+//    }
+//    
+//    public void testPersistenceWorkItems3() {
+//        KnowledgeBuilder kbuilder = KnowledgeBuilderFactory.newKnowledgeBuilder();
+//        kbuilder.add( new ClassPathResource( "WorkItemsProcess.rf" ),
+//                      ResourceType.DRF );
+//        KnowledgeBase kbase = KnowledgeBaseFactory.newKnowledgeBase();
+//        kbase.addKnowledgePackages( kbuilder.getKnowledgePackages() );
+//
+//        EntityManagerFactory emf = Persistence.createEntityManagerFactory( "org.drools.persistence.jpa" );
+//        Environment env = KnowledgeBaseFactory.newEnvironment();
+//        env.set( EnvironmentName.ENTITY_MANAGER_FACTORY,
+//                 emf );
+//
+//        env.set( EnvironmentName.GLOBALS, new MapGlobalResolver() );
+//
+//        StatefulKnowledgeSession ksession = JPAKnowledgeService.newStatefulKnowledgeSession( kbase, null, env );
+//        ksession.getWorkItemManager().registerWorkItemHandler("MyWork", new SystemOutWorkItemHandler());
+//        ProcessInstance processInstance = ksession.startProcess( "org.drools.test.TestProcess" );
+//        ksession.insert( "TestString" );
+//        assertEquals(ProcessInstance.STATE_COMPLETED, processInstance.getState());
+//    }
+//    
+//    public void testPersistenceState() {
+//        KnowledgeBuilder kbuilder = KnowledgeBuilderFactory.newKnowledgeBuilder();
+//        kbuilder.add( new ClassPathResource( "StateProcess.rf" ),
+//                      ResourceType.DRF );
+//        KnowledgeBase kbase = KnowledgeBaseFactory.newKnowledgeBase();
+//        kbase.addKnowledgePackages( kbuilder.getKnowledgePackages() );
+//
+//        EntityManagerFactory emf = Persistence.createEntityManagerFactory( "org.drools.persistence.jpa" );
+//        Environment env = KnowledgeBaseFactory.newEnvironment();
+//        env.set( EnvironmentName.ENTITY_MANAGER_FACTORY, emf );
+//        env.set( EnvironmentName.TRANSACTION_MANAGER,
+//                 TransactionManagerServices.getTransactionManager() );        
+//        env.set( EnvironmentName.GLOBALS, new MapGlobalResolver() );
+//
+//        StatefulKnowledgeSession ksession = JPAKnowledgeService.newStatefulKnowledgeSession( kbase, null, env );
+//        int id = ksession.getId();
+//        
+//        ProcessInstance processInstance = ksession.startProcess( "org.drools.test.TestProcess" );
+//        System.out.println( "Started process instance " + processInstance.getId() );
+//
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        processInstance = ksession.getProcessInstance( processInstance.getId() );
+//        assertNotNull( processInstance );
+//
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        ksession.insert(new ArrayList<Object>());
+//
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        processInstance = ksession.getProcessInstance( processInstance.getId() );
+//        assertNull( processInstance );
+//    }
+//    
+//    public void testPersistenceRuleSet() {
+//        KnowledgeBuilder kbuilder = KnowledgeBuilderFactory.newKnowledgeBuilder();
+//        kbuilder.add( new ClassPathResource( "RuleSetProcess.rf" ),
+//                      ResourceType.DRF );
+//        kbuilder.add( new ClassPathResource( "RuleSetRules.drl" ),
+//                      ResourceType.DRL );
+//        KnowledgeBase kbase = KnowledgeBaseFactory.newKnowledgeBase();
+//        kbase.addKnowledgePackages( kbuilder.getKnowledgePackages() );
+//
+//        EntityManagerFactory emf = Persistence.createEntityManagerFactory( "org.drools.persistence.jpa" );
+//        Environment env = KnowledgeBaseFactory.newEnvironment();
+//        env.set( EnvironmentName.ENTITY_MANAGER_FACTORY, emf );
+//        env.set( EnvironmentName.TRANSACTION_MANAGER,
+//                 TransactionManagerServices.getTransactionManager() );        
+//        env.set( EnvironmentName.GLOBALS, new MapGlobalResolver() );
+//
+//        StatefulKnowledgeSession ksession = JPAKnowledgeService.newStatefulKnowledgeSession( kbase, null, env );
+//        int id = ksession.getId();
+//        
+//        ksession.insert(new ArrayList<Object>());
+//
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        ProcessInstance processInstance = ksession.startProcess( "org.drools.test.TestProcess" );
+//
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        processInstance = ksession.getProcessInstance( processInstance.getId() );
+//        assertNotNull( processInstance );
+//
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        ksession.fireAllRules();
+//        processInstance = ksession.getProcessInstance( processInstance.getId() );
+//        assertNull( processInstance );
+//    }
+//    
+//    public void testPersistenceEvents() {
+//        KnowledgeBuilder kbuilder = KnowledgeBuilderFactory.newKnowledgeBuilder();
+//        kbuilder.add( new ClassPathResource( "EventsProcess.rf" ),
+//                      ResourceType.DRF );
+//        KnowledgeBase kbase = KnowledgeBaseFactory.newKnowledgeBase();
+//        kbase.addKnowledgePackages( kbuilder.getKnowledgePackages() );
+//
+//        EntityManagerFactory emf = Persistence.createEntityManagerFactory( "org.drools.persistence.jpa" );
+//        Environment env = KnowledgeBaseFactory.newEnvironment();
+//        env.set( EnvironmentName.ENTITY_MANAGER_FACTORY,
+//                 emf );
+//
+//        env.set( EnvironmentName.GLOBALS, new MapGlobalResolver() );
+//
+//        StatefulKnowledgeSession ksession = JPAKnowledgeService.newStatefulKnowledgeSession( kbase, null, env );
+//        int id = ksession.getId();
+//        
+//        ProcessInstance processInstance = ksession.startProcess( "org.drools.test.TestProcess" );
+//        System.out.println( "Started process instance " + processInstance.getId() );
+//
+//        TestWorkItemHandler handler = TestWorkItemHandler.getInstance();
+//        WorkItem workItem = handler.getWorkItem();
+//        assertNotNull( workItem );
+//
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        processInstance = ksession.getProcessInstance( processInstance.getId() );
+//        assertNotNull( processInstance );
+//
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        ksession.getWorkItemManager().completeWorkItem( workItem.getId(), null );
+//        
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        processInstance = ksession.getProcessInstance( processInstance.getId() );
+//        assertNotNull( processInstance );
+//
+//        ksession.signalEvent("MyEvent1", null, processInstance.getId());
+//
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        processInstance = ksession.getProcessInstance( processInstance.getId() );
+//        assertNotNull( processInstance );
+//
+//        ksession.signalEvent("MyEvent2", null, processInstance.getId());
+//        
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        processInstance = ksession.getProcessInstance( processInstance.getId() );
+//        assertNull( processInstance );
+//    }
+//    
+//    public void testProcessListener() {
+//        KnowledgeBuilder kbuilder = KnowledgeBuilderFactory.newKnowledgeBuilder();
+//        kbuilder.add( new ClassPathResource( "WorkItemsProcess.rf" ),
+//                      ResourceType.DRF );
+//        KnowledgeBase kbase = KnowledgeBaseFactory.newKnowledgeBase();
+//        kbase.addKnowledgePackages( kbuilder.getKnowledgePackages() );
+//
+//        EntityManagerFactory emf = Persistence.createEntityManagerFactory( "org.drools.persistence.jpa" );
+//        Environment env = KnowledgeBaseFactory.newEnvironment();
+//        env.set( EnvironmentName.ENTITY_MANAGER_FACTORY,
+//                 emf );
+//
+//        env.set( EnvironmentName.GLOBALS, new MapGlobalResolver() );
+//
+//        StatefulKnowledgeSession ksession = JPAKnowledgeService.newStatefulKnowledgeSession( kbase, null, env );
+//        final List<ProcessEvent> events = new ArrayList<ProcessEvent>();
+//        ProcessEventListener listener = new ProcessEventListener() {
+//            public void afterNodeLeft(ProcessNodeLeftEvent event) {
+//                System.out.println("After node left: " + event.getNodeInstance().getNodeName());
+//                events.add(event);              
+//            }
+//            public void afterNodeTriggered(ProcessNodeTriggeredEvent event) {
+//                System.out.println("After node triggered: " + event.getNodeInstance().getNodeName());
+//                events.add(event);              
+//            }
+//            public void afterProcessCompleted(ProcessCompletedEvent event) {
+//                System.out.println("After process completed");
+//                events.add(event);              
+//            }
+//            public void afterProcessStarted(ProcessStartedEvent event) {
+//                System.out.println("After process started");
+//                events.add(event);              
+//            }
+//            public void beforeNodeLeft(ProcessNodeLeftEvent event) {
+//                System.out.println("Before node left: " + event.getNodeInstance().getNodeName());
+//                events.add(event);              
+//            }
+//            public void beforeNodeTriggered(ProcessNodeTriggeredEvent event) {
+//                System.out.println("Before node triggered: " + event.getNodeInstance().getNodeName());
+//                events.add(event);              
+//            }
+//            public void beforeProcessCompleted(ProcessCompletedEvent event) {
+//                System.out.println("Before process completed");
+//                events.add(event);              
+//            }
+//            public void beforeProcessStarted(ProcessStartedEvent event) {
+//                System.out.println("Before process started");
+//                events.add(event);              
+//            }
+//        };
+//        ksession.addEventListener(listener);
+//        
+//        ProcessInstance processInstance = ksession.startProcess( "org.drools.test.TestProcess" );
+//        System.out.println( "Started process instance " + processInstance.getId() );
+//        
+//        assertEquals(12, events.size());
+//        assertTrue(events.get(0) instanceof ProcessStartedEvent);
+//        assertTrue(events.get(1) instanceof ProcessNodeTriggeredEvent);
+//        assertTrue(events.get(2) instanceof ProcessNodeLeftEvent);
+//        assertTrue(events.get(3) instanceof ProcessNodeTriggeredEvent);
+//        assertTrue(events.get(4) instanceof ProcessNodeLeftEvent);
+//        assertTrue(events.get(5) instanceof ProcessNodeTriggeredEvent);
+//        assertTrue(events.get(6) instanceof ProcessNodeTriggeredEvent);
+//        assertTrue(events.get(7) instanceof ProcessNodeLeftEvent);
+//        assertTrue(events.get(8) instanceof ProcessNodeTriggeredEvent);
+//        assertTrue(events.get(9) instanceof ProcessNodeLeftEvent);
+//        assertTrue(events.get(10) instanceof ProcessNodeTriggeredEvent);
+//        assertTrue(events.get(11) instanceof ProcessStartedEvent);
+//        
+//        ksession.removeEventListener(listener);
+//        events.clear();
+//        
+//        processInstance = ksession.startProcess( "org.drools.test.TestProcess" );
+//        System.out.println( "Started process instance " + processInstance.getId() );
+//        
+//        assertTrue(events.isEmpty());
+//    }
+//
+//    public void testPersistenceSubProcess() {
+//        KnowledgeBuilder kbuilder = KnowledgeBuilderFactory.newKnowledgeBuilder();
+//        kbuilder.add( new ClassPathResource( "SuperProcess.rf" ),
+//                      ResourceType.DRF );
+//        kbuilder.add( new ClassPathResource( "SubProcess.rf" ),
+//                      ResourceType.DRF );
+//        KnowledgeBase kbase = KnowledgeBaseFactory.newKnowledgeBase();
+//        kbase.addKnowledgePackages( kbuilder.getKnowledgePackages() );
+//
+//        EntityManagerFactory emf = Persistence.createEntityManagerFactory( "org.drools.persistence.jpa" );
+//        Environment env = KnowledgeBaseFactory.newEnvironment();
+//        env.set( EnvironmentName.ENTITY_MANAGER_FACTORY,
+//                 emf );
+//
+//        StatefulKnowledgeSession ksession = JPAKnowledgeService.newStatefulKnowledgeSession( kbase, null, env );
+//        int id = ksession.getId();
+//        
+//        ProcessInstance processInstance = ksession.startProcess( "com.sample.SuperProcess" );
+//        System.out.println( "Started process instance " + processInstance.getId() );
+//
+//        TestWorkItemHandler handler = TestWorkItemHandler.getInstance();
+//        WorkItem workItem = handler.getWorkItem();
+//        assertNotNull( workItem );
+//
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        processInstance = ksession.getProcessInstance( processInstance.getId() );
+//        assertNotNull( processInstance );
+//
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        ksession.getWorkItemManager().completeWorkItem( workItem.getId(),
+//                                                       null );
+//
+//        workItem = handler.getWorkItem();
+//        assertNotNull( workItem );
+//
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        processInstance = ksession.getProcessInstance( processInstance.getId() );
+//        assertNotNull( processInstance );
+//
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        ksession.getWorkItemManager().completeWorkItem( workItem.getId(),
+//                                                       null );
+//
+//        workItem = handler.getWorkItem();
+//        assertNull( workItem );
+//
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        processInstance = ksession.getProcessInstance( processInstance.getId() );
+//        assertNull( processInstance );
+//    }
+//    
+//    public void testPersistenceVariables() {
+//        KnowledgeBuilder kbuilder = KnowledgeBuilderFactory.newKnowledgeBuilder();
+//        kbuilder.add( new ClassPathResource( "VariablesProcess.rf" ), ResourceType.DRF );
+//        for (KnowledgeBuilderError error: kbuilder.getErrors()) {
+//            System.out.println(error);
+//        }
+//        KnowledgeBase kbase = KnowledgeBaseFactory.newKnowledgeBase();
+//        kbase.addKnowledgePackages( kbuilder.getKnowledgePackages() );
+//
+//        EntityManagerFactory emf = Persistence.createEntityManagerFactory( "org.drools.persistence.jpa" );
+//        Environment env = KnowledgeBaseFactory.newEnvironment();
+//        env.set( EnvironmentName.ENTITY_MANAGER_FACTORY, emf );
+//
+//        env.set( EnvironmentName.GLOBALS, new MapGlobalResolver() );
+//
+//        StatefulKnowledgeSession ksession = JPAKnowledgeService.newStatefulKnowledgeSession( kbase, null, env );
+//        int id = ksession.getId();
+//
+//        Map<String, Object> parameters = new HashMap<String, Object>();
+//        parameters.put("name", "John Doe");
+//        ProcessInstance processInstance = ksession.startProcess( "org.drools.test.TestProcess", parameters );
+//
+//        TestWorkItemHandler handler = TestWorkItemHandler.getInstance();
+//        WorkItem workItem = handler.getWorkItem();
+//        assertNotNull( workItem );
+//        assertEquals( "John Doe", workItem.getParameter("name"));
+//
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        processInstance = ksession.getProcessInstance( processInstance.getId() );
+//        assertNotNull( processInstance );
+//
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        ksession.getWorkItemManager().completeWorkItem( workItem.getId(), null );
+//
+//        workItem = handler.getWorkItem();
+//        assertNotNull( workItem );
+//        assertEquals( "John Doe", workItem.getParameter("text"));
+//        
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        processInstance = ksession.getProcessInstance( processInstance.getId() );
+//        assertNotNull( processInstance );
+//
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        ksession.getWorkItemManager().completeWorkItem( workItem.getId(), null );
+//
+//        workItem = handler.getWorkItem();
+//        assertNull( workItem );
+//
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        processInstance = ksession.getProcessInstance( processInstance.getId() );
+//        assertNull( processInstance );
+//    }
+//
+//    public void testSetFocus() {
+//        String str = "";
+//        str += "package org.drools.test\n";
+//        str += "global java.util.List list\n";
+//        str += "rule rule1\n";
+//        str += "agenda-group \"badfocus\"";
+//        str += "when\n";
+//        str += "  Integer(intValue > 0)\n";
+//        str += "then\n";
+//        str += "  list.add( 1 );\n";
+//        str += "end\n";
+//        str += "\n";
+//
+//        KnowledgeBuilder kbuilder = KnowledgeBuilderFactory.newKnowledgeBuilder();
+//        kbuilder.add( ResourceFactory.newByteArrayResource( str.getBytes() ),
+//                      ResourceType.DRL );
+//        KnowledgeBase kbase = KnowledgeBaseFactory.newKnowledgeBase();
+//
+//        if ( kbuilder.hasErrors() ) {
+//            fail( kbuilder.getErrors().toString() );
+//        }
+//
+//        kbase.addKnowledgePackages( kbuilder.getKnowledgePackages() );
+//
+//        EntityManagerFactory emf = Persistence.createEntityManagerFactory( "org.drools.persistence.jpa" );
+//        Environment env = KnowledgeBaseFactory.newEnvironment();
+//        env.set( EnvironmentName.ENTITY_MANAGER_FACTORY,
+//                 emf );
+//        env.set( EnvironmentName.TRANSACTION_MANAGER,
+//                 TransactionManagerServices.getTransactionManager() );
+//        env.set( EnvironmentName.GLOBALS, new MapGlobalResolver() );
+//
+//        StatefulKnowledgeSession ksession = JPAKnowledgeService.newStatefulKnowledgeSession( kbase, null, env );
+//        List<?> list = new ArrayList<Object>();
+//
+//        ksession.setGlobal( "list",
+//                            list );
+//
+//        ksession.insert( 1 );
+//        ksession.insert( 2 );
+//        ksession.insert( 3 );
+//        ksession.getAgenda().getAgendaGroup("badfocus").setFocus();
+//
+//        ksession.fireAllRules();
+//
+//        assertEquals( 3,
+//                      list.size() );
+//    }
+//
+//    public void testPersistenceTimer() throws Exception {
+//        KnowledgeBuilder kbuilder = KnowledgeBuilderFactory.newKnowledgeBuilder();
+//        kbuilder.add( new ClassPathResource( "TimerProcess.rf" ),
+//                      ResourceType.DRF );
+//        KnowledgeBase kbase = kbuilder.newKnowledgeBase();
+//
+//        EntityManagerFactory emf = Persistence.createEntityManagerFactory( "org.drools.persistence.jpa" );
+//        Environment env = KnowledgeBaseFactory.newEnvironment();
+//        env.set( EnvironmentName.ENTITY_MANAGER_FACTORY, emf );
+//        env.set( EnvironmentName.GLOBALS, new MapGlobalResolver() );
+//
+//        StatefulKnowledgeSession ksession = JPAKnowledgeService.newStatefulKnowledgeSession( kbase, null, env );
+//        int id = ksession.getId();
+//        ksession.dispose();
+//        
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        ProcessInstance processInstance = ksession.startProcess( "org.drools.test.TestProcess" );
+//        ksession.dispose();
+//
+//        assertNotNull(TestWorkItemHandler.getInstance().getWorkItem());
+//        
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        processInstance = ksession.getProcessInstance( processInstance.getId() );
+//        assertNotNull( processInstance );
+//        
+//        Thread.sleep(2000);
+//        
+//        ksession.dispose();
+//
+//        ksession = JPAKnowledgeService.loadStatefulKnowledgeSession( id, kbase, null, env );
+//        processInstance = ksession.getProcessInstance( processInstance.getId() );
+//        assertNull( processInstance );
+//    }
+    
+}

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/resources/META-INF/orm.xml
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/resources/META-INF/orm.xml	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/resources/META-INF/orm.xml	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,6 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<entity-mappings xmlns="http://java.sun.com/xml/ns/persistence/orm"
+                 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+                 xsi:schemaLocation="http://java.sun.com/xml/ns/persistence/orm orm_1_0.xsd"
+                 version="1.0">  
+</entity-mappings>

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/resources/META-INF/persistence.xml
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/resources/META-INF/persistence.xml	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/resources/META-INF/persistence.xml	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1,22 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<persistence version="1.0" xmlns="http://java.sun.com/xml/ns/persistence" xmlns:orm="http://java.sun.com/xml/ns/persistence/orm" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/persistence       http://java.sun.com/xml/ns/persistence/persistence_1_0.xsd    http://java.sun.com/xml/ns/persistence/orm     http://java.sun.com/xml/ns/persistence/orm_1_0.xsd">
+ <!--persistence-unit name="ProcessService">
+  <jta-data-source>java:/DefaultDS</jta-data-source>
+  <properties>
+   <property name="hibernate.hbm2ddl.auto" value="create-drop"/>
+  </properties>
+ </persistence-unit-->
+    <persistence-unit name="org.drools.persistence.jpa" transaction-type="JTA">
+        <provider>org.hibernate.ejb.HibernatePersistence</provider>
+        <jta-data-source>jdbc/testDS1</jta-data-source>        
+        <class>org.drools.persistence.info.SessionInfo</class>
+        <class>org.drools.persistence.info.WorkItemInfo</class>
+	    <properties>
+	        <property name="hibernate.dialect" value="org.hibernate.dialect.H2Dialect"/>	        
+	        <property name="hibernate.max_fetch_depth" value="3"/>
+		    <property name="hibernate.hbm2ddl.auto" value="update" />
+            <property name="hibernate.show_sql" value="true" />	
+            <property name="hibernate.transaction.manager_lookup_class" value="org.hibernate.transaction.BTMTransactionManagerLookup" />
+	    </properties>        
+    </persistence-unit>
+</persistence>

Added: labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/resources/jndi.properties
===================================================================
--- labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/resources/jndi.properties	                        (rev 0)
+++ labs/jbossrules/tags/5.2.0.M1/drools-persistence-jpa/src/test/resources/jndi.properties	2011-02-24 17:26:49 UTC (rev 36709)
@@ -0,0 +1 @@
+java.naming.factory.initial=bitronix.tm.jndi.BitronixInitialContextFactory
\ No newline at end of file



More information about the jboss-svn-commits mailing list