提交 7389ed90 编写于 作者: T tombaeyens

ACT-687 Add owner property to tasks

上级 4e54e449
......@@ -9,7 +9,12 @@
<img src="docs/userguide/images/activiti_readme.png"/>
<h1>License</h1>
<p><a href="license.txt">Apache license</a></p>
<p>All the software included in this distribution is distributed under <a href="license.txt">Apache license V2</a>
unless for these exceptions:
</p>
<ul>
<li>We are including slightly modified source code of the Apache Licensed <a href="http://juel.sourceforge.net/" title="JUEL project page">JUEL 2.2.1</a>, created by Odysseus Software GmbH.</li>
</ul>
<h1>Documentation</h1>
<ul>
......@@ -39,9 +44,6 @@
A more elaborate collection of Activiti-links can be found on the
<a href="http://activiti.org/community.html">Activiti Community page</a>
<h1>Remarks</h1>
<p>We are including slightly modified source code of the Apache Licensed <a href="http://juel.sourceforge.net/" title="JUEL project page">JUEL 2.2.1</a>, created by Odysseus Software GmbH.</p>
<h1>Activiti Release Notes</h1>
<h3>Release Notes - Activiti - Version 5.3</h3>
......
......@@ -16,6 +16,7 @@ import java.util.Collection;
import java.util.List;
import java.util.Map;
import org.activiti.engine.task.DelegationState;
import org.activiti.engine.task.IdentityLink;
import org.activiti.engine.task.IdentityLinkType;
import org.activiti.engine.task.Task;
......@@ -88,10 +89,28 @@ public interface TaskService {
/**
* Called when the task is successfully executed.
* @param taskId the id of the task to complete, cannot be null.
* @throws ActivitiException when no task exists with the given id.
* @throws ActivitiException when no task exists with the given id or when this task is {@link DelegationState#PENDING} delegation.
*/
void complete(String taskId);
/**
* Delegates the task to another user. This means that the assignee is set
* and the delegation state is set to {@link DelegationState#PENDING}
* @param taskId The id of the task that will be delegated.
* @param userId The id of the user that will be set as assignee.
* @throws ActivitiException when no task exists with the given id.
*/
void delegateTask(String taskId, String userId);
/**
* Marks that the assignee is done with this task and that it can be send back to the owner.
* Can only be called when this task is {@link DelegationState#PENDING} delegation.
* After this method returns, the {@link Task#getDelegationState() delegationState} is set to {@link DelegationState#RESOLVED}.
* @param taskId the id of the task to resolve, cannot be null.
* @throws ActivitiException when no task exists with the given id.
*/
void resolveTask(String taskId);
/**
* Called when the task is successfully executed,
* and the required task parameters are given by the end-user.
......
......@@ -68,9 +68,6 @@ public interface DelegateTask extends VariableScope {
/** Returns the execution currently at the task. */
DelegateExecution getExecution();
/** Refers to a {@link User.getId() user} which is the owner or person responsible for completing this task. */
String getAssignee();
/** Returns the event name which triggered the task listener to fire for this task. */
String getEventName();
......@@ -86,7 +83,16 @@ public interface DelegateTask extends VariableScope {
/** Adds multiple groups as candidate group to this task. */
void addCandidateGroups(Collection<String> candidateGroups);
/** Sets the current assignee of this task to the given user */
/** The {@link User.getId() userId} of the person responsible for this task. */
String getOwner();
/** The {@link User.getId() userId} of the person responsible for this task.*/
void setOwner(String owner);
/** The {@link User.getId() userId} of the person to which this task is delegated. */
String getAssignee();
/** The {@link User.getId() userId} of the person to which this task is delegated. */
void setAssignee(String assignee);
/**
......
......@@ -22,15 +22,16 @@ import org.activiti.engine.TaskService;
import org.activiti.engine.impl.cmd.AddIdentityLinkCmd;
import org.activiti.engine.impl.cmd.ClaimTaskCmd;
import org.activiti.engine.impl.cmd.CompleteTaskCmd;
import org.activiti.engine.impl.cmd.DelegateTaskCmd;
import org.activiti.engine.impl.cmd.DeleteIdentityLinkCmd;
import org.activiti.engine.impl.cmd.DeleteTaskCmd;
import org.activiti.engine.impl.cmd.GetIdentityLinksForTaskCmd;
import org.activiti.engine.impl.cmd.GetTaskVariableCmd;
import org.activiti.engine.impl.cmd.GetTaskVariablesCmd;
import org.activiti.engine.impl.cmd.DeleteIdentityLinkCmd;
import org.activiti.engine.impl.cmd.ResolveTaskCmd;
import org.activiti.engine.impl.cmd.SaveTaskCmd;
import org.activiti.engine.impl.cmd.SetTaskPriorityCmd;
import org.activiti.engine.impl.cmd.SetTaskVariablesCmd;
import org.activiti.engine.impl.interceptor.CommandExecutor;
import org.activiti.engine.impl.task.TaskEntity;
import org.activiti.engine.task.IdentityLink;
import org.activiti.engine.task.IdentityLinkType;
......@@ -128,6 +129,18 @@ public class TaskServiceImpl extends ServiceImpl implements TaskService {
commandExecutor.execute(new CompleteTaskCmd(taskId, variables));
}
public void delegateTask(String taskId, String userId) {
commandExecutor.execute(new DelegateTaskCmd(taskId, userId));
}
public void resolveTask(String taskId) {
commandExecutor.execute(new ResolveTaskCmd(taskId, null));
}
public void resolve(String taskId, Map<String, Object> variables) {
commandExecutor.execute(new ResolveTaskCmd(taskId, variables));
}
public void setPriority(String taskId, int priority) {
commandExecutor.execute(new SetTaskPriorityCmd(taskId, priority) );
}
......
......@@ -49,9 +49,12 @@ public class CompleteTaskCmd implements Command<Void> {
task.setExecutionVariables(variables);
}
task.complete();
completeTask(task);
return null;
}
protected void completeTask(TaskEntity task) {
task.complete();
}
}
/* 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.activiti.engine.impl.cmd;
import org.activiti.engine.ActivitiException;
import org.activiti.engine.impl.cfg.TaskSession;
import org.activiti.engine.impl.interceptor.Command;
import org.activiti.engine.impl.interceptor.CommandContext;
import org.activiti.engine.impl.task.TaskEntity;
/**
* @author Tom Baeyens
*/
public class DelegateTaskCmd implements Command<Object> {
protected String taskId;
protected String userId;
public DelegateTaskCmd(String taskId, String userId) {
this.taskId = taskId;
this.userId = userId;
}
@Override
public Object execute(CommandContext commandContext) {
if(taskId == null) {
throw new ActivitiException("taskId is null");
}
TaskSession taskSession = commandContext.getTaskSession();
TaskEntity task = taskSession.findTaskById(taskId);
if (task == null) {
throw new ActivitiException("Cannot find task with id " + taskId);
}
task.delegate(userId);
return null;
}
}
/* 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.activiti.engine.impl.cmd;
import java.util.Map;
import org.activiti.engine.impl.task.TaskEntity;
/**
* @author Tom Baeyens
*/
public class ResolveTaskCmd extends CompleteTaskCmd {
public ResolveTaskCmd(String taskId, Map<String, Object> variables) {
super(taskId, variables);
}
@Override
protected void completeTask(TaskEntity task) {
task.resolve();
}
}
......@@ -41,6 +41,7 @@ import org.activiti.engine.impl.runtime.ExecutionEntity;
import org.activiti.engine.impl.runtime.VariableInstanceEntity;
import org.activiti.engine.impl.runtime.VariableScopeImpl;
import org.activiti.engine.impl.util.ClockUtil;
import org.activiti.engine.task.DelegationState;
import org.activiti.engine.task.IdentityLink;
import org.activiti.engine.task.IdentityLinkType;
import org.activiti.engine.task.Task;
......@@ -59,7 +60,10 @@ public class TaskEntity extends VariableScopeImpl implements Task, DelegateTask,
protected String id;
protected int revision;
protected String owner;
protected String assignee;
protected DelegationState delegationState;
protected String name;
protected String description;
protected int priority = Task.PRIORITY_NORMAL;
......@@ -153,7 +157,9 @@ public class TaskEntity extends VariableScopeImpl implements Task, DelegateTask,
}
public void update(TaskEntity task) {
setOwner(task.getOwner());
setAssignee(task.getAssignee());
setDelegationState(task.getDelegationState());
setName(task.getName());
setDescription(task.getDescription());
setPriority(task.getPriority());
......@@ -167,10 +173,21 @@ public class TaskEntity extends VariableScopeImpl implements Task, DelegateTask,
getExecution().signal(null, null);
}
}
public void delegate(String userId) {
setDelegationState(DelegationState.PENDING);
setAssignee(userId);
}
public void resolve() {
setDelegationState(DelegationState.RESOLVED);
setAssignee(this.owner);
}
public Object getPersistentState() {
Map<String, Object> persistentState = new HashMap<String, Object>();
persistentState.put("assignee", this.assignee);
persistentState.put("owner", this.owner);
persistentState.put("name", this.name);
persistentState.put("priority", this.priority);
if (executionId!=null) {
......@@ -589,4 +606,22 @@ public class TaskEntity extends VariableScopeImpl implements Task, DelegateTask,
public void setProcessInstanceId(String processInstanceId) {
this.processInstanceId = processInstanceId;
}
public String getOwner() {
return owner;
}
public void setOwner(String owner) {
this.owner = owner;
}
public DelegationState getDelegationState() {
return delegationState;
}
public void setDelegationState(DelegationState delegationState) {
this.delegationState = delegationState;
}
public String getDelegationStateString() {
return (delegationState!=null ? delegationState.toString() : null);
}
public void setDelegationStateString(String delegationStateString) {
this.delegationState = (delegationStateString!=null ? DelegationState.valueOf(DelegationState.class, delegationStateString) : null);
}
}
/* 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.activiti.engine.task;
/** Defines the different states of delegation that a task can be in.
*
* @author Tom Baeyens
*/
public enum DelegationState {
/**
* The owner delegated the task and wants to review the result
* after the assignee has resolved the task. When the assignee
* completes the task, the task is marked as {@link #RESOLVED} and
* sent back to the owner. When that happens, the owner is set as
* the assignee so that the owner gets this task back in the ToDo.
*/
PENDING,
/**
* The assignee has resolved the task, the assignee was set to the owner
* again and the owner now finds this task back in the ToDo list for review.
* The owner now is able to complete the task.
*/
RESOLVED
}
......@@ -52,11 +52,23 @@ public interface Task {
void setPriority(int priority);
/** The {@link User.getId() userId} of the person that is responsible for this task. */
String getOwner();
/** The {@link User.getId() userId} of the person that is responsible for this task. */
void setOwner(String owner);
/** The {@link User.getId() userId} of the person to which this task is delegated. */
String getAssignee();
/** The {@link User.getId() userId} of the person that is responsible for this task. */
/** The {@link User.getId() userId} of the person to which this task is delegated. */
void setAssignee(String assignee);
/** The current {@link DelegationState} for this task. */
DelegationState getDelegationState();
/** The current {@link DelegationState} for this task. */
void setDelegationState(DelegationState delegationState);
/** Reference to the process instance or null if it is not related to a process instance. */
String getProcessInstanceId();
......@@ -71,4 +83,7 @@ public interface Task {
/** The id of the activity in the process defining this task or null if this is not related to a process */
String getTaskDefinitionKey();
/** delegates this task to the given user and sets the {@link #getDelegationState() delegationState} to {@link DelegationState#PENDING}. */
void delegate(String userId);
}
......@@ -88,7 +88,9 @@ create table ACT_RU_TASK (
NAME_ varchar(255),
DESCRIPTION_ varchar(255),
TASK_DEF_KEY_ varchar(255),
OWNER_ varchar(64),
ASSIGNEE_ varchar(64),
DELEGATION_ varchar(64),
PRIORITY_ integer,
CREATE_TIME_ timestamp,
primary key (ID_)
......
......@@ -86,7 +86,9 @@ create table ACT_RU_TASK (
NAME_ varchar(255),
DESCRIPTION_ varchar(255),
TASK_DEF_KEY_ varchar(255),
OWNER_ varchar(64),
ASSIGNEE_ varchar(64),
DELEGATION_ varchar(64),
PRIORITY_ integer,
CREATE_TIME_ timestamp,
primary key (ID_)
......
......@@ -86,7 +86,9 @@ create table ACT_RU_TASK (
NAME_ nvarchar(255),
DESCRIPTION_ nvarchar(255),
TASK_DEF_KEY_ nvarchar(255),
OWNER_ nvarchar(64),
ASSIGNEE_ nvarchar(64),
DELEGATION_ nvarchar(64),
PRIORITY_ int,
CREATE_TIME_ datetime,
primary key (ID_)
......
......@@ -87,7 +87,9 @@ create table ACT_RU_TASK (
NAME_ varchar(255),
DESCRIPTION_ varchar(255),
TASK_DEF_KEY_ varchar(255),
OWNER_ varchar(64),
ASSIGNEE_ varchar(64),
DELEGATION_ varchar(64),
PRIORITY_ integer,
CREATE_TIME_ timestamp,
primary key (ID_)
......
......@@ -86,7 +86,9 @@ create table ACT_RU_TASK (
NAME_ NVARCHAR2(255),
DESCRIPTION_ NVARCHAR2(255),
TASK_DEF_KEY_ NVARCHAR2(255),
OWNER_ NVARCHAR2(64),
ASSIGNEE_ NVARCHAR2(64),
DELEGATION_ NVARCHAR2(64),
PRIORITY_ INTEGER,
CREATE_TIME_ TIMESTAMP(6),
primary key (ID_)
......
......@@ -87,7 +87,9 @@ create table ACT_RU_TASK (
NAME_ varchar(255),
DESCRIPTION_ varchar(255),
TASK_DEF_KEY_ varchar(255),
OWNER_ varchar(64),
ASSIGNEE_ varchar(64),
DELEGATION_ varchar(64),
PRIORITY_ integer,
CREATE_TIME_ timestamp,
primary key (ID_)
......
......@@ -7,15 +7,17 @@
<!-- TASK INSERT -->
<insert id="insertTask" parameterType="org.activiti.engine.impl.task.TaskEntity">
insert into ACT_RU_TASK (ID_, REV_, NAME_, DESCRIPTION_, PRIORITY_, CREATE_TIME_,
ASSIGNEE_, EXECUTION_ID_, PROC_INST_ID_, PROC_DEF_ID_, TASK_DEF_KEY_)
insert into ACT_RU_TASK (ID_, REV_, NAME_, DESCRIPTION_, PRIORITY_, CREATE_TIME_, OWNER_,
ASSIGNEE_, DELEGATION_, EXECUTION_ID_, PROC_INST_ID_, PROC_DEF_ID_, TASK_DEF_KEY_)
values (#{id, jdbcType=VARCHAR},
1,
#{name, jdbcType=VARCHAR},
#{description, jdbcType=VARCHAR},
#{priority, jdbcType=INTEGER},
#{createTime, jdbcType=TIMESTAMP},
#{owner, jdbcType=VARCHAR},
#{assignee, jdbcType=VARCHAR},
#{delegationStateString, jdbcType=VARCHAR},
#{executionId, jdbcType=VARCHAR},
#{processInstanceId, jdbcType=VARCHAR},
#{processDefinitionId, jdbcType=VARCHAR},
......@@ -32,7 +34,9 @@
NAME_ = #{name, jdbcType=VARCHAR},
PRIORITY_ = #{priority, jdbcType=INTEGER},
CREATE_TIME_ = #{createTime, jdbcType=TIMESTAMP},
OWNER_ = #{owner, jdbcType=VARCHAR},
ASSIGNEE_ = #{assignee, jdbcType=VARCHAR},
DELEGATION_ = #{delegationStateString, jdbcType=VARCHAR},
EXECUTION_ID_ = #{executionId, jdbcType=VARCHAR},
DESCRIPTION_ = #{description, jdbcType=VARCHAR}
</set>
......@@ -54,7 +58,9 @@
<result property="description" column="DESCRIPTION_" jdbcType="VARCHAR"/>
<result property="priority" column="PRIORITY_" jdbcType="INTEGER"/>
<result property="createTime" column="CREATE_TIME_" jdbcType="TIMESTAMP" />
<result property="owner" column="OWNER_" jdbcType="VARCHAR"/>
<result property="assigneeWithoutFireEvent" column="ASSIGNEE_" jdbcType="VARCHAR"/>
<result property="delegationStateString" column="DELEGATION_" jdbcType="VARCHAR"/>
<result property="executionId" column="EXECUTION_ID_" jdbcType="VARCHAR" />
<result property="processInstanceId" column="PROC_INST_ID_" jdbcType="VARCHAR" />
<result property="processDefinitionId" column="PROC_DEF_ID_" jdbcType="VARCHAR"/>
......
......@@ -25,6 +25,7 @@ import org.activiti.engine.identity.User;
import org.activiti.engine.impl.cfg.ProcessEngineConfigurationImpl;
import org.activiti.engine.impl.test.PluggableActivitiTestCase;
import org.activiti.engine.runtime.ProcessInstance;
import org.activiti.engine.task.DelegationState;
import org.activiti.engine.task.IdentityLink;
import org.activiti.engine.task.Task;
import org.activiti.engine.task.IdentityLinkType;
......@@ -63,6 +64,90 @@ public class TaskServiceTest extends PluggableActivitiTestCase {
taskService.deleteTask(task.getId(), true);
}
public void testTaskOwner() {
Task task = taskService.newTask();
task.setOwner("johndoe");
taskService.saveTask(task);
// Fetch the task again and update
task = taskService.createTaskQuery().taskId(task.getId()).singleResult();
assertEquals("johndoe", task.getOwner());
task.setOwner("joesmoe");
taskService.saveTask(task);
task = taskService.createTaskQuery().taskId(task.getId()).singleResult();
assertEquals("joesmoe", task.getOwner());
// Finally, delete task
taskService.deleteTask(task.getId(), true);
}
public void testTaskDelegation() {
Task task = taskService.newTask();
task.setOwner("johndoe");
task.delegate("joesmoe");
taskService.saveTask(task);
String taskId = task.getId();
task = taskService.createTaskQuery().taskId(taskId).singleResult();
assertEquals("johndoe", task.getOwner());
assertEquals("joesmoe", task.getAssignee());
assertEquals(DelegationState.PENDING, task.getDelegationState());
taskService.resolveTask(taskId);
task = taskService.createTaskQuery().taskId(taskId).singleResult();
assertEquals("johndoe", task.getOwner());
assertEquals("johndoe", task.getAssignee());
assertEquals(DelegationState.RESOLVED, task.getDelegationState());
task.setAssignee(null);
task.setDelegationState(null);
taskService.saveTask(task);
task = taskService.createTaskQuery().taskId(taskId).singleResult();
assertEquals("johndoe", task.getOwner());
assertNull(task.getAssignee());
assertNull(task.getDelegationState());
task.setAssignee("jackblack");
task.setDelegationState(DelegationState.RESOLVED);
taskService.saveTask(task);
task = taskService.createTaskQuery().taskId(taskId).singleResult();
assertEquals("johndoe", task.getOwner());
assertEquals("jackblack", task.getAssignee());
assertEquals(DelegationState.RESOLVED, task.getDelegationState());
// Finally, delete task
taskService.deleteTask(taskId, true);
}
public void testTaskDelegationThroughServiceCall() {
Task task = taskService.newTask();
task.setOwner("johndoe");
taskService.saveTask(task);
String taskId = task.getId();
// Fetch the task again and update
task = taskService.createTaskQuery().taskId(taskId).singleResult();
taskService.delegateTask(taskId, "joesmoe");
task = taskService.createTaskQuery().taskId(taskId).singleResult();
assertEquals("johndoe", task.getOwner());
assertEquals("joesmoe", task.getAssignee());
assertEquals(DelegationState.PENDING, task.getDelegationState());
taskService.resolveTask(taskId);
task = taskService.createTaskQuery().taskId(taskId).singleResult();
assertEquals("johndoe", task.getOwner());
assertEquals("johndoe", task.getAssignee());
assertEquals(DelegationState.RESOLVED, task.getDelegationState());
// Finally, delete task
taskService.deleteTask(taskId, true);
}
public void testTaskAssignee() {
Task task = taskService.newTask();
task.setAssignee("johndoe");
......
......@@ -45,7 +45,7 @@ public class ManagementServiceTest extends PluggableActivitiTestCase {
public void testGetTableMetaData() {
TableMetaData tableMetaData = managementService.getTableMetaData("ACT_RU_TASK");
assertEquals(tableMetaData.getColumnNames().size(), tableMetaData.getColumnTypes().size());
assertEquals(11, tableMetaData.getColumnNames().size());
assertEquals(13, tableMetaData.getColumnNames().size());
int assigneeIndex = tableMetaData.getColumnNames().indexOf("ASSIGNEE_");
int createTimeIndex = tableMetaData.getColumnNames().indexOf("CREATE_TIME_");
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册