Wakefield Framework SpringBoot+Activiti Workflow Usage

Time:2023-10-11

Introduction: This technology point is mainly for the class approval business process modeling, there can be: task release (i.e., the beginning of the process) to a level of approval to the final end (i.e., the end of the process) a complete set of models

1、idea download activiti plugin

  1. Previous versions of ider downloaded actiBPM, but the new version of ider this plugin is obsolete and has been replaced by the following one

 Wakefield Framework SpringBoot+Activiti Workflow Usage

 Wakefield Framework SpringBoot+Activiti Workflow Usage

2. Start a separate activiti service.

3. Add the dependency in the activiti service:

<dependency>
   <groupId>org.springframework.boot</groupId>
   <artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
   <groupId>org.springframework.boot</groupId>
   <artifactId>spring-boot-starter-jdbc</artifactId>
</dependency>
<dependency>
   <groupId>org.springframework.boot</groupId>
   <artifactId>spring-boot-starter-test</artifactId>
</dependency>
<dependency>
   <groupId>org.activiti</groupId>
   <artifactId>activiti-spring-boot-starter</artifactId>
   <version>7.0.0.Beta2</version>
</dependency>
<dependency>
   <groupId>org.mybatis.spring.boot</groupId>
   <artifactId>mybatis-spring-boot-starter</artifactId>
   <version>2.0.0</version>
</dependency>
<dependency>
   <groupId>mysql</groupId>
   <artifactId>mysql-connector-java</artifactId>
</dependency>
<dependency>
   <groupId>org.projectlombok</groupId>
   <artifactId>lombok</artifactId>
</dependency>

4, Addition arrangement

I have a service structure here:

 Wakefield Framework SpringBoot+Activiti Workflow Usage

a. activiti.cfg.xml configuration (direct paste, need to modify to their own database):

<?xml version=”1.0″ encoding=”UTF-8″?>
<beans xmlns=”http://www.springframework.org/schema/beans”
      xmlns:xsi=”http://www.w3.org/2001/XMLSchema-instance”
      xmlns:context=”http://www.springframework.org/schema/context”
      xmlns:tx=”http://www.springframework.org/schema/tx”
      xsi:schemaLocation=”http://www.springframework.org/schema/beans
                   http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/contex
http://www.springframework.org/schema/context/spring-context.xsd
http://www.springframework.org/schema/tx
http://www.springframework.org/schema/tx/spring-tx.xsd”>
   <!– default (setting)idThe corresponding value isprocessEngineConfiguration –>
   <!– processEngine Activitiprocess engine–>
   <bean id=”processEngineConfiguration”
         class=”org.activiti.engine.impl.cfg.StandaloneProcessEngineConfiguration”>
       <property name=”jdbcDriver” value=”com.mysql.cj.jdbc.Driver”/>
       <property name=”jdbcUrl” value=”jdbc:mysql://*****:3306/activiti”/>
       <property name=”jdbcUsername” value=”root”/>
       <property name=”jdbcPassword” value=”*****”/>
       <!– activitiDatabase table handling strategy Create table if it doesn’t exist–>
       <property name=”databaseSchemaUpdate” value=”true”/>
   </bean>
</beans>

Configuration Explained:

 Wakefield Framework SpringBoot+Activiti Workflow Usage

b. Add log4j configuration (no need to modify, directly stick):

# Set root category priority to INFO and its only appender to CONSOLE.
#log4j.rootCategory=INFO, CONSOLE debug info warn error fatal
log4j.rootCategory=debug, CONSOLE, LOGFILE
# Set the enterprise logger category to FATAL and its only appender to CONSOLE.
log4j.logger.org.apache.axis.enterprise=FATAL, CONSOLE
# CONSOLE is set to be a ConsoleAppender using a PatternLayout.
log4j.appender.CONSOLE=org.apache.log4j.ConsoleAppender
log4j.appender.CONSOLE.layout=org.apache.log4j.PatternLayout
log4j.appender.CONSOLE.layout.ConversionPattern=%d{ISO8601} %-6r[%15.15t] %-5p %30.30c %x – %m\n
# LOGFILE is set to be a File appender using a PatternLayout.
log4j.appender.LOGFILE=org.apache.log4j.FileAppender
log4j.appender.LOGFILE.File=d:\XX\activiti.log
log4j.appender.LOGFILE.Append=true
log4j.appender.LOGFILE.layout=org.apache.log4j.PatternLayout
log4j.appender.LOGFILE.layout.ConversionPattern=%d{ISO8601} %-6r[%15.15t] %-5p %30.30c %x – %m\n

  1. Create a flowchart file:

 Wakefield Framework SpringBoot+Activiti Workflow Usage

