Activiti supports two main entry points that you need to implement in order to integrate your identity solution. These are the user manager and the group manager classes. We will first create a factory for group/user management, and then implement the class that we create in the factory. Lets take a dive into the code, implementing the MyGroupManagerFactory class first:
1: package my.great.company.com.businessprocessengine.identityservice;
2:
3: import org.activiti.engine.impl.interceptor.Session;
4: import org.activiti.engine.impl.interceptor.SessionFactory;
5: import org.activiti.engine.impl.persistence.entity.GroupManager;
6:
7: public class MyGroupManagerFactory implements SessionFactory {
8:
9: private MyConnectionParams connectionParams;
10:
11: public MyGroupManagerFactory(MyConnectionParams params) {
12: this.connectionParams = params;
13: }
14:
15: @Override
16: public Class<?> getSessionType() {
17: return GroupManager.class;
18: }
19:
20: @Override
21: public Session openSession() {
22: return new MyGroupManager(connectionParams);
23: }
24: }
1: package my.great.company.com.businessprocessengine.identityservice;
2:
3: import org.activiti.engine.impl.interceptor.Session;
4: import org.activiti.engine.impl.interceptor.SessionFactory;
5: import org.activiti.engine.impl.persistence.entity.UserManager;
6:
7: public class MyUserManagerFactory implements SessionFactory {
8:
9: private MyConnectionParams connectionParams;
10:
11: public MyUserManagerFactory(MyConnectionParams params) {
12: this.connectionParams = params;
13: }
14:
15: @Override
16: public Class<?> getSessionType() {
17: return UserManager.class;
18: }
19:
20: @Override
21: public Session openSession() {
22: return new MyUserManager(connectionParams);
23: }
24:
25: }
We now implement MyGroupManager and MyUserManager classes. We did not not detail the entire code, but created an example to show what must be implemented and what you can skip. In MyGroupManager we only implemented the findGroupByQueryCriteria, and findGroupCountByQueryCriteria. Methods that are marked with TODO notation are mandatory in order to work with Activiti core engine. If you want to work with Activity Explorer - implement all the methods.
1: package my.great.company.com.businessprocessengine.identityservice;
2:
3: import java.util.ArrayList;
4: import java.util.List;
5:
6: import org.activiti.engine.ActivitiException;
7: import org.activiti.engine.identity.Group;
8: import org.activiti.engine.impl.GroupQueryImpl;
9: import org.activiti.engine.impl.Page;
10: import org.activiti.engine.impl.persistence.entity.GroupEntity;
11: import org.activiti.engine.impl.persistence.entity.GroupManager;
12: import org.apache.commons.lang.StringUtils;
13:
14: public class MyGroupManager extends GroupManager {
15:
16:
17: public MyGroupManager(MyConnectionParams connectionParams) {
18:
19: }
20:
21: @Override
22: public Group createNewGroup(String groupId) {
23: throw new ActivitiException("My group manager doesn't support creating a new group");
24: }
25:
26: @Override
27: public void insertGroup(Group group) {
28: throw new ActivitiException("My group manager doesn't support inserting a new group");
29: }
30:
31: @Override
32: public void updateGroup(Group updatedGroup) {
33: throw new ActivitiException("My group manager doesn't support updating a new group");
34: }
35:
36: @Override
37: public void deleteGroup(String groupId) {
38: throw new ActivitiException("My group manager doesn't support deleting a new group");
39: }
40:
41: @Override
42: public long findGroupCountByQueryCriteria(Object query) {
43: return findGroupByQueryCriteria(query, null).size();
44: }
45:
46: @Override
47: public List<Group> findGroupByQueryCriteria(Object query, Page page) {
48: List<Group> groupList = new ArrayList<Group>();
49: GroupQueryImpl groupQuery = (GroupQueryImpl) query;
50: if (StringUtils.isNotEmpty(groupQuery.getId())) {
51: GroupEntity singleGroup = findGroupById(groupQuery.getId());
52: groupList.add(singleGroup);
53: return groupList;
54: } else if (StringUtils.isNotEmpty(groupQuery.getName())) {
55: GroupEntity singleGroup = findGroupById(groupQuery.getId());
56: groupList.add(singleGroup);
57: return groupList;
58: } else if (StringUtils.isNotEmpty(groupQuery.getUserId())) {
59: return findGroupsByUser(groupQuery.getUserId());
60: } else {
61: //TODO: get all groups from your identity domain and convert them to List<Group>
62: return null;
63: } //TODO: you can add other search criteria that will allow extended support using the Activiti engine API
64: }
65:
66: @Override
67: public GroupEntity findGroupById(String activitiGroupID) {
68: //TODO
69: throw new ActivitiException("My group manager doesn't support finding a group");
70: }
71:
72: @Override
73: public List<Group> findGroupsByUser(String userLogin) {
74: //TODO
75: throw new ActivitiException("My group manager doesn't support finding a group");
76: }
77: }
1: package my.great.company.com.businessprocessengine.identityservice;
2:
3: import java.util.ArrayList;
4: import java.util.List;
5:
6: import org.activiti.engine.ActivitiException;
7: import org.activiti.engine.identity.User;
8: import org.activiti.engine.impl.Page;
9: import org.activiti.engine.impl.UserQueryImpl;
10: import org.activiti.engine.impl.persistence.entity.UserEntity;
11: import org.activiti.engine.impl.persistence.entity.UserManager;
12: import org.apache.commons.lang.StringUtils;
13:
14: public class MyUserManager extends UserManager {
15:
16: public MyUserManager(MyConnectionParams connectionParams) {
17: }
18:
19: @Override
20: public User createNewUser(String userId) {
21: throw new ActivitiException("My user manager doesn't support creating a new user");
22: }
23:
24: @Override
25: public void insertUser(User user) {
26: throw new ActivitiException("My user manager doesn't support inserting a new user");
27: }
28:
29: @Override
30: public void updateUser(User updatedUser) {
31: throw new ActivitiException("My user manager doesn't support updating a user");
32: }
33:
34: @Override
35: public void deleteUser(String userId) {
36: throw new ActivitiException("My user manager doesn't support deleting a user");
37: }
38:
39: @Override
40: public UserEntity findUserById(String userLogin) {
41: //TODO: get my user according to userLogin and convert it to UserEntity
42: throw new ActivitiException("My user manager doesn't support finding a user");
43: }
44:
45: @Override
46: public List<User> findUserByQueryCriteria(Object query, Page page) {
47:
48: List<User> userList = new ArrayList<User>();
49: UserQueryImpl userQuery = (UserQueryImpl) query;
50: if (StringUtils.isNotEmpty(userQuery.getId())) {
51: userList.add(findUserById(userQuery.getId()));
52: return userList;
53: } else if (StringUtils.isNotEmpty(userQuery.getLastName())) {
54: userList.add(findUserById(userQuery.getLastName()));
55: return userList;
56: } else {
57: //TODO: get all users from your identity domain and convert them to List<User>
58: return null;
59: } //TODO: you can add other search criteria that will allow extended support using the Activiti engine API
60: }
61:
62: @Override
63: public long findUserCountByQueryCriteria(Object query) {
64: return findUserByQueryCriteria(query, null).size();
65: }
66:
67: @Override
68: public Boolean checkPassword(String userId, String password) {
69: //TODO: check the password in your domain and return the appropriate boolean
70: return false;
71: }
72: }
1: <?xml version="1.0" encoding="UTF-8"?>
2: <beans xmlns="http://www.springframework.org/schema/beans"
3: xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
4: xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">
5:
6: <bean id="processEngineConfiguration" class="org.activiti.spring.SpringProcessEngineConfiguration">
7:
8: ...
9: <property name="customSessionFactories">
10: <list>
11: <bean
12: class="my.great.company.com.businessprocessengine.identityservice.MyUserManagerFactory">
13: <constructor-arg ref="MyConnectionParams" />
14: </bean>
15: <bean
16: class="my.great.company.com.businessprocessengine.identityservice.MyGroupManagerFactory">
17: <constructor-arg ref="MyConnectionParams" />
18: </bean>
19: </list>
20: </property>
21: ...
22: </bean>
23:
24: <bean id="MyConnectionParams"
25: class="my.great.company.com.businessprocessengine.identityservice.MyConnectionParams">
26: </bean>
27: ...
28:
29: </beans>
So, here are a few extra pointers about Activiti Identity:
- First of all there are 3 predefined group types:
- activity-role
- assignment
- user
- Now, no one tells you this, but if you are using Activiti Explorer, and you want your user to have admin privileges (i.e. be able to see the 'manage' tab), then the user's group type must be 'security-role' and the user's group name must be hard coded 'admin'. This means you will need to create some special code hacking for special users to use the Activiti Explorer.
- Lets say you created a process that has a user task with a candidate group option (denote said group as X). NOTE: If you start a process instance, than only if the type of the group X is 'assignment' then users that belong to X will be able to claim the task. Otherwise, the user will not be able to claim the task at all.