[jboss-svn-commits] JBL Code SVN: r32428 - in labs/jbossrules/trunk: drools-compiler/src/test/java/org/drools/integrationtests and 9 other directories.
jboss-svn-commits at lists.jboss.org
jboss-svn-commits at lists.jboss.org
Mon Apr 5 17:58:54 EDT 2010
Author: KrisVerlaenen
Date: 2010-04-05 17:58:53 -0400 (Mon, 05 Apr 2010)
New Revision: 32428
Added:
labs/jbossrules/trunk/drools-compiler/src/test/java/org/drools/integrationtests/ProcessRuleFlowGroupTest.java
labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/node/DynamicUtils.java
Modified:
labs/jbossrules/trunk/drools-compiler/src/main/java/org/drools/osgi/compiler/Activator.java
labs/jbossrules/trunk/drools-compiler/src/test/java/org/drools/integrationtests/ProcessDynamicNodeTest.java
labs/jbossrules/trunk/drools-core/src/main/java/org/drools/Agenda.java
labs/jbossrules/trunk/drools-core/src/main/java/org/drools/audit/WorkingMemoryLogger.java
labs/jbossrules/trunk/drools-core/src/main/java/org/drools/base/DefaultKnowledgeHelper.java
labs/jbossrules/trunk/drools-core/src/main/java/org/drools/base/SequentialKnowledgeHelper.java
labs/jbossrules/trunk/drools-core/src/main/java/org/drools/common/DefaultAgenda.java
labs/jbossrules/trunk/drools-core/src/main/java/org/drools/common/InternalRuleFlowGroup.java
labs/jbossrules/trunk/drools-core/src/main/java/org/drools/common/RuleFlowGroupImpl.java
labs/jbossrules/trunk/drools-core/src/main/java/org/drools/marshalling/impl/AbstractProcessInstanceMarshaller.java
labs/jbossrules/trunk/drools-core/src/main/java/org/drools/marshalling/impl/PersisterEnums.java
labs/jbossrules/trunk/drools-core/src/main/java/org/drools/spi/KnowledgeHelper.java
labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/core/node/CompositeNode.java
labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/core/node/DynamicNode.java
labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/impl/ExtendedNodeInstanceImpl.java
labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/impl/NodeInstanceImpl.java
labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/impl/WorkflowProcessInstanceImpl.java
labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/node/CompositeNodeInstance.java
labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/node/DynamicNodeInstance.java
labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/node/RuleSetNodeInstance.java
labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/node/SubProcessNodeInstance.java
labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/node/WorkItemNodeInstance.java
Log:
JBRULES-2120: Dynamic or Ah-Hoc node
- extended impl. of dynamic node
Modified: labs/jbossrules/trunk/drools-compiler/src/main/java/org/drools/osgi/compiler/Activator.java
===================================================================
--- labs/jbossrules/trunk/drools-compiler/src/main/java/org/drools/osgi/compiler/Activator.java 2010-04-05 20:04:24 UTC (rev 32427)
+++ labs/jbossrules/trunk/drools-compiler/src/main/java/org/drools/osgi/compiler/Activator.java 2010-04-05 21:58:53 UTC (rev 32428)
@@ -6,7 +6,6 @@
import org.drools.Service;
import org.drools.builder.KnowledgeBuilderFactoryService;
import org.drools.builder.impl.KnowledgeBuilderFactoryServiceImpl;
-import org.drools.compiler.BPMN2ProcessFactory;
import org.drools.compiler.BPMN2ProcessProvider;
import org.drools.compiler.DecisionTableProvider;
import org.drools.osgi.api.Activator.BundleContextInstantiator;
@@ -25,6 +24,7 @@
private ServiceRegistration kbuilderReg;
private ServiceTracker dtableTracker;
+ private ServiceTracker bpmn2Tracker;
public void start(BundleContext bc) throws Exception {
System.out.println( "registering compiler services" );
@@ -42,12 +42,19 @@
this ) );
this.dtableTracker.open();
+ this.bpmn2Tracker = new ServiceTracker( bc,
+ BPMN2ProcessProvider.class.getName(),
+ new DroolsServiceTracker( bc,
+ this ) );
+ this.bpmn2Tracker.open();
+
System.out.println( "compiler services registered" );
}
public void stop(BundleContext bc) throws Exception {
this.kbuilderReg.unregister();
this.dtableTracker.close();
+ this.bpmn2Tracker.close();
}
public static class DroolsServiceTracker
Modified: labs/jbossrules/trunk/drools-compiler/src/test/java/org/drools/integrationtests/ProcessDynamicNodeTest.java
===================================================================
--- labs/jbossrules/trunk/drools-compiler/src/test/java/org/drools/integrationtests/ProcessDynamicNodeTest.java 2010-04-05 20:04:24 UTC (rev 32427)
+++ labs/jbossrules/trunk/drools-compiler/src/test/java/org/drools/integrationtests/ProcessDynamicNodeTest.java 2010-04-05 21:58:53 UTC (rev 32428)
@@ -3,20 +3,34 @@
import java.io.Reader;
import java.io.StringReader;
import java.util.ArrayList;
+import java.util.HashMap;
import java.util.List;
+import java.util.Map;
import junit.framework.TestCase;
+import org.drools.KnowledgeBase;
import org.drools.RuleBase;
import org.drools.RuleBaseFactory;
import org.drools.WorkingMemory;
+import org.drools.builder.KnowledgeBuilder;
+import org.drools.builder.KnowledgeBuilderFactory;
+import org.drools.builder.ResourceType;
import org.drools.compiler.DroolsError;
import org.drools.compiler.PackageBuilder;
+import org.drools.io.ResourceFactory;
+import org.drools.logger.KnowledgeRuntimeLogger;
+import org.drools.logger.KnowledgeRuntimeLoggerFactory;
import org.drools.process.instance.ProcessInstance;
+import org.drools.process.instance.impl.demo.SystemOutWorkItemHandler;
import org.drools.rule.Package;
+import org.drools.runtime.StatefulKnowledgeSession;
import org.drools.runtime.process.WorkItem;
import org.drools.runtime.process.WorkItemHandler;
import org.drools.runtime.process.WorkItemManager;
+import org.drools.runtime.process.WorkflowProcessInstance;
+import org.drools.workflow.instance.node.DynamicNodeInstance;
+import org.drools.workflow.instance.node.DynamicUtils;
public class ProcessDynamicNodeTest extends TestCase {
@@ -159,7 +173,147 @@
assertEquals(ProcessInstance.STATE_COMPLETED, processInstance.getState());
assertEquals(3, list.size());
}
+
+ public void testAddDynamicWorkItem() {
+ Reader source = new StringReader(
+ "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n" +
+ "<process xmlns=\"http://drools.org/drools-5.0/process\"\n" +
+ " xmlns:xs=\"http://www.w3.org/2001/XMLSchema-instance\"\n" +
+ " xs:schemaLocation=\"http://drools.org/drools-5.0/process drools-processes-5.0.xsd\"\n" +
+ " type=\"RuleFlow\" name=\"ruleflow\" id=\"org.drools.dynamic\" package-name=\"org.drools\" >\n" +
+ "\n" +
+ " <header>\n" +
+ " </header>\n" +
+ "\n" +
+ " <nodes>\n" +
+ " <start id=\"1\" name=\"Start\" />\n" +
+ " <dynamic id=\"2\" name=\"DynamicNode\" >\n" +
+ " <nodes>\n" +
+ " <actionNode id=\"1\" name=\"Action\" >\n" +
+ " <action type=\"expression\" dialect=\"mvel\" >System.out.println(\"Action\");</action>\n" +
+ " </actionNode>\n" +
+ " </nodes>\n" +
+ " <connections>\n" +
+ " </connections>\n" +
+ " <in-ports/>\n" +
+ " <out-ports/>\n" +
+ " </dynamic>\n" +
+ " <end id=\"3\" name=\"End\" />\n" +
+ " </nodes>\n" +
+ "\n" +
+ " <connections>\n" +
+ " <connection from=\"1\" to=\"2\" />\n" +
+ " <connection from=\"2\" to=\"3\" />\n" +
+ " </connections>\n" +
+ "</process>");
+ KnowledgeBuilder kbuilder = KnowledgeBuilderFactory.newKnowledgeBuilder();
+ kbuilder.add(ResourceFactory.newReaderResource(source), ResourceType.DRF);
+ KnowledgeBase kbase = kbuilder.newKnowledgeBase();
+ StatefulKnowledgeSession ksession = kbase.newStatefulKnowledgeSession();
+ KnowledgeRuntimeLogger logger = KnowledgeRuntimeLoggerFactory.newFileLogger(ksession, "test");
+ TestWorkItemHandler handler = new TestWorkItemHandler();
+ ksession.getWorkItemManager().registerWorkItemHandler("Human Task", handler);
+ // start a new process instance
+ ProcessInstance processInstance = (ProcessInstance) ksession.startProcess("org.drools.dynamic");
+ DynamicNodeInstance dynamicContext = (DynamicNodeInstance)
+ ((WorkflowProcessInstance) processInstance).getNodeInstances().iterator().next();
+ Map<String, Object> parameters = new HashMap<String, Object>();
+ parameters.put("TaskName", "Dynamic Task");
+ assertNull(handler.getWorkItem());
+ assertEquals(0, dynamicContext.getNodeInstances().size());
+ DynamicUtils.addDynamicWorkItem(dynamicContext, ksession, "Human Task", parameters);
+ assertNotNull(handler.getWorkItem());
+ assertEquals(1, dynamicContext.getNodeInstances().size());
+ logger.close();
+ }
+ public void testAddDynamicSubProcess() {
+ Reader source = new StringReader(
+ "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n" +
+ "<process xmlns=\"http://drools.org/drools-5.0/process\"\n" +
+ " xmlns:xs=\"http://www.w3.org/2001/XMLSchema-instance\"\n" +
+ " xs:schemaLocation=\"http://drools.org/drools-5.0/process drools-processes-5.0.xsd\"\n" +
+ " type=\"RuleFlow\" name=\"ruleflow\" id=\"org.drools.dynamic\" package-name=\"org.drools\" >\n" +
+ "\n" +
+ " <header>\n" +
+ " </header>\n" +
+ "\n" +
+ " <nodes>\n" +
+ " <start id=\"1\" name=\"Start\" />\n" +
+ " <dynamic id=\"2\" name=\"DynamicNode\" >\n" +
+ " <nodes>\n" +
+ " <actionNode id=\"1\" name=\"Action\" >\n" +
+ " <action type=\"expression\" dialect=\"mvel\" >System.out.println(\"Action\");</action>\n" +
+ " </actionNode>\n" +
+ " </nodes>\n" +
+ " <connections>\n" +
+ " </connections>\n" +
+ " <in-ports/>\n" +
+ " <out-ports/>\n" +
+ " </dynamic>\n" +
+ " <end id=\"3\" name=\"End\" />\n" +
+ " </nodes>\n" +
+ "\n" +
+ " <connections>\n" +
+ " <connection from=\"1\" to=\"2\" />\n" +
+ " <connection from=\"2\" to=\"3\" />\n" +
+ " </connections>\n" +
+ "</process>");
+ Reader source2 = new StringReader(
+ "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n" +
+ "<process xmlns=\"http://drools.org/drools-5.0/process\"\n" +
+ " xmlns:xs=\"http://www.w3.org/2001/XMLSchema-instance\"\n" +
+ " xs:schemaLocation=\"http://drools.org/drools-5.0/process drools-processes-5.0.xsd\"\n" +
+ " type=\"RuleFlow\" name=\"subflow\" id=\"org.drools.subflow\" package-name=\"org.drools\" >\n" +
+ "\n" +
+ " <header>\n" +
+ " <variables>\n" +
+ " <variable name=\"x\" >\n" +
+ " <type name=\"org.drools.process.core.datatype.impl.type.StringDataType\" />\n" +
+ " <value>SomeText</value>\n" +
+ " </variable>\n" +
+ " </variables>\n" +
+ " </header>\n" +
+ "\n" +
+ " <nodes>\n" +
+ " <start id=\"1\" name=\"Start\" />\n" +
+ " <actionNode id=\"2\" name=\"Action\" >\n" +
+ " <action type=\"expression\" dialect=\"mvel\" >System.out.println(x);</action>\n" +
+ " </actionNode>\n" +
+ " <workItem id=\"3\" name=\"Work\" >\n" +
+ " <work name=\"Human Task\" />\n" +
+ " </workItem>\n" +
+ " <end id=\"4\" name=\"End\" />\n" +
+ " </nodes>\n" +
+ "\n" +
+ " <connections>\n" +
+ " <connection from=\"1\" to=\"2\" />\n" +
+ " <connection from=\"2\" to=\"3\" />\n" +
+ " <connection from=\"3\" to=\"4\" />\n" +
+ " </connections>\n" +
+ "</process>");
+ KnowledgeBuilder kbuilder = KnowledgeBuilderFactory.newKnowledgeBuilder();
+ kbuilder.add(ResourceFactory.newReaderResource(source), ResourceType.DRF);
+ kbuilder.add(ResourceFactory.newReaderResource(source2), ResourceType.DRF);
+ KnowledgeBase kbase = kbuilder.newKnowledgeBase();
+ StatefulKnowledgeSession ksession = kbase.newStatefulKnowledgeSession();
+ KnowledgeRuntimeLogger logger = KnowledgeRuntimeLoggerFactory.newFileLogger(ksession, "test");
+ TestWorkItemHandler handler = new TestWorkItemHandler();
+ ksession.getWorkItemManager().registerWorkItemHandler("Human Task", handler);
+ // start a new process instance
+ ProcessInstance processInstance = (ProcessInstance) ksession.startProcess("org.drools.dynamic");
+ DynamicNodeInstance dynamicContext = (DynamicNodeInstance)
+ ((WorkflowProcessInstance) processInstance).getNodeInstances().iterator().next();
+ Map<String, Object> parameters = new HashMap<String, Object>();
+ parameters.put("x", "NewValue");
+ assertNull(handler.getWorkItem());
+ assertEquals(0, dynamicContext.getNodeInstances().size());
+ DynamicUtils.addDynamicSubProcess(dynamicContext, ksession, "org.drools.subflow", parameters);
+ assertNotNull(handler.getWorkItem());
+ assertEquals(1, dynamicContext.getNodeInstances().size());
+ logger.close();
+ }
+
private static class TestWorkItemHandler implements WorkItemHandler {
private WorkItem workItem;
public void executeWorkItem(WorkItem workItem, WorkItemManager manager) {
Added: labs/jbossrules/trunk/drools-compiler/src/test/java/org/drools/integrationtests/ProcessRuleFlowGroupTest.java
===================================================================
--- labs/jbossrules/trunk/drools-compiler/src/test/java/org/drools/integrationtests/ProcessRuleFlowGroupTest.java (rev 0)
+++ labs/jbossrules/trunk/drools-compiler/src/test/java/org/drools/integrationtests/ProcessRuleFlowGroupTest.java 2010-04-05 21:58:53 UTC (rev 32428)
@@ -0,0 +1,73 @@
+package org.drools.integrationtests;
+
+import java.io.Reader;
+import java.io.StringReader;
+
+import junit.framework.TestCase;
+
+import org.drools.Person;
+import org.drools.RuleBase;
+import org.drools.RuleBaseFactory;
+import org.drools.WorkingMemory;
+import org.drools.compiler.PackageBuilder;
+import org.drools.process.instance.ProcessInstance;
+import org.drools.rule.Package;
+import org.drools.ruleflow.instance.RuleFlowProcessInstance;
+
+public class ProcessRuleFlowGroupTest extends TestCase {
+
+ public void testRuleSetProcessContext() throws Exception {
+ PackageBuilder builder = new PackageBuilder();
+ Reader source = new StringReader(
+ "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n" +
+ "<process xmlns=\"http://drools.org/drools-5.0/process\"\n" +
+ " xmlns:xs=\"http://www.w3.org/2001/XMLSchema-instance\"\n" +
+ " xs:schemaLocation=\"http://drools.org/drools-5.0/process drools-processes-5.0.xsd\"\n" +
+ " type=\"RuleFlow\" name=\"flow\" id=\"org.drools.ruleset\" package-name=\"org.drools\" version=\"1\" >\n" +
+ "\n" +
+ " <header>\n" +
+ " </header>\n" +
+ "\n" +
+ " <nodes>\n" +
+ " <start id=\"1\" name=\"Start\" />\n" +
+ " <ruleSet id=\"2\" name=\"RuleSet\" ruleFlowGroup=\"MyGroup\" >\n" +
+ " </ruleSet>\n" +
+ " <end id=\"3\" name=\"End\" />\n" +
+ " </nodes>\n" +
+ "\n" +
+ " <connections>\n" +
+ " <connection from=\"1\" to=\"2\" />\n" +
+ " <connection from=\"2\" to=\"3\" />\n" +
+ " </connections>\n" +
+ "\n" +
+ "</process>");
+ Reader source2 = new StringReader(
+ "package org.drools;\n" +
+ "\n" +
+ "import org.drools.Person;\n" +
+ "import org.drools.runtime.process.ProcessContext;\n" +
+ "\n" +
+ "rule MyRule ruleflow-group \"MyGroup\"\n" +
+ " when\n" +
+ " Person( age > 25 )\n" +
+ " then\n" +
+ " System.out.println(drools.getContext(ProcessContext.class).getProcessInstance().getProcessName());\n" +
+ "end");
+ builder.addRuleFlow(source);
+ builder.addPackageFromDrl(source2);
+ Package pkg = builder.getPackage();
+ RuleBase ruleBase = RuleBaseFactory.newRuleBase();
+ ruleBase.addPackage( pkg );
+ WorkingMemory workingMemory = ruleBase.newStatefulSession();
+ Person person = new Person();
+ person.setAge(30);
+ workingMemory.insert(person);
+ // start process
+ RuleFlowProcessInstance processInstance = (RuleFlowProcessInstance)
+ workingMemory.startProcess("org.drools.ruleset");
+ assertEquals(ProcessInstance.STATE_ACTIVE, processInstance.getState());
+ workingMemory.fireAllRules();
+ assertEquals(ProcessInstance.STATE_COMPLETED, processInstance.getState());
+ }
+
+}
Modified: labs/jbossrules/trunk/drools-core/src/main/java/org/drools/Agenda.java
===================================================================
--- labs/jbossrules/trunk/drools-core/src/main/java/org/drools/Agenda.java 2010-04-05 20:04:24 UTC (rev 32427)
+++ labs/jbossrules/trunk/drools-core/src/main/java/org/drools/Agenda.java 2010-04-05 21:58:53 UTC (rev 32428)
@@ -48,6 +48,16 @@
* its activations are automatically added to the agenda.
*/
public void activateRuleFlowGroup(String name);
+
+ /**
+ * Activates the <code>RuleFlowGroup</code> with the given name.
+ * All activations in the given <code>RuleFlowGroup</code> are added to the agenda.
+ * As long as the <code>RuleFlowGroup</code> remains active,
+ * its activations are automatically added to the agenda.
+ * The given processInstanceId and nodeInstanceId define the process context
+ * in which this <code>RuleFlowGroup</code> is used.
+ */
+ public void activateRuleFlowGroup(String name, long processInstanceId, String nodeInstanceId);
/**
* Deactivates the <code>RuleFlowGroup</code> with the given name.
Modified: labs/jbossrules/trunk/drools-core/src/main/java/org/drools/audit/WorkingMemoryLogger.java
===================================================================
--- labs/jbossrules/trunk/drools-core/src/main/java/org/drools/audit/WorkingMemoryLogger.java 2010-04-05 20:04:24 UTC (rev 32427)
+++ labs/jbossrules/trunk/drools-core/src/main/java/org/drools/audit/WorkingMemoryLogger.java 2010-04-05 21:58:53 UTC (rev 32428)
@@ -459,6 +459,9 @@
private String createNodeId(NodeInstance nodeInstance) {
Node node = ((org.drools.workflow.instance.NodeInstance) nodeInstance).getNode();
+ if (node == null) {
+ return "";
+ }
String nodeId = "" + node.getId();
NodeContainer nodeContainer = node.getNodeContainer();
while (nodeContainer != null) {
Modified: labs/jbossrules/trunk/drools-core/src/main/java/org/drools/base/DefaultKnowledgeHelper.java
===================================================================
--- labs/jbossrules/trunk/drools-core/src/main/java/org/drools/base/DefaultKnowledgeHelper.java 2010-04-05 20:04:24 UTC (rev 32427)
+++ labs/jbossrules/trunk/drools-core/src/main/java/org/drools/base/DefaultKnowledgeHelper.java 2010-04-05 21:58:53 UTC (rev 32428)
@@ -27,7 +27,10 @@
import org.drools.FactException;
import org.drools.FactHandle;
import org.drools.WorkingMemory;
+import org.drools.common.InternalFactHandle;
+import org.drools.common.InternalRuleFlowGroup;
import org.drools.common.InternalWorkingMemoryActions;
+import org.drools.common.InternalWorkingMemoryEntryPoint;
import org.drools.impl.StatefulKnowledgeSessionImpl;
import org.drools.reteoo.ReteooWorkingMemory;
import org.drools.rule.Declaration;
@@ -35,11 +38,12 @@
import org.drools.rule.Rule;
import org.drools.runtime.ExitPoint;
import org.drools.runtime.KnowledgeRuntime;
+import org.drools.runtime.process.NodeInstance;
+import org.drools.runtime.process.NodeInstanceContainer;
+import org.drools.runtime.process.ProcessContext;
+import org.drools.runtime.process.ProcessInstance;
+import org.drools.runtime.process.WorkflowProcessInstance;
import org.drools.runtime.rule.WorkingMemoryEntryPoint;
-import org.drools.FactHandle;
-import org.drools.WorkingMemory;
-import org.drools.common.InternalFactHandle;
-import org.drools.common.InternalWorkingMemoryEntryPoint;
import org.drools.common.LogicalDependency;
import org.drools.core.util.LinkedList;
import org.drools.spi.Activation;
@@ -303,5 +307,43 @@
}
return handle;
}
+
+ @SuppressWarnings("unchecked")
+ public <T> T getContext(Class<T> contextClass) {
+ if (ProcessContext.class.equals(contextClass)) {
+ String ruleflowGroupName = getActivation().getRule().getRuleFlowGroup();
+ if (ruleflowGroupName != null) {
+ Map<Long, String> nodeInstances = ((InternalRuleFlowGroup) workingMemory.getAgenda().getRuleFlowGroup(ruleflowGroupName)).getNodeInstances();
+ if (!nodeInstances.isEmpty()) {
+ if (nodeInstances.size() > 1) {
+ // TODO
+ throw new UnsupportedOperationException(
+ "Not supporting multiple node instances for the same ruleflow group");
+ }
+ Map.Entry<Long, String> entry = nodeInstances.entrySet().iterator().next();
+ ProcessInstance processInstance = workingMemory.getProcessInstance(entry.getKey());
+ org.drools.spi.ProcessContext context = new org.drools.spi.ProcessContext();
+ context.setProcessInstance((org.drools.process.instance.ProcessInstance) processInstance);
+ String nodeInstance = entry.getValue();
+ String[] nodeInstanceIds = nodeInstance.split(":");
+ NodeInstanceContainer container = (WorkflowProcessInstance) processInstance;
+ for (int i = 0; i < nodeInstanceIds.length; i++) {
+ for (NodeInstance subNodeInstance: container.getNodeInstances()) {
+ if (subNodeInstance.getId() == new Long(nodeInstanceIds[i])) {
+ if (i == nodeInstanceIds.length - 1) {
+ context.setNodeInstance(subNodeInstance);
+ break;
+ } else {
+ container = (NodeInstanceContainer) subNodeInstance;
+ }
+ }
+ }
+ }
+ return (T) context;
+ }
+ }
+ }
+ return null;
+ }
}
Modified: labs/jbossrules/trunk/drools-core/src/main/java/org/drools/base/SequentialKnowledgeHelper.java
===================================================================
--- labs/jbossrules/trunk/drools-core/src/main/java/org/drools/base/SequentialKnowledgeHelper.java 2010-04-05 20:04:24 UTC (rev 32427)
+++ labs/jbossrules/trunk/drools-core/src/main/java/org/drools/base/SequentialKnowledgeHelper.java 2010-04-05 21:58:53 UTC (rev 32428)
@@ -21,9 +21,10 @@
import java.util.Map;
import org.drools.FactException;
+import org.drools.FactHandle;
+import org.drools.WorkingMemory;
import org.drools.common.InternalWorkingMemoryActions;
import org.drools.impl.StatefulKnowledgeSessionImpl;
-import org.drools.reteoo.ReteooStatefulSession;
import org.drools.reteoo.ReteooWorkingMemory;
import org.drools.rule.Declaration;
import org.drools.rule.GroupElement;
@@ -31,8 +32,6 @@
import org.drools.runtime.ExitPoint;
import org.drools.runtime.KnowledgeRuntime;
import org.drools.runtime.rule.WorkingMemoryEntryPoint;
-import org.drools.FactHandle;
-import org.drools.WorkingMemory;
import org.drools.spi.Activation;
import org.drools.spi.KnowledgeHelper;
import org.drools.spi.Tuple;
@@ -216,8 +215,14 @@
this.identityMap = identityMap;
}
+ public <T> T getContext(Class<T> contextClass) {
+ // TODO
+ return null;
+ }
+
public void cancelRemainingPreviousLogicalDependencies() {
// TODO Auto-generated method stub
}
+
}
Modified: labs/jbossrules/trunk/drools-core/src/main/java/org/drools/common/DefaultAgenda.java
===================================================================
--- labs/jbossrules/trunk/drools-core/src/main/java/org/drools/common/DefaultAgenda.java 2010-04-05 20:04:24 UTC (rev 32427)
+++ labs/jbossrules/trunk/drools-core/src/main/java/org/drools/common/DefaultAgenda.java 2010-04-05 21:58:53 UTC (rev 32428)
@@ -571,6 +571,12 @@
((InternalRuleFlowGroup) getRuleFlowGroup( name )).setActive( true );
}
+ public void activateRuleFlowGroup(final String name, long processInstanceId, String nodeInstanceId) {
+ InternalRuleFlowGroup ruleFlowGroup = (InternalRuleFlowGroup) getRuleFlowGroup( name );
+ ruleFlowGroup.addNodeInstance(processInstanceId, nodeInstanceId);
+ ruleFlowGroup.setActive( true );
+ }
+
public void deactivateRuleFlowGroup(final String name) {
((InternalRuleFlowGroup) getRuleFlowGroup( name )).setActive( false );
}
Modified: labs/jbossrules/trunk/drools-core/src/main/java/org/drools/common/InternalRuleFlowGroup.java
===================================================================
--- labs/jbossrules/trunk/drools-core/src/main/java/org/drools/common/InternalRuleFlowGroup.java 2010-04-05 20:04:24 UTC (rev 32427)
+++ labs/jbossrules/trunk/drools-core/src/main/java/org/drools/common/InternalRuleFlowGroup.java 2010-04-05 21:58:53 UTC (rev 32428)
@@ -1,5 +1,7 @@
package org.drools.common;
+import java.util.Map;
+
import org.drools.spi.Activation;
import org.drools.spi.RuleFlowGroup;
@@ -34,4 +36,10 @@
void removeRuleFlowGroupListener(RuleFlowGroupListener listener);
+ void addNodeInstance(Long processInstanceId, String nodeInstanceId);
+
+ void removeNodeInstance(Long processInstanceId, String nodeInstanceId);
+
+ Map<Long, String> getNodeInstances();
+
}
Modified: labs/jbossrules/trunk/drools-core/src/main/java/org/drools/common/RuleFlowGroupImpl.java
===================================================================
--- labs/jbossrules/trunk/drools-core/src/main/java/org/drools/common/RuleFlowGroupImpl.java 2010-04-05 20:04:24 UTC (rev 32427)
+++ labs/jbossrules/trunk/drools-core/src/main/java/org/drools/common/RuleFlowGroupImpl.java 2010-04-05 21:58:53 UTC (rev 32428)
@@ -19,7 +19,9 @@
import java.io.IOException;
import java.io.ObjectInput;
import java.io.ObjectOutput;
+import java.util.HashMap;
import java.util.List;
+import java.util.Map;
import java.util.concurrent.CopyOnWriteArrayList;
import org.drools.core.util.Iterator;
@@ -54,6 +56,7 @@
private boolean autoDeactivate = true;
private LinkedList list;
private List<RuleFlowGroupListener> listeners;
+ private Map<Long, String> nodeInstances = new HashMap<Long, String>();
public RuleFlowGroupImpl() {
@@ -139,6 +142,7 @@
activation.getActivationGroupNode().getActivationGroup().removeActivation( activation );
}
}
+ nodeInstances.clear();
notifyRuleFlowGroupListeners();
((EventSupport) this.workingMemory).getRuleFlowEventSupport().fireAfterRuleFlowGroupDeactivated( this,
this.workingMemory );
@@ -289,4 +293,17 @@
}
}
}
+
+ public void addNodeInstance(Long processInstanceId, String nodeInstanceId) {
+ nodeInstances.put(processInstanceId, nodeInstanceId);
+ }
+
+ public void removeNodeInstance(Long processInstanceId, String nodeInstanceId) {
+ nodeInstances.put(processInstanceId, nodeInstanceId);
+ }
+
+ public Map<Long, String> getNodeInstances() {
+ return nodeInstances;
+ }
+
}
Modified: labs/jbossrules/trunk/drools-core/src/main/java/org/drools/marshalling/impl/AbstractProcessInstanceMarshaller.java
===================================================================
--- labs/jbossrules/trunk/drools-core/src/main/java/org/drools/marshalling/impl/AbstractProcessInstanceMarshaller.java 2010-04-05 20:04:24 UTC (rev 32427)
+++ labs/jbossrules/trunk/drools-core/src/main/java/org/drools/marshalling/impl/AbstractProcessInstanceMarshaller.java 2010-04-05 21:58:53 UTC (rev 32428)
@@ -26,6 +26,7 @@
import org.drools.workflow.instance.impl.NodeInstanceImpl;
import org.drools.workflow.instance.impl.WorkflowProcessInstanceImpl;
import org.drools.workflow.instance.node.CompositeContextNodeInstance;
+import org.drools.workflow.instance.node.DynamicNodeInstance;
import org.drools.workflow.instance.node.ForEachNodeInstance;
import org.drools.workflow.instance.node.HumanTaskNodeInstance;
import org.drools.workflow.instance.node.JoinInstance;
@@ -175,6 +176,52 @@
} else {
stream.writeInt(0);
}
+ } else if (nodeInstance instanceof DynamicNodeInstance) {
+ stream.writeShort(PersisterEnums.DYNAMIC_NODE_INSTANCE);
+ DynamicNodeInstance dynamicNodeInstance = (DynamicNodeInstance) nodeInstance;
+ List<Long> timerInstances = dynamicNodeInstance.getTimerInstances();
+ if (timerInstances != null) {
+ stream.writeInt(timerInstances.size());
+ for (Long id : timerInstances) {
+ stream.writeLong(id);
+ }
+ } else {
+ stream.writeInt(0);
+ }
+ VariableScopeInstance variableScopeInstance = (VariableScopeInstance) dynamicNodeInstance.getContextInstance(VariableScope.VARIABLE_SCOPE);
+ if (variableScopeInstance == null) {
+ stream.writeInt(0);
+ } else {
+ Map<String, Object> variables = variableScopeInstance.getVariables();
+ List<String> keys = new ArrayList<String>(variables.keySet());
+ Collections.sort(keys,
+ new Comparator<String>() {
+ public int compare(String o1,
+ String o2) {
+ return o1.compareTo(o2);
+ }
+ });
+ stream.writeInt(keys.size());
+ for (String key : keys) {
+ stream.writeUTF(key);
+ stream.writeObject(variables.get(key));
+ }
+ }
+ List<NodeInstance> nodeInstances = new ArrayList<NodeInstance>(dynamicNodeInstance.getNodeInstances());
+ Collections.sort(nodeInstances,
+ new Comparator<NodeInstance>() {
+
+ public int compare(NodeInstance o1,
+ NodeInstance o2) {
+ return (int) (o1.getId() - o2.getId());
+ }
+ });
+ for (NodeInstance subNodeInstance : nodeInstances) {
+ stream.writeShort(PersisterEnums.NODE_INSTANCE);
+ writeNodeInstance(context,
+ subNodeInstance);
+ }
+ stream.writeShort(PersisterEnums.END);
} else if (nodeInstance instanceof CompositeContextNodeInstance) {
stream.writeShort(PersisterEnums.COMPOSITE_NODE_INSTANCE);
CompositeContextNodeInstance compositeNodeInstance = (CompositeContextNodeInstance) nodeInstance;
@@ -327,6 +374,7 @@
switch (nodeType) {
case PersisterEnums.COMPOSITE_NODE_INSTANCE:
+ case PersisterEnums.DYNAMIC_NODE_INSTANCE:
int nbVariables = stream.readInt();
if (nbVariables > 0) {
Context variableScope = ((org.drools.process.core.Process) processInstance.getProcess()).getDefaultContext(VariableScope.VARIABLE_SCOPE);
@@ -347,7 +395,7 @@
(CompositeContextNodeInstance) nodeInstance,
processInstance);
}
- break;
+ // don't break just yet, also do below
case PersisterEnums.FOR_EACH_NODE_INSTANCE:
while (stream.readShort() == PersisterEnums.NODE_INSTANCE) {
readNodeInstance(context,
@@ -425,6 +473,9 @@
case PersisterEnums.FOR_EACH_NODE_INSTANCE:
nodeInstance = new ForEachNodeInstance();
break;
+ case PersisterEnums.DYNAMIC_NODE_INSTANCE:
+ nodeInstance = new DynamicNodeInstance();
+ break;
case PersisterEnums.STATE_NODE_INSTANCE:
nodeInstance = new StateNodeInstance();
nbTimerInstances = stream.readInt();
Modified: labs/jbossrules/trunk/drools-core/src/main/java/org/drools/marshalling/impl/PersisterEnums.java
===================================================================
--- labs/jbossrules/trunk/drools-core/src/main/java/org/drools/marshalling/impl/PersisterEnums.java 2010-04-05 20:04:24 UTC (rev 32427)
+++ labs/jbossrules/trunk/drools-core/src/main/java/org/drools/marshalling/impl/PersisterEnums.java 2010-04-05 21:58:53 UTC (rev 32428)
@@ -40,5 +40,6 @@
public static final short FOR_EACH_NODE_INSTANCE = 28;
public static final short TIMER = 29;
public static final short STATE_NODE_INSTANCE = 30;
+ public static final short DYNAMIC_NODE_INSTANCE = 31;
}
Modified: labs/jbossrules/trunk/drools-core/src/main/java/org/drools/spi/KnowledgeHelper.java
===================================================================
--- labs/jbossrules/trunk/drools-core/src/main/java/org/drools/spi/KnowledgeHelper.java 2010-04-05 20:04:24 UTC (rev 32427)
+++ labs/jbossrules/trunk/drools-core/src/main/java/org/drools/spi/KnowledgeHelper.java 2010-04-05 21:58:53 UTC (rev 32428)
@@ -124,4 +124,6 @@
public IdentityHashMap<Object, FactHandle> getIdentityMap();
public void setIdentityMap(IdentityHashMap<Object, FactHandle> identityMap);
+
+ <T> T getContext(Class<T> contextClass);
}
\ No newline at end of file
Modified: labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/core/node/CompositeNode.java
===================================================================
--- labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/core/node/CompositeNode.java 2010-04-05 20:04:24 UTC (rev 32427)
+++ labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/core/node/CompositeNode.java 2010-04-05 21:58:53 UTC (rev 32428)
@@ -24,7 +24,8 @@
private org.drools.workflow.core.NodeContainer nodeContainer;
private Map<String, CompositeNode.NodeAndType> inConnectionMap = new HashMap<String, CompositeNode.NodeAndType>();
private Map<String, CompositeNode.NodeAndType> outConnectionMap = new HashMap<String, CompositeNode.NodeAndType>();
-
+ private boolean cancelRemainingInstances = true;
+
public CompositeNode() {
this.nodeContainer = new NodeContainerImpl();
}
@@ -321,6 +322,14 @@
}
}
+ public boolean isCancelRemainingInstances() {
+ return cancelRemainingInstances;
+ }
+
+ public void setCancelRemainingInstances(boolean cancelRemainingInstances) {
+ this.cancelRemainingInstances = cancelRemainingInstances;
+ }
+
public class NodeAndType implements Serializable {
private static final long serialVersionUID = 1L;
Modified: labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/core/node/DynamicNode.java
===================================================================
--- labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/core/node/DynamicNode.java 2010-04-05 20:04:24 UTC (rev 32427)
+++ labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/core/node/DynamicNode.java 2010-04-05 21:58:53 UTC (rev 32428)
@@ -1,7 +1,35 @@
package org.drools.workflow.core.node;
+import org.drools.definition.process.Node;
+
public class DynamicNode extends CompositeContextNode {
private static final long serialVersionUID = 400L;
+ private boolean autoComplete = false;
+
+ public boolean isAutoComplete() {
+ return autoComplete;
+ }
+
+ public void setAutoComplete(boolean autoComplete) {
+ this.autoComplete = autoComplete;
+ }
+
+ public boolean acceptsEvent(String type, Object event) {
+ for (Node node: getNodes()) {
+ if (type.equals(node.getName()) && node.getIncomingConnections().isEmpty()) {
+ return true;
+ }
+ }
+ return super.acceptsEvent(type, event);
+ }
+
+ public Node internalGetNode(long id) {
+ try {
+ return getNode(id);
+ } catch (IllegalArgumentException e) {
+ return null;
+ }
+ }
}
Modified: labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/impl/ExtendedNodeInstanceImpl.java
===================================================================
--- labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/impl/ExtendedNodeInstanceImpl.java 2010-04-05 20:04:24 UTC (rev 32427)
+++ labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/impl/ExtendedNodeInstanceImpl.java 2010-04-05 21:58:53 UTC (rev 32428)
@@ -38,7 +38,11 @@
}
protected void triggerEvent(String type) {
- List<DroolsAction> actions = getExtendedNode().getActions(type);
+ ExtendedNodeImpl extendedNode = getExtendedNode();
+ if (extendedNode == null) {
+ return;
+ }
+ List<DroolsAction> actions = extendedNode.getActions(type);
if (actions != null) {
KnowledgeHelper knowledgeHelper = createKnowledgeHelper();
for (DroolsAction droolsAction: actions) {
Modified: labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/impl/NodeInstanceImpl.java
===================================================================
--- labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/impl/NodeInstanceImpl.java 2010-04-05 20:04:24 UTC (rev 32427)
+++ labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/impl/NodeInstanceImpl.java 2010-04-05 21:58:53 UTC (rev 32428)
@@ -33,6 +33,7 @@
import org.drools.runtime.process.NodeInstanceContainer;
import org.drools.workflow.core.impl.NodeImpl;
import org.drools.workflow.instance.WorkflowProcessInstance;
+import org.drools.workflow.instance.node.CompositeNodeInstance;
/**
* Default implementation of a RuleFlow node instance.
@@ -65,7 +66,8 @@
}
public String getNodeName() {
- return getNode().getName();
+ Node node = getNode();
+ return node == null ? "" : node.getName();
}
public void setProcessInstance(final WorkflowProcessInstance processInstance) {
@@ -122,18 +124,23 @@
((org.drools.workflow.instance.NodeInstanceContainer) getNodeInstanceContainer())
.removeNodeInstance(this);
}
- List<Connection> connections = getNode().getOutgoingConnections(type);
+ Node node = getNode();
+ List<Connection> connections = null;
+ if (node != null) {
+ connections = node.getOutgoingConnections(type);
+ }
if (connections == null || connections.isEmpty()) {
((org.drools.workflow.instance.NodeInstanceContainer) getNodeInstanceContainer())
.nodeInstanceCompleted(this, type);
+ } else {
+ for (Connection connection: connections) {
+ // stop if this process instance has been aborted / completed
+ if (getProcessInstance().getState() != ProcessInstance.STATE_ACTIVE) {
+ return;
+ }
+ triggerConnection(connection);
+ }
}
- for (Connection connection: connections) {
- // stop if this process instance has been aborted / completed
- if (getProcessInstance().getState() != ProcessInstance.STATE_ACTIVE) {
- return;
- }
- triggerConnection(connection);
- }
}
protected void triggerConnection(Connection connection) {
@@ -201,4 +208,15 @@
}
}
+ public String getUniqueId() {
+ String result = "" + getId();
+ NodeInstanceContainer parent = getNodeInstanceContainer();
+ while (parent instanceof CompositeNodeInstance) {
+ CompositeNodeInstance nodeInstance = (CompositeNodeInstance) parent;
+ result = nodeInstance.getId() + ":" + result;
+ parent = nodeInstance.getNodeInstanceContainer();
+ }
+ return result;
+ }
+
}
Modified: labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/impl/WorkflowProcessInstanceImpl.java
===================================================================
--- labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/impl/WorkflowProcessInstanceImpl.java 2010-04-05 20:04:24 UTC (rev 32427)
+++ labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/impl/WorkflowProcessInstanceImpl.java 2010-04-05 21:58:53 UTC (rev 32428)
@@ -38,6 +38,7 @@
import org.drools.process.instance.impl.ProcessInstanceImpl;
import org.drools.runtime.process.EventListener;
import org.drools.runtime.process.NodeInstanceContainer;
+import org.drools.workflow.core.impl.NodeImpl;
import org.drools.workflow.core.node.EventNode;
import org.drools.workflow.core.node.EventNodeInterface;
import org.drools.workflow.instance.NodeInstance;
@@ -102,6 +103,21 @@
return Collections.unmodifiableCollection(result);
}
+ public List<String> getActiveNodeIds() {
+ List<String> result = new ArrayList<String>();
+ addActiveNodeIds(this, result);
+ return result;
+ }
+
+ private void addActiveNodeIds(NodeInstanceContainer container, List<String> result) {
+ for (org.drools.runtime.process.NodeInstance nodeInstance: container.getNodeInstances()) {
+ result.add(((NodeImpl) ((NodeInstanceImpl) nodeInstance).getNode()).getUniqueId());
+ if (nodeInstance instanceof NodeInstanceContainer) {
+ addActiveNodeIds((NodeInstanceContainer) nodeInstance, result);
+ }
+ }
+ }
+
public NodeInstance getFirstNodeInstance(final long nodeId) {
for (final Iterator<NodeInstance> iterator = this.nodeInstances
.iterator(); iterator.hasNext();) {
Modified: labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/node/CompositeNodeInstance.java
===================================================================
--- labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/node/CompositeNodeInstance.java 2010-04-05 20:04:24 UTC (rev 32427)
+++ labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/node/CompositeNodeInstance.java 2010-04-05 21:58:53 UTC (rev 32428)
@@ -126,10 +126,13 @@
}
public void triggerCompleted(String outType) {
- triggerCompleted(outType, true);
- while (!nodeInstances.isEmpty()) {
- NodeInstance nodeInstance = (NodeInstance) nodeInstances.get(0);
- ((org.drools.workflow.instance.NodeInstance) nodeInstance).cancel();
+ boolean cancelRemainingInstances = getCompositeNode().isCancelRemainingInstances();
+ triggerCompleted(outType, cancelRemainingInstances);
+ if (cancelRemainingInstances) {
+ while (!nodeInstances.isEmpty()) {
+ NodeInstance nodeInstance = (NodeInstance) nodeInstances.get(0);
+ ((org.drools.workflow.instance.NodeInstance) nodeInstance).cancel();
+ }
}
}
Modified: labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/node/DynamicNodeInstance.java
===================================================================
--- labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/node/DynamicNodeInstance.java 2010-04-05 20:04:24 UTC (rev 32427)
+++ labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/node/DynamicNodeInstance.java 2010-04-05 21:58:53 UTC (rev 32428)
@@ -1,45 +1,53 @@
package org.drools.workflow.instance.node;
-import java.util.List;
-import java.util.Map;
-
-import org.drools.definition.process.Connection;
import org.drools.definition.process.Node;
import org.drools.runtime.process.NodeInstance;
import org.drools.workflow.core.impl.NodeImpl;
+import org.drools.workflow.core.node.DynamicNode;
public class DynamicNodeInstance extends CompositeContextNodeInstance {
private static final long serialVersionUID = 4L;
- private transient boolean executing = false;
+ private String getRuleFlowGroupName() {
+ return getNodeName();
+ }
+ protected DynamicNode getDynamicNode() {
+ return (DynamicNode) getNode();
+ }
+
public void internalTrigger(NodeInstance from, String type) {
- executing = true;
- createNodeInstances();
- executing = false;
- if (getNodeInstances(false).isEmpty()) {
- triggerCompleted(NodeImpl.CONNECTION_DEFAULT_TYPE);
- }
+ getProcessInstance().getWorkingMemory().getAgenda().getRuleFlowGroup(getRuleFlowGroupName()).setAutoDeactivate(false);
+ getProcessInstance().getWorkingMemory().getAgenda().activateRuleFlowGroup(
+ getRuleFlowGroupName(), getProcessInstance().getId(), getUniqueId());
+// if (getDynamicNode().isAutoComplete() && getNodeInstances(false).isEmpty()) {
+// triggerCompleted(NodeImpl.CONNECTION_DEFAULT_TYPE);
+// }
}
-
- private void createNodeInstances() {
- for (Node node: getCompositeNode().getNodes()) {
- Map<String, List<Connection>> incomingConnections = node.getIncomingConnections();
- if (incomingConnections.isEmpty()) {
- NodeInstance nodeInstance = getNodeInstance(node);
- ((org.drools.workflow.instance.NodeInstance) nodeInstance)
- .trigger(null, NodeImpl.CONNECTION_DEFAULT_TYPE);
- }
- }
- }
public void nodeInstanceCompleted(org.drools.workflow.instance.NodeInstance nodeInstance, String outType) {
// TODO what if we reach the end of one branch but others might still need to be created ?
// TODO are we sure there will always be node instances left if we are not done yet?
- if (!executing && getNodeInstances(false).isEmpty()) {
+ if (getDynamicNode().isAutoComplete() && getNodeInstances(false).isEmpty()) {
triggerCompleted(NodeImpl.CONNECTION_DEFAULT_TYPE);
}
}
+
+ public void triggerCompleted(String outType) {
+ getProcessInstance().getWorkingMemory().getAgenda().deactivateRuleFlowGroup(getRuleFlowGroupName());
+ super.triggerCompleted(outType);
+ }
+ public void signalEvent(String type, Object event) {
+ super.signalEvent(type, event);
+ for (Node node: getCompositeNode().getNodes()) {
+ if (type.equals(node.getName()) && node.getIncomingConnections().isEmpty()) {
+ NodeInstance nodeInstance = getNodeInstance(node);
+ ((org.drools.workflow.instance.NodeInstance) nodeInstance)
+ .trigger(null, NodeImpl.CONNECTION_DEFAULT_TYPE);
+ }
+ }
+ }
+
}
Added: labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/node/DynamicUtils.java
===================================================================
--- labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/node/DynamicUtils.java (rev 0)
+++ labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/node/DynamicUtils.java 2010-04-05 21:58:53 UTC (rev 32428)
@@ -0,0 +1,67 @@
+package org.drools.workflow.instance.node;
+
+import java.util.Map;
+
+import org.drools.common.EventSupport;
+import org.drools.common.InternalRuleBase;
+import org.drools.common.InternalWorkingMemory;
+import org.drools.definition.process.Process;
+import org.drools.impl.StatefulKnowledgeSessionImpl;
+import org.drools.process.instance.ProcessInstance;
+import org.drools.process.instance.WorkItemManager;
+import org.drools.process.instance.impl.WorkItemImpl;
+import org.drools.runtime.process.ProcessRuntime;
+import org.drools.runtime.process.WorkItem;
+import org.drools.workflow.instance.WorkflowProcessInstance;
+
+
+public class DynamicUtils {
+
+ public static void addDynamicWorkItem(
+ DynamicNodeInstance dynamicContext, ProcessRuntime ksession,
+ String workItemName, Map<String, Object> parameters) {
+ WorkflowProcessInstance processInstance = dynamicContext.getProcessInstance();
+ WorkItemImpl workItem = new WorkItemImpl();
+ workItem.setState(WorkItem.ACTIVE);
+ workItem.setProcessInstanceId(processInstance.getId());
+ workItem.setName(workItemName);
+ workItem.setParameters(parameters);
+ WorkItemNodeInstance workItemNodeInstance = new WorkItemNodeInstance();
+ workItemNodeInstance.setNodeInstanceContainer(dynamicContext);
+ workItemNodeInstance.setProcessInstance(processInstance);
+ workItemNodeInstance.internalSetWorkItem(workItem);
+ workItemNodeInstance.addEventListeners();
+ InternalWorkingMemory workingMemory = ((StatefulKnowledgeSessionImpl) ksession).session;
+ ((EventSupport) workingMemory).getRuleFlowEventSupport().fireBeforeRuleFlowNodeTriggered(workItemNodeInstance, workingMemory);
+ ((WorkItemManager) ksession.getWorkItemManager()).internalExecuteWorkItem(workItem);
+ ((EventSupport) workingMemory).getRuleFlowEventSupport().fireAfterRuleFlowNodeTriggered(workItemNodeInstance, (InternalWorkingMemory) workingMemory);
+ }
+
+ public static void addDynamicSubProcess(
+ DynamicNodeInstance dynamicContext, ProcessRuntime ksession,
+ String processId, Map<String, Object> parameters) {
+ WorkflowProcessInstance processInstance = dynamicContext.getProcessInstance();
+ SubProcessNodeInstance subProcessNodeInstance = new SubProcessNodeInstance();
+ subProcessNodeInstance.setNodeInstanceContainer(dynamicContext);
+ subProcessNodeInstance.setProcessInstance(processInstance);
+ InternalWorkingMemory workingMemory = ((StatefulKnowledgeSessionImpl) ksession).session;
+ Process process = ((InternalRuleBase) workingMemory.getRuleBase()).getProcess(processId);
+ if (process == null) {
+ System.err.println("Could not find process " + processId);
+ System.err.println("Aborting process");
+ processInstance.setState(ProcessInstance.STATE_ABORTED);
+ } else {
+ ((EventSupport) workingMemory).getRuleFlowEventSupport().fireBeforeRuleFlowNodeTriggered(subProcessNodeInstance, workingMemory);
+ ProcessInstance subProcessInstance = (ProcessInstance)
+ workingMemory.startProcess(processId, parameters);
+ ((EventSupport) workingMemory).getRuleFlowEventSupport().fireAfterRuleFlowNodeTriggered(subProcessNodeInstance, (InternalWorkingMemory) workingMemory);
+ if (subProcessInstance.getState() == ProcessInstance.STATE_COMPLETED) {
+ subProcessNodeInstance.triggerCompleted();
+ } else {
+ subProcessNodeInstance.internalSetProcessInstanceId(subProcessInstance.getId());
+ subProcessNodeInstance.addEventListeners();
+ }
+ }
+ }
+
+}
Modified: labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/node/RuleSetNodeInstance.java
===================================================================
--- labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/node/RuleSetNodeInstance.java 2010-04-05 20:04:24 UTC (rev 32427)
+++ labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/node/RuleSetNodeInstance.java 2010-04-05 21:58:53 UTC (rev 32428)
@@ -39,7 +39,7 @@
throw new IllegalArgumentException( "A RuleSetNode only accepts default incoming connections!" );
}
addRuleSetListener();
- ((ProcessInstance) getProcessInstance()).getAgenda().activateRuleFlowGroup( getRuleSetNode().getRuleFlowGroup() );
+ ((ProcessInstance) getProcessInstance()).getAgenda().activateRuleFlowGroup( getRuleSetNode().getRuleFlowGroup(), getProcessInstance().getId(), getUniqueId() );
}
public void addEventListeners() {
Modified: labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/node/SubProcessNodeInstance.java
===================================================================
--- labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/node/SubProcessNodeInstance.java 2010-04-05 20:04:24 UTC (rev 32427)
+++ labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/node/SubProcessNodeInstance.java 2010-04-05 21:58:53 UTC (rev 32428)
@@ -22,9 +22,11 @@
import java.util.regex.Pattern;
import org.drools.common.InternalRuleBase;
+import org.drools.definition.process.Node;
import org.drools.definition.process.Process;
import org.drools.process.core.context.variable.VariableScope;
import org.drools.process.instance.ProcessInstance;
+import org.drools.process.instance.WorkItem;
import org.drools.process.instance.context.variable.VariableScopeInstance;
import org.drools.runtime.process.EventListener;
import org.drools.runtime.process.NodeInstance;
@@ -129,7 +131,7 @@
public void cancel() {
super.cancel();
- if (!getSubProcessNode().isIndependent()) {
+ if (getSubProcessNode() == null || !getSubProcessNode().isIndependent()) {
ProcessInstance processInstance = (ProcessInstance)
((ProcessInstance) getProcessInstance()).getWorkingMemory()
.getProcessInstance(processInstanceId);
@@ -202,5 +204,13 @@
}
}
}
+
+ public String getNodeName() {
+ Node node = getNode();
+ if (node == null) {
+ return "[Dynamic] Sub Process";
+ }
+ return super.getNodeName();
+ }
}
\ No newline at end of file
Modified: labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/node/WorkItemNodeInstance.java
===================================================================
--- labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/node/WorkItemNodeInstance.java 2010-04-05 20:04:24 UTC (rev 32427)
+++ labs/jbossrules/trunk/drools-core/src/main/java/org/drools/workflow/instance/node/WorkItemNodeInstance.java 2010-04-05 21:58:53 UTC (rev 32428)
@@ -24,6 +24,7 @@
import org.drools.WorkingMemory;
import org.drools.common.InternalRuleBase;
+import org.drools.definition.process.Node;
import org.drools.process.core.Work;
import org.drools.process.core.context.variable.VariableScope;
import org.drools.process.instance.ProcessInstance;
@@ -71,6 +72,10 @@
this.workItemId = workItemId;
}
+ public void internalSetWorkItem(WorkItem workItem) {
+ this.workItem = workItem;
+ }
+
public boolean isInversionOfControl() {
return ((InternalRuleBase) ((ProcessInstance) getProcessInstance())
.getWorkingMemory().getRuleBase()).getConfiguration().isAdvancedProcessRuleIntegration();
@@ -165,26 +170,29 @@
}
public void triggerCompleted(WorkItem workItem) {
- for (Iterator<Map.Entry<String, String>> iterator = getWorkItemNode().getOutMappings().entrySet().iterator(); iterator.hasNext(); ) {
- Map.Entry<String, String> mapping = iterator.next();
- VariableScopeInstance variableScopeInstance = (VariableScopeInstance)
- resolveContextInstance(VariableScope.VARIABLE_SCOPE, mapping.getValue());
- if (variableScopeInstance != null) {
- Object value = workItem.getResult(mapping.getKey());
- if (value == null) {
- try {
- value = MVEL.eval(mapping.getKey(), new WorkItemResolverFactory(workItem));
- } catch (Throwable t) {
- // do nothing
- }
- }
- variableScopeInstance.setVariable(mapping.getValue(), value);
- } else {
- System.err.println("Could not find variable scope for variable " + mapping.getValue());
- System.err.println("when trying to complete Work Item " + workItem.getName());
- System.err.println("Continuing without setting variable.");
- }
- }
+ WorkItemNode workItemNode = getWorkItemNode();
+ if (workItemNode != null) {
+ for (Iterator<Map.Entry<String, String>> iterator = getWorkItemNode().getOutMappings().entrySet().iterator(); iterator.hasNext(); ) {
+ Map.Entry<String, String> mapping = iterator.next();
+ VariableScopeInstance variableScopeInstance = (VariableScopeInstance)
+ resolveContextInstance(VariableScope.VARIABLE_SCOPE, mapping.getValue());
+ if (variableScopeInstance != null) {
+ Object value = workItem.getResult(mapping.getKey());
+ if (value == null) {
+ try {
+ value = MVEL.eval(mapping.getKey(), new WorkItemResolverFactory(workItem));
+ } catch (Throwable t) {
+ // do nothing
+ }
+ }
+ variableScopeInstance.setVariable(mapping.getValue(), value);
+ } else {
+ System.err.println("Could not find variable scope for variable " + mapping.getValue());
+ System.err.println("when trying to complete Work Item " + workItem.getName());
+ System.err.println("Continuing without setting variable.");
+ }
+ }
+ }
if (isInversionOfControl()) {
WorkingMemory workingMemory = ((ProcessInstance) getProcessInstance()).getWorkingMemory();
workingMemory.update(workingMemory.getFactHandle(this), this);
@@ -247,4 +255,17 @@
}
}
+ public String getNodeName() {
+ Node node = getNode();
+ if (node == null) {
+ String nodeName = "[Dynamic]";
+ WorkItem workItem = getWorkItem();
+ if (workItem != null) {
+ nodeName += " " + workItem.getParameter("TaskName");
+ }
+ return nodeName;
+ }
+ return super.getNodeName();
+ }
+
}
\ No newline at end of file
More information about the jboss-svn-commits
mailing list