Right-click anywhere in the created file and select View BPMN Diagram to open the visualization interface (the interface for process definition).

Wakefield Framework SpringBoot+Activiti Workflow Usage

Arbitrarily right-click and select Define Process:

Wakefield Framework SpringBoot+Activiti Workflow Usage

 Wakefield Framework SpringBoot+Activiti Workflow Usage

 Wakefield Framework SpringBoot+Activiti Workflow Usage

 Wakefield Framework SpringBoot+Activiti Workflow Usage

 Wakefield Framework SpringBoot+Activiti Workflow Usage

Solve the problem of garbled pictures

1. Open the IDEA installation path and find the following installation directory

Wakefield Framework SpringBoot+Activiti Workflow Usage

Additional one-article instruction: -Dfile.encoding=UTF-8
as shown below

Wakefield Framework SpringBoot+Activiti Workflow Usage

This is the end of the activiti preparation, the next is the code part:

I. demo code example:
public class TestCreateTable {
   /**
    * generatingactivitidatabase tables
    */
   @Test
   public void testCreateDbTable() {
       //utilizationclasspathloweractiviti.cfg.xmlThe configuration in theprocessEngine
       //If you use the default, you need the aboveactiviti.cfg.xmldeployment
       ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
       System.out.println(processEngine);
   }

   //deployments
   @Test
   public void test01() {
       //1CreateProcessEngine
       ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
       //2GetRepositoryServicean actual example
       RepositoryService repositoryService = processEngine.getRepositoryService();
       //3Use ofRepositoryServicedeploy
       Deployment deploy = repositoryService.createDeployment().addClasspathResource(“bpmn/chuchai.bpmn20.xml”)
               .addClasspathResource(“bpmn/diagram.png”)
               .name(Group Purchase Applicationv1.0″)
               .deploy();
       //4The output of the deployment information
       System.out.println(deploymentsid+deploy.getId());
       System.out.println(The name of the deployed task:+deploy.getName());
   }

   //Startup process
   @Test
   public void testDeploy() {
       //1.establishProcessEngineboyfriend
       ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
       //establishTaskService
       TaskService taskService = processEngine.getTaskService();

       Map<String, Object> variables = new HashMap<>();
       //Zhang San is the one inbpmnIn theAssigneeConfigured parameters
       variables.put(John Doe, “aaa”);
       //3.Creating a Process Instance The process definition of thekeyneed to know holiday
       ProcessInstance processInstance = ProcessEngines.getDefaultProcessEngine()
               .getRuntimeService()
               .startProcessInstanceByKey(“chuchai”, variables);
       Task tmp = taskService.createTaskQuery()
               .processInstanceId(processInstance.getProcessInstanceId()).singleResult();
       tmp.setAssignee(John Doe);
       //Complete this node. Approved by the next node. Completedact_ru_taskwill create a piece of data that will be approved by the next node
       taskService.complete(tmp.getId(),variables);
       //4.Information about the output example
       System.out.println( Process DeploymentID+ processInstance.getDeploymentId() );
       System.out.println( Process DefinitionID+ processInstance.getProcessDefinitionId());
       System.out.println( Process ExamplesID+ processInstance.getId() );
       System.out.println( maneuverID+ processInstance.getActivityId() );
   }


   @Test
   //Query Tasks
   public void test(){
       ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
       //establishTaskService
       TaskService taskService = processEngine.getTaskService();
       //Based on the processkey and mandate holders Querying of mandates
       List<Task> list = taskService.createTaskQuery()
               .processDefinitionKey(“chuchai”) //workflowsKey
               .taskAssignee(John Doe)//Query only the tasks of this task manager
               .list();

       for (Task task : list) {
           System.out.println(Process Examplesid+ task.getProcessInstanceId());
           System.out.println(mandatesid+ task.getId());
           System.out.println(Mandate holders:+ task.getAssignee());
           System.out.println(Task Name:+ task.getName());
       }

   }

   //Approval Process
   @Test
   public void test1(){
       //1.establishProcessEngineboyfriend
       ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
       //establishTaskService
       TaskService taskService = processEngine.getTaskService();
       //Get your own to-do list based on role information
       List<Task> T = taskService.createTaskQuery().taskAssignee(“zs”).list();
       if(!ObjectUtils.isEmpty(T)) {
           for (Task item : T) {
               Map<String, Object> variables = new HashMap<>();
               variables.put(John Doe, “zs”);
               variables.put(“isSuccess”, true);
               item.setAssignee(the fourth child in the family);
               //Addition of Approval Remarks
               taskService.addComment(item.getId(),item.getProcessInstanceId(),Department Manager Agreed);
               //Complete this approval. Approval by the next node
               taskService.complete(item.getId(), variables);
           }
       }
   }

