Location>code7788 >text

Flowable task listener and java-service dependency injection issues

Popularity:586 ℃/2025-04-11 14:23:06

Preface

1. Dependency injection methods for Java service tasks in Flowable, such as using Spring's @Autowired or constructor injection, and ensure that the service task class is managed by Spring.

2. Enable dependency injection and expression parsing related settings in the process engine configuration.

3. Configuration of the asynchronous task executor, ensuring it is integrated with the Spring context, and handling dependency injection beans.

4. Frequently asked questions, such as checking the scope of the bean, whether delegateExpression is used correctly, etc.

5. Possible sample code or configuration snippets to help users understand how to configure correctly.

In addition, users may need to be reminded to pay attention to whether the service task configuration in the process definition file is correct, such as whether expression or delegateExpression is used to reference Spring Beans, or whether Java classes are directly specified, resulting in Spring's dependency injection not taking effect.

Finally, if necessary, you can compare how dependency injection is manually handled in non-Spring environments, but most of the time users may be using Spring, so the focus is on Spring integration.

1. Java service task dependency injection

Scene: In realizationJavaDelegateInject Spring-managed beans (such as Service, Repository) into the class.

Correct configuration method:

  • Step 1: Register the service class as a Spring Bean

@Component("myServiceTask") //Use names to facilitate reference in the process
public class MyServiceTask implements JavaDelegate {
    
    private final MyService myService;

    @Autowired //Constructor injection recommendations
    public MyServiceTask(MyService myService) {
        this.myService = myService;
    }

    @Override
    public void execute(DelegateExecution execution) {
        ();
    }
}
  • Step 2: Reference Beans in Process Definition
    usedelegateExpressionName pointing to Spring Bean:

<serviceTask id="serviceTask1" name="My Task" flowable:delegateExpression="${myServiceTask}" />

Frequently Asked Questions:

  • Bean injection as null

    • Make sure the class is scanned by Spring (located under @ComponentScan path).

    • Check if the process definition is used incorrectlyclassAttributes rather thandelegateExpression

    • Verify that the process engine configuration enables Spring integration.

  • Expression parsing failed
    existFlowableConfigEnable expression parsing and Spring injection in:

@Bean
public SpringProcessEngineConfiguration processEngineConfiguration(DataSource dataSource, PlatformTransactionManager transactionManager) {
    SpringProcessEngineConfiguration config = new SpringProcessEngineConfiguration();
    (dataSource);
    (transactionManager);
    (Flowable.DB_SCHEMA_UPDATE_TRUE);
    (true); //Enable asynchronous executor
    (new SpringExpressionManager(applicationContext, null)); //Enable Spring Expressions
    return config;
}

2. Asynchronous task executor configuration

When the service task is marked asynchronous (flowable:async="true") When the task is processed by the asynchronous executor.

Configure the asynchronous executor:

@Bean
public AsyncExecutor asyncExecutor(DataSource dataSource) {
    DefaultAsyncExecutor asyncExecutor = new DefaultAsyncExecutor();
    (dataSource);
    (5); //Number of core threads
    (10); //Maximum number of threads
    (100); //Task queue size
    return asyncExecutor;
}

existprocessEngineConfigurationEnable in:

(asyncExecutor);
(true);

Key points for asynchronous task dependency injection:

  • Bean scope: Asynchronous tasks may run in new threads to ensure that the injected bean is thread-safe or used@Scope(proxyMode = ScopedProxyMode.TARGET_CLASS)

  • Transaction Management: If an asynchronous task involves database operations, it is required to configure it@TransactionalAnd make sure the transaction is spread correctly.

3. Obtain the ApplicationContext object instance through the ApplicationContextAware interface

Possible error situations include: AsyncExecutorEnabled is not set to true in the process engine configuration, or the injection failure is caused by not using the expression correctly in the service task. In addition, the scope of beans may also lead to the failure of dependency injection.

For example, if the scope of a bean is a prototype, it may require a different approach when injecting. The following is how I get the ApplicationContext object instance through the ApplicationContextAware interface, and then pass ("myService")

Method to get the corresponding bean

@Component
public class MyListener implements TaskListener, ApplicationContextAware {

    private static  ApplicationContext applicationContext;

    @Override
    public void setApplicationContext(ApplicationContext arg0) throws BeansException {
        applicationContext = arg0;
    }

    @Override
    public void notify(DelegateTask delegateTask) {

        String processInsId = ();
        MyService myService = (MyService) ("myService");

        //TODO execute service method
        
        ("==========Execute the listener======");
    }

}

4. Troubleshooting of FAQs

  • Error: Unable to parse expression${myServiceTask}

    • Check if the bean name matches.

    • Confirm that the process engine configuration is setSpringExpressionManager

  • Asynchronous tasks are not executed

    • examineasyncExecutorWhether to start: call()

    • Check whether there are task submission exceptions in the log.

  • The transaction does not take effect

    • Make sure the asynchronous executor is configured with transaction manager: asyncExecutor.setTransactionManager(transactionManager);

5. Spring Boot Integration

If usedflowable-spring-boot-starter, simplified configuration is as follows:

(1)

flowable:
  async-executor-enabled: true
  database-schema-update: true
  async-executor:
    core-pool-size: 5
    max-pool-size: 10
    queue-size: 100

(2) Service Tasks

@Component
public class EmailServiceTask implements JavaDelegate {

    private final EmailService emailService;

    public EmailServiceTask(EmailService emailService) {
        this.emailService = emailService;
    }

    @Override
    public void execute(DelegateExecution execution) {
        String recipient = (String) ("email");
        (recipient, "Process Notification", "Your task has been processed.");
    }
}

(3) Process definition XML

<serviceTask id="sendEmail" flowable:delegateExpression="${emailServiceTask}" />

Summarize

  • Dependency injection: Make sure that the service task class is Spring Bean and used in the processdelegateExpressionQuote.

  • Asynchronous execution:ConfigurationAsyncExecutorAnd enable, pay attention to thread safety and transactions.

  • Obtain ApplicationContext object instance in the ApplicationContextAware interface

  • Spring Integration: Correct configurationSpringProcessEngineConfigurationTo support expressions and bean parsing.