9 Replies Latest reply on Sep 1, 2009 3:34 AM by Ronald van Kuijk

    decision node based on data not in task variables

    Sofie Ravyts Newbie

      Hello,

      I'm strugling with the conversion from jbpm3 to jbpm4 in our application:

      I'm trying to find a workaround for not being able to configure a custom Variable Resolver (we need to make decisions based on data that is not stored in taks variables but in our own datastore)

      I was thinking implementing something like this:
      construct transition conditions using a method in a spring bean
      example:

      <decision name="evaluate document" g="96,102,48,48">
       <transition name="good" to="submit document" g="120,60:-37,22" >
       <condition ref="myConditionBean" method="isTrue">
       <arg><string value="true"/></arg>
       </condition>
       </transition>
       <transition name="bad" to="try again" g=":-19,-22" >
       <condition class="myConditionBean" method="isFalse">
       <arg><string value="true"/></arg>
       </condition>
       </transition>
       </decision>
      



      In this case (where the argument for the method is a string "true" the first transition will be taken.

      This would allow us to pass as the argument a reference to an object in our own datastore and allow us to inject spring beans in the myConditionBean class for retrieving the data referenced.
      But, the condition element doesn't allow to reference a class which doesn't implement the Condition interface as far as I can see in the source code.

      If I would be able to pass an extra argument to the evaluate method in the class implementing Condition (and have this class be referenced as a spring bean), it would also solve my problem.

      Is any of these things possible?
      Is there another solution I'm missing?

      Wkr,
      Sofie


        • 1. Re: decision node based on data not in task variables
          Ronald van Kuijk Master

          Sofie,

          Read the userguide about decisions and use the 'handler' solution

          • 2. Re: decision node based on data not in task variables
            Sofie Ravyts Newbie

            Of course I have done this extensively before posting to this mailing list.

            But this solution isn't working for me because i don't know the names of the transitions in the handler class. We are trying to build a generic system (we create processdefinitions on the fly) and cannot create specific classes for each process.

            That is why I wanted the "handler" functionality on the transition conditions and not on the decision node level.



            • 3. Re: decision node based on data not in task variables
              Ronald van Kuijk Master

              Then next time please mention you did all this and this the additional information you provided now.



              The handler will work, otherwise I would not have pointed to you, but you have to be creative.... you can pass arguments to the handler. So make a generic handler and pass it the expressions you want, including e.g. the transitionnames that belong to it. e.g. pass it

              <conditions>
               <condition>
               <transition>bad</transition>
               <expression>MyCustomExpression<expression>
               </condition>
               <condition>
               <transition>good</transition>
               <expression>MySecondCustomExpression<expression>
               </condition>
              </conditions>
              


              And that will be in a Document in the handler where you can do ANYTHING you like with it and return the transitionname without you having to know it in the handler in advance.

              • 4. Re: decision node based on data not in task variables
                Sofie Ravyts Newbie

                Is it possible to use a spring bean as the handler in a decision node?

                I can't seem to get this working (although I registered spring as a language for the expression language in jbpm.cfg.xml:

                <script-manager default-expression-language="juel"
                 default-script-language="juel"
                 read-contexts="execution, environment, process-engine, spring"
                 write-context="">
                 <script-language name="juel"
                 factory="org.jbpm.pvm.internal.script.JuelScriptEngineFactory" />
                 </script-manager>
                


                I get the following error:

                Caused by: javax.el.PropertyNotFoundException: Cannot find property decisionConditionHandler
                 at de.odysseus.el.util.SimpleResolver.get(SimpleResolver.java:106)
                 at de.odysseus.el.util.SimpleResolver.getValue(SimpleResolver.java:126)
                 at de.odysseus.el.tree.impl.ast.AstIdentifier.eval(AstIdentifier.java:69)
                 at de.odysseus.el.tree.impl.ast.AstEval.eval(AstEval.java:42)
                 at de.odysseus.el.tree.impl.ast.AstNode.getValue(AstNode.java:29)
                 at de.odysseus.el.TreeValueExpression.getValue(TreeValueExpression.java:120)
                 at org.jbpm.pvm.internal.script.JuelScriptEngine.evalExpr(JuelScriptEngine.java:176)


                this is my process :

                <?xml version="1.0" encoding="UTF-8"?>
                
                <process name="DecisionConditions" xmlns="http://jbpm.org/4.0/jpdl">
                
                 <start g="16,102,48,48">
                 <transition to="evaluate document" />
                 </start>
                
                 <decision name="evaluate document" g="96,102,48,48">
                 <handler expr="#{decisionConditionHandler}">
                 <conditions>
                 <condition>
                 <transition>bad</transition>
                 <expression>#{huur.commercieel == false}</expression>
                 </condition>
                 <condition>
                 <transition>good</transition>
                 <expression>#{huur.commercieel == true}</expression>
                 </condition>
                 </conditions>
                 </handler>
                
                
                 <transition name="good" to="submit document" g="120,60:-37,22" />
                 <transition name="bad" to="try again" g=":-19,-22" />
                 </decision>
                
                 <state name="submit document" g="175,35,122,52"/>
                 <state name="try again" g="176,100,122,52"/>
                
                </process>



                • 5. Re: decision node based on data not in task variables
                  Sofie Ravyts Newbie

                  Forgot to include the correct beans so please ignore my previous post.
                  I need to get some more sleep I guess...

                  • 6. Re: decision node based on data not in task variables
                    Sofie Ravyts Newbie

                    One more question:

                    How do you pass arguments if you can't change the method signature (the condition handler needs to implement DecisionHandler which has a method
                    decide(executionContext)... )?

                    How do I get the Document you mention into this class?

                    What am I not seeing here?


                    Wkr,
                    Sofie

                    • 7. Re: decision node based on data not in task variables
                      Ronald van Kuijk Master

                      You are not seeing the default way to pass data to delegationhandlers (actionhandlers, eventhandlers, decisionhandlers)
                      Putting something like

                      
                       <field name="assignee">
                       <string value="johndoe" />
                       </field>
                      

                      inside the handler tag and declaring assignee as a String field in your class will make sure it is passed on

                      • 8. Re: decision node based on data not in task variables
                        Sofie Ravyts Newbie

                        Ok, that was indeed what I was missing, thanks for the help.

                        This is my actual node in my processdefinition:


                        <j:decision name="evaluate document">
                         <handler expr="#{decisionConditionHandler}">
                         <field name="conditions">
                         <list>
                         <object class="org.example.Condition">
                         <field name="transitionName">
                         <string value="Bad"/>
                         </field>
                         <field name="expression">
                         <string value="#{varName == false}"/>
                         </field>
                         </object>
                         <object class="org.example.Condition">
                         <field name="transitionName">
                         <string value="Good"/>
                         </field>
                         <field name="expression">
                         <string value="#{varName == true}"/>
                         </field>
                         </object>
                         </list>
                         </field>
                         </handler>
                         <j:transition name="Bad" to="Try again"/>
                         <j:transition name="Good" to="Submit document"/>
                         </j:decision>


                        and my decisionconditionHandler has a variable:

                        List<Condition> conditions;


                        Wkr,
                        Sofie


                        • 9. Re: decision node based on data not in task variables
                          Ronald van Kuijk Master

                          Great, it is kind of a 'hack' but it works and it is a demonstration of the flexibility of jBPM.

                          Don't think (just a little) outside the box, think in an unlimited universe :-)