6 Replies Latest reply on Feb 12, 2008 2:14 AM by kukeltje

    Threads and jbpm

    jcarlos_andia

      Hi.
      I am using jbpm to push a project application but i am stuck when i want to implement states between tasks.

      E.g. I have task1 and taskInstance2 and task2 have to start after x hours task1 finished.

      I place a state between those tasks to prevent task2 starts inmediately after task1 finishes and there is a thread that is checking if the lagTime (x) has been reached in which case the thread signal the state causing the token to move to the next task. The problem come out when I want to get the rootToken children or when i signal a state

      [ConnectionManager] forcing batcher resource cleanup on transaction completion; forgot to close Scrollable Results/Iterator?
      


      The line in which fails is not always the same, understandable considering that threads are involved. Any idea of what is happening? Maybe a suggestion of how to implement this in a different way.

        • 1. Re: Threads and jbpm
          jpechanec

          Hi,

          is not it better to put another state between these two tasks with the timer to implement wait before transition to next task?

          http://docs.jboss.com/jbpm/v3/userguide/scheduler.html#timers

          J.

          • 2. Re: Threads and jbpm
            jcarlos_andia

            Hi J.

            That was my first attempt but since my process definition was created from scratch, by code, no xml in between, had some trouble trying to implement a timer on states. If you know where there is an example of how to implement timers by code please let me know. I have seen the use of JobExecutor too, but not too much documentation so far. Any clue on how to implement this would be highly appreciated. Thanks in advance

            • 3. Re: Threads and jbpm
              kukeltje

              The unittests (in the source in cvs) show many 'examples', including how to create timers by code.

              • 4. Re: Threads and jbpm
                jcarlos_andia

                Thanks for the response kukeltje.

                I have this code for the timer:

                 Calendar cal=Calendar.getInstance();
                 BusinessCalendar bc=new BusinessCalendar();
                 Duration duration=new Duration("60 seconds");
                 Date dueDate=bc.add(cal.getTime(), duration);
                
                 Delegation delegate=new Delegation("com.jotatech.vgrc.action.visual.MyActionHandler");
                 delegate.setProcessDefinition(bpmProject);
                
                 Action myAction=new Action(delegate);
                 myAction.setName("[ACTION]");
                 myAction.setProcessDefinition(bpmProject);
                 bpmProject.addAction(myAction);
                
                 Timer myTimer=new Timer();
                 myTimer.setName("[TIMER] "+myState.getName());
                 myTimer.setDueDate(dueDate);
                 myTimer.setRepeat("3 seconds");
                 myTimer.setRetries(3);
                 myTimer.setGraphElement(myState);
                 myTimer.setAction(myAction);
                 myTimer.setProcessInstance(myProcesInstance);
                
                 log.info("Adding a timer to state {0} with dueDate {1}...",myState,myTimer.getDueDate());
                 jbpmContext.getServices().getSchedulerService().createTimer(myTimer);
                


                And the action:

                public class MyActionHandler implements ActionHandler{
                
                 private static final long serialVersionUID = -7574831777028763706L;
                
                 @Logger
                 private Log log;
                
                 public void execute(ExecutionContext context) throws Exception{
                 log.info("EXECUTING ...");
                 System.out.println("EXECUTING ...");
                 }
                }
                


                The execute method is not called but the retries goes from 3 to 0 when the dueDate is reached. Any clue? I assign the timer to the processInstance, is there any way to assign it to a processDefinition?. Thanks in advance.

                • 5. Re: Threads and jbpm
                  jcarlos_andia

                  Solved. Created the timer within an ActionHandler:

                  First define an event on the state:

                   public void createTimer(State myState){
                   Delegation delegate=new Delegation("com.jotatech.vgrc.action.visual.MyActionHandler");
                  
                   Event myEvent=new Event(Event.EVENTTYPE_NODE_ENTER);
                  
                   Action myAction=new Action(delegate);
                   myAction.setName("[ACTION]");
                  
                   myEvent.addAction(myAction);
                  
                   myState.setAction(myAction);
                   myState.addEvent(myEvent);
                   }
                  


                  Then in the ActionHandler:

                  public class MyActionHandler implements ActionHandler{
                  
                   private static final long serialVersionUID = -7574831777028763706L;
                  
                   public void execute(ExecutionContext context) throws Exception{
                  
                   if(context.getTimer()==null){
                   System.out.println("ADDING TIMER ...");
                   Calendar cal=Calendar.getInstance();
                   BusinessCalendar bc=new BusinessCalendar();
                   Duration duration=new Duration("20 seconds");
                   Date dueDate=bc.add(cal.getTime(), duration);
                  
                   Timer myTimer=new Timer();
                   myTimer.setName("[TIMER] "+context.getEventSource().getName());
                   myTimer.setDueDate(dueDate);
                   myTimer.setRepeat("20 seconds");
                   myTimer.setRetries(3);
                  
                   myTimer.setAction(context.getAction());
                  
                   context.setTimer(myTimer);
                  
                   context.getJbpmContext().getServices().getSchedulerService().createTimer(myTimer);
                   }else{
                   System.out.println("EXECUTING ...");
                   /* CODE YOU WANT THE TIMER TO EXECUTE */
                   }
                   }
                  


                  Hope this helps anybody with the same problem. Question: how can I inject a SEAM component or a Stateful session bean in the timer? I mean: I can't do Component.getInstance("SEAMComponent") or Component.getInstance("MySFSB"). Maybe a way to merge both SEAM and JBPM Contexts? Thanks in advance.

                  • 6. Re: Threads and jbpm
                    kukeltje

                    new questions belong in new topics. That makes them easier to find by others