  | Mailing List | | Home | | Forum Home | | JBoss - Java Application Server | | Tomcat - JSP/Servlet container | | Struts - A MVC web framework | | iText - An open source PDF Java Library | | JDOM - JDOM XML Parser | | J2EE - A mailing list for Java(tm) 2 Platform, Enterprise Edition | | JSP - A mailing list about Java Server Pages specification and reference | | J2EE Pattern - An interest list for Sun Java Center J2EE Pattern Catalog | | Servlet - A mailing list for discussion about Sun Microsystem's Java Servlet API Technology | |
Struts & Hibernate
|
|
|
  | | | - Actions and async= | - Actions and async= 2007-08-09 - By jeffj55374
Back org.jbpm.JbpmException: token '18547' can't be locked by 'job[18548]' cause it 's already locked by 'token[18547]' Full stack trace, process definition, action handler are all below.
Environment jBPM 3.2.1 | Standalone Java 1.6 (no appserver) | Actions and async="true" don't mix. | JobExecutor is configured for one thread. | Hibernate 3.2.4.sp1 | Oracle 10g | | | Summary: | 1. Token is signaled to start the process. | 2. Token transitions to node1 from the start node. | 3. Node one has an action handler defined so Node.execute(...) calls GraphElement.executeAction() which locks the token. | 4. The action handler calls ctx.leaveNode after it does its work. (Section 9.5 of the user guide states: "Note the difference | between an action that is placed in an event versus an action that is placed in a node. Actions that are put in an event | are executed when the event fires. Actions on events have no way to influence the flow of control of the process. | It is similar to the observer pattern. On the other hand, an action that is put on a node has the responsibility of propagating the execution. | 5. ctx.leaveNode on Node1 ultimately results in Node.enter() being called on Node2 | 6. Since Node2 is an async node, rather than executing the node, the code prepares for an async continuation. | 7. After sending the message the code attempts to lock the token, but it already locked as a result of #3 | // execute the node | if (isAsync) { | ExecuteNodeJob job = createAsyncContinuationJob(token); | MessageService messageService = (MessageService) Services .getCurrentService(Services.SERVICENAME_MESSAGE); | messageService.send(job); | token.lock(job.toString()); // ** THIS IS THE PROBLEM LINE!!!! *** | } else { | execute(executionContext); | } | | The conflict: | Javadoc for Token.lock(): | /** | * locks a process instance for further execution. A locked token | * cannot continue execution. This is a non-persistent | * operation. This is used to prevent tokens being propagated during | * the execution of actions. | * @(protected) #unlock(String) | */ | public void lock(String lockOwnerId) { | | But Section 9.5 of the user's guide says that an action is responsible for propagating the execution, but the token is locked in an attempt to propagate it. | | I'm currently trying to understand the design and come up with a solution to allow my process to run as designed. | What I don't understand yet is why the token is used to prevent propagation or why the code in Node.execute is trying to lock the token with the job id. | Should the code unlock the token and then lock it with the job? Is the token lock really necessary? | If I remove the action fron Node 1, things work fine. | | Possibly related to http://jira.jboss.com/jira/browse/JBPM-983 (See http://BPM-983.ora-code.com). Similar, but a little different twist | | Any ideas? | | Once I research this a little more, I might submit a bug, but I'd like a little feedback to verify that I'm on the right track. | | Thanks for your help. | | Full stack trace: | | org.jbpm.JbpmException: token '18547' can't be locked by 'job[18548]' cause it's already locked by 'token[18547]' | at org.jbpm.graph.exe.Token.lock(Token.java:646) | at org.jbpm.graph.def.Node.enter(Node.java:316) | at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) | at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source) | at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source) | at java.lang.reflect.Method (Unknown Source) | at org.hibernate.proxy.pojo.cglib.CGLIBLazyInitializer  (CGLIBLazyInitializer.java:157) | at org.jbpm.graph.def.Node$$EnhancerByCGLIB$$dc89a302.enter() | at org.jbpm.graph.def.Transition.take(Transition.java:151) | at org.jbpm.graph.def.Node.leave(Node.java:393) | at org.jbpm.graph.def.Node.leave(Node.java:357) | at org.jbpm.graph.exe.ExecutionContext.leaveNode(ExecutionContext.java:120) | at com.digitalriver.mds.jbpm.SampleActionHandler.execute (SampleActionHandler.java:46) | at org.jbpm.graph.def.Action.execute(Action.java:122) | at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) | at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source) | at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source) | at java.lang.reflect.Method (Unknown Source) | at org.hibernate.proxy.pojo.cglib.CGLIBLazyInitializer  (CGLIBLazyInitializer.java:157) | at org.jbpm.graph.def.Action$$EnhancerByCGLIB$$5863de36.execute() | at org.jbpm.graph.def.GraphElement.executeAction(GraphElement.java:255) | at org.jbpm.graph.def.Node.execute(Node.java:338) | at org.jbpm.graph.def.Node.enter(Node.java:318) | at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) | at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source) | at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source) | at java.lang.reflect.Method (Unknown Source) | at org.hibernate.proxy.pojo.cglib.CGLIBLazyInitializer  (CGLIBLazyInitializer.java:157) | at org.jbpm.graph.def.Node$$EnhancerByCGLIB$$dc89a302.enter() | at org.jbpm.graph.def.Transition.take(Transition.java:151) | at org.jbpm.graph.def.Node.leave(Node.java:393) | at org.jbpm.graph.node.StartState.leave(StartState.java:70) | at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) | at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source) | at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source) | at java.lang.reflect.Method (Unknown Source) | at org.hibernate.proxy.pojo.cglib.CGLIBLazyInitializer  (CGLIBLazyInitializer.java:157) | at org.jbpm.graph.def.Node$$EnhancerByCGLIB$$dc89a302.leave() | at org.jbpm.graph.exe.Token.signal(Token.java:194) | at org.jbpm.graph.exe.Token.signal(Token.java:139) | at com.digitalriver.proto.StandaloneSample.runStandaloneSample (StandaloneSample.java:89) | at com.digitalriver.proto.StandaloneSample.run(StandaloneSample.java:130) | at com.digitalriver.proto.StandaloneSample.main(StandaloneSample.java:40) | | | | | The Job Executor bean config | | <bean id="jbpm.job.executor" class="org.jbpm.job.executor.JbpmJobExecutor"> | | <property name="jbpmConfiguration" ref="jbpmConfiguration" /> | | <property name="name" value="JbpmJobExector"/> | | <property name="nbrOfThreads" value="1"/> | | <property name="idleInterval" value="5000"/> | | <property name="maxIdleInterval" value="300000"/> | | <property name="historyMaxSize" value="20"/> | | <property name="maxLockTime" value="600000"/> <!-- 10 minutes --> | | <property name="lockMonitorInterval" value="60000"/> <!-- 1 minute --> | | <property name="lockBufferTime" value="5000"/> <!-- 5 seconds --> | | </bean> | | | The Process Definition | | <?xml version="1.0" encoding="UTF-8 (See http://UTF-8.ora-code.com)"?> | | | | <process-definition | | xmlns="" name="StandaloneSample"> | | <start-state name="start"> | | <transition name="" to="node1"></transition> | | </start-state> | | <end-state name="end1"></end-state> | | <node name="node1"> | | <action class="com.digitalriver.mds.jbpm.SampleActionHandler">< /action> | | <transition name="" to="node2"></transition> | | </node> | | <node async="true" name="node2"> | | <action class="com.digitalriver.mds.jbpm.SampleActionHandler">< /action> | | <transition name="" to="end1"></transition> | | </node> | | </process-definition> | | The action handler | package com.digitalriver.mds.jbpm; | | | | /** Copyright (c) Digital River, Inc. All rights reserved. 2007 | | * Filename: SampleActionHandler.java | | * Author: @(protected) | | */ | | | | | | import java.io.FileWriter ; | | | | import org.apache.commons.logging.Log ; | | import org.apache.commons.logging.LogFactory ; | | import org.jbpm.context.exe.ContextInstance; | | import org.jbpm.graph.def.ActionHandler; | | import org.jbpm.graph.exe.ExecutionContext; | | | | /** | | * @(protected) jpjohnson | | * | | */ | | public class SampleActionHandler | | implements ActionHandler { | | | | /** | | * | | */ | | private static final long serialVersionUID = 1L; | | @(protected)("unused") | | private static final Log log = LogFactory.getLog(SampleActionHandler .class); | | | | /* (non-Javadoc) | | * @(protected) org.jbpm.graph.def.ActionHandler#execute(org.jbpm.graph.exe .ExecutionContext) | | */ | | public void execute(final ExecutionContext ctx) throws Exception | | { | | log.debug("JPJ execute called for task " + ctx.getNode().getName() + | | " action " + ctx.getAction().getName()); | | | | ContextInstance contextInstance = ctx.getProcessInstance() .getContextInstance(); | | Integer id = (Integer) contextInstance.getVariable("MyID"); | | | | FileWriter file = new FileWriter("Node-" + ctx.getNode().getName() + " PI-" + | | ctx.getProcessInstance().getId() + ".txt"); | | file.write("Test output: Process ID " + id); | | file.close(); | | | | ctx.leaveNode(); | | // ctx.getToken().signal(); | | } | | | | } | | | |
View the original post : http://www.jboss.com/index.html?module=bb&op=viewtopic &p=4072679#4072679
Reply to the post : http://www.jboss.com/index.html?module=bb&op=posting&mode =reply&p=4072679 __ ____ ____ ____ ____ ____ ____ ____ ____ ____ jboss-user mailing list jboss-user@(protected) https://lists.jboss.org/mailman/listinfo/jboss-user
|
|
 |