   // Closing process
   @Test
   public void test02() {
       //1.establishProcessEngineboyfriend
       ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
       //        establishTaskService
       TaskService taskService = processEngine.getTaskService();
       //act_re_execution id
       String taskId = “42503”;
       //        Mandate holders
       String assingee = the fourth child in the family;
       Task task = taskService.createTaskQuery()
               .taskId(taskId)
               .taskAssignee(assingee)
               .singleResult();
       if (task != null) {
           HashMap<String, Object> map = new HashMap<>();
           map.put(“agree”, 1);
           taskService.complete(taskId, map);

           System.out.println(finalize one’s mission);
       }

   }
}

Second, the project code example: controller layer code (here is applied to the project code)


@RestController
@RequestMapping(“/activiti”)
@Slf4j
public class ActivitiController {

   @Autowired
   private IActivitiService iActivitiService;
   //generating25Sheets
   @GetMapping
   public Result getTables(){
       log.info(Start generating tables……………………………………………………….”);
       Result result = iActivitiService.getTable();
       return result;
   }

   //Process Deployment
   @GetMapping(“/bushu”)
   public Result bushu(){
       log.info(deployments “);
       return Result.success(“ok”);

   }

   //Querying an individual’s pending tasks
   @GetMapping(“/list”)
   public Result list(){
       log.info(Querying an individual’s pending tasks);
       Result result = iActivitiService.list();
       return result;
   }

   //close
   @GetMapping(“/complete”)
   public Result complete(){
       log.info(close);
       Result result = iActivitiService.complete();
       return result;
   }
}

Service layer code:


@Service
@Repository
@Slf4j
public class ActivitiServiceImpl implements IActivitiService {

   @Autowired
   public IActivitiMapper iActivitiMapper;

   @Override
   public Result getTable() {
       //utilizationclasspathloweractiviti.cfg.xmlThe configuration in theprocessEngine
       //If you use the default, you need the aboveactiviti.cfg.xmldeployment
       ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
       return Result.success(Generate Table Success);
   }

   @Override
   public Result bushu() {
       //1CreateProcessEngine
       ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
       //2GetRepositoryServicean actual example
       RepositoryService repositoryService = processEngine.getRepositoryService();
       //3Use ofRepositoryServicedeploy
       Deployment deploy = repositoryService.createDeployment().addClasspathResource(“activiti/groupactiviti.bpmn20.xml”)
               .addClasspathResource(“activiti/groupactiviti.png”)
               .name(Group Purchase Application Approval)
               .deploy();
       //4The output of the deployment information
       log.info(deploymentsid+deploy.getId());
       log.info(The name of the deployed task:+deploy.getName());

       //5The process definition is initiated according to the process definition of theidStartup process                           key:act_re_procdefhit the nail on the headKEY
       //establishTaskService
       TaskService taskService = processEngine.getTaskService();

       Map<String, Object> variables = new HashMap<>();
       String username = SecurityUtils.getLoginUser().getSysUser().getUserName();
//        String username = “admin”;
       //userpreciselybpmnIn theAssigneeConfigured parameters
       variables.put(“admin”, username);
       //3.Creating a Process Instance The process definition of thekeyneed to know holiday
       ProcessInstance processInstance = ProcessEngines.getDefaultProcessEngine()
               .getRuntimeService()
               .startProcessInstanceByKey(“groupactiviti”, variables);
       System.out.println(processInstance+“=============================================”);
       Task tmp = taskService.createTaskQuery()
               .processInstanceId(processInstance.getProcessInstanceId()).singleResult();
       tmp.setAssignee(“ry”);
       //Complete this node. Approved by the next node. Completedact_ru_taskwill create a piece of data that will be approved by the next node
       taskService.complete(tmp.getId(),variables);
       //4.Information about the output example
       log.info(Process DeploymentID+ processInstance.getDeploymentId() );
       log.info(Process DefinitionID+ processInstance.getProcessDefinitionId());
       log.info(Process ExamplesID+ processInstance.getId());
       log.info(maneuverID+ processInstance.getActivityId());
       return Result.success(true,Application submitted);
   }

   //Individual pending missions
   @Override
   public Result list() {
       ProcessEngine defaultProcessEngine = ProcessEngines.getDefaultProcessEngine();
       TaskService taskService = defaultProcessEngine.getTaskService();
       // Query the tasks of the current registrant.
       String username= SecurityUtils.getLoginUser().getSysUser().getUserName();
       System.out.println(Currently logged in+username);

       if (username == null){
           throw new CheckedException(The current login is empty);
       }
       List<Task> task = taskService.createTaskQuery()
               .processDefinitionKey(“groupactiviti”)
               .taskAssignee(username)
               .list();
       System.out.println(“===================”+task);
       if(!ObjectUtils.isEmpty(task)) {
           for (Task item : task) {
               Map<String, Object> variables = new HashMap<>();
               if (username.equals(“ry”)){
                   variables.put(“ry”, username);
                   variables.put(“isSuccess”, true);
                   item.setAssignee(“aaa”);
                   //Addition of Approval Remarks
                   taskService.addComment(item.getId(),item.getProcessInstanceId(),The line manager has agreed);
                   //Complete this approval. Approval by the next node  act_hi_taskinstWill change the time
                   taskService.complete(item.getId(), variables);
               }
               if (username.equals(“aaa”)){
                   variables.put(“aaa”, username);
                   variables.put(“isSuccess”, true);
                   item.setAssignee(“aaa”);
                   //Addition of Approval Remarks
                   taskService.addComment(item.getId(),item.getProcessInstanceId(),Finance has been agreed);
                   //Complete this approval. Approval by the next node  act_hi_taskinstWill change the time
                   taskService.complete(item.getId(), variables);
               }
           }
       }
       return Result.success(true,Audit Success);
   }

   // close
   @Override
   public Result complete() {
       //1.establishProcessEngineboyfriend
       ProcessEngine processEngine = ProcessEngines.getDefaultProcessEngine();
       //establishTaskService
       TaskService taskService = processEngine.getTaskService();
       // Get the current login Judge yesadminIt’s the end of the mission.
       String username = SecurityUtils.getLoginUser().getSysUser().getUserName();
//        String username = “aaa”;
       if (username == null) {
           throw new CheckedException(The current login is empty);
       }
       if (username.equals(“aaa”)) {
           //act_re_execution mandatesid
           Task task = taskService.createTaskQuery()
                   .processDefinitionKey(“groupactiviti”)
                   .taskAssignee(username)
                   .singleResult();
           if (task != null) {
               HashMap<String, Object> map = new HashMap<>();
               map.put(“agree”, 1);
               taskService.complete(task.getId(), map);
               System.out.println(finalize one’s mission);
           }
       }
       return Result.success(true,Audit Success);
   }

}

Define a remote call remote for other services to call.

Structure:

Wakefield Framework SpringBoot+Activiti Workflow Usage

  1. ActivitiRemoteFallback code:



/**
* activitiService Degradation Processing
*
* @author 
*/
@Component
public class ActivitiRemoteFallback implements FallbackFactory<ActivitiRemoteService>
{
   private static final Logger log = LoggerFactory.getLogger(ActivitiRemoteFallback.class);

   @Override
   public ActivitiRemoteService create(Throwable cause) {
       log.error(Workflow invocation failure:{}”, cause.getMessage());
       return new ActivitiRemoteService(){


           @Override
           public Result getTables() {
               return null;
           }

           @Override
           public Result bushu() {
               return Result.error(Remote Invocation Workflow Deployment Failure);
           }

           @Override
           public Result list() {
               return Result.error(Remote invocation workflow audit failed);
           }

           @Override
           public Result complete() {
               return Result.error(Remote Call Workflow End Audit Failure);
           }
       };
   }
}

  1. ActivitiRemoteServiceCode:



/**
* customer service
*
* @author bawei
*/
@FeignClient(contextId = “rctivitiRemoteService”,
       value = ServiceNameConstants.**** own filename,
       fallbackFactory = ActivitiRemoteFallback.class,path = “/activiti”)
public interface ActivitiRemoteService {
   //generating25Sheets
   @GetMapping
   public Result getTables();

   //Process Deployment
   @GetMapping(“/bushu”)
   public Result bushu();

   //Querying an individual’s pending tasks
   @GetMapping(“/list”)
   public Result list();
   //close
   @GetMapping(“/complete”)
   public Result complete();
}

  1. org.springframework.boot.autoconfigure.AutoConfiguration.importsConfigured code

Finally: Inject the service directly into Activiti wherever it is needed.

Recommended Today

uniapp and applet set tabBar and show and hide tabBar

(1) Set the tabBar: uni.setTabberItem({}); wx.setTabberItem({}); indexnumberisWhich item of the tabBar, counting from the left, is indexed from 0.textstringnoButton text on tabiconPathstringnoImage PathselectedIconPathstringnoImage path when selectedpagePathstringnoPage absolute pathvisiblebooleannotab Whether to display uni.setTabBarItem({ index: 0, text: ‘text’, iconPath: ‘/path/to/iconPath’, selectedIconPath: ‘/path/to/selectedIconPath’, pagePath: ‘pages/home/home’ }) wx.setTabBarItem({ index: 0, text: ‘text’, iconPath: ‘/path/to/iconPath’, selectedIconPath: ‘/path/to/selectedIconPath’, pagePath: ‘pages/home/home’ }) […]