From 05f69070d87870152f939bcbdc84c593aae67ec5 Mon Sep 17 00:00:00 2001 From: Janne Valkealahti Date: Sun, 9 Aug 2015 09:51:23 +0100 Subject: [PATCH] Change TaskExecutor bean name - Now using stateMachineTaskExecutor instead of taskExecutor so that it's easier to use custom executor and not to collide with bean created i.e. scheduling. - Fixes #83 --- .../StateMachineSystemConstants.java | 3 + .../StateMachineCommonConfiguration.java | 3 +- .../support/StateMachineContextUtils.java | 4 +- .../AbstractStateMachineTests.java | 4 +- .../statemachine/config/ContextTests.java | 160 ++++++++++++++++++ .../config/ManualBuilderTests.java | 5 +- .../src/main/java/demo/tasks/Application.java | 3 +- 7 files changed, 174 insertions(+), 8 deletions(-) create mode 100644 spring-statemachine-core/src/test/java/org/springframework/statemachine/config/ContextTests.java diff --git a/spring-statemachine-core/src/main/java/org/springframework/statemachine/StateMachineSystemConstants.java b/spring-statemachine-core/src/main/java/org/springframework/statemachine/StateMachineSystemConstants.java index 50edab51..5dbc917f 100644 --- a/spring-statemachine-core/src/main/java/org/springframework/statemachine/StateMachineSystemConstants.java +++ b/spring-statemachine-core/src/main/java/org/springframework/statemachine/StateMachineSystemConstants.java @@ -35,4 +35,7 @@ public abstract class StateMachineSystemConstants { /** State machine id key for headers and variables */ public static final String STATEMACHINE_IDENTIFIER = "_sm_id_"; + /** Bean name for task executor */ + public static final String TASK_EXECUTOR_BEAN_NAME = "stateMachineTaskExecutor"; + } diff --git a/spring-statemachine-core/src/main/java/org/springframework/statemachine/config/configuration/StateMachineCommonConfiguration.java b/spring-statemachine-core/src/main/java/org/springframework/statemachine/config/configuration/StateMachineCommonConfiguration.java index 29ddffd8..2a5613e7 100644 --- a/spring-statemachine-core/src/main/java/org/springframework/statemachine/config/configuration/StateMachineCommonConfiguration.java +++ b/spring-statemachine-core/src/main/java/org/springframework/statemachine/config/configuration/StateMachineCommonConfiguration.java @@ -21,6 +21,7 @@ import org.springframework.core.task.SyncTaskExecutor; import org.springframework.core.task.TaskExecutor; import org.springframework.scheduling.TaskScheduler; import org.springframework.scheduling.concurrent.ConcurrentTaskScheduler; +import org.springframework.statemachine.StateMachineSystemConstants; /** * Common configuration for statemachine. @@ -31,7 +32,7 @@ import org.springframework.scheduling.concurrent.ConcurrentTaskScheduler; @Configuration public class StateMachineCommonConfiguration { - @Bean + @Bean(name = StateMachineSystemConstants.TASK_EXECUTOR_BEAN_NAME) public TaskExecutor taskExecutor() { return new SyncTaskExecutor(); } diff --git a/spring-statemachine-core/src/main/java/org/springframework/statemachine/support/StateMachineContextUtils.java b/spring-statemachine-core/src/main/java/org/springframework/statemachine/support/StateMachineContextUtils.java index 061db946..5770b199 100644 --- a/spring-statemachine-core/src/main/java/org/springframework/statemachine/support/StateMachineContextUtils.java +++ b/spring-statemachine-core/src/main/java/org/springframework/statemachine/support/StateMachineContextUtils.java @@ -36,7 +36,7 @@ public class StateMachineContextUtils { public static final String TASK_SCHEDULER_BEAN_NAME = "taskScheduler"; /* Default task executor bean name */ - public static final String TASK_EXECUTOR_BEAN_NAME = "taskExecutor"; + public static final String TASK_EXECUTOR_BEAN_NAME = StateMachineSystemConstants.TASK_EXECUTOR_BEAN_NAME; /* Default conversion service bean name */ public static final String CONVERSION_SERVICE_BEAN_NAME = "cloudClusterConversionService"; @@ -103,7 +103,7 @@ public class StateMachineContextUtils { return getBeanOfType(beanFactory, StateMachineSystemConstants.DEFAULT_ID_EVENT_PUBLISHER, StateMachineEventPublisher.class); } - + /** * Gets a bean from a factory with a given name and type. * diff --git a/spring-statemachine-core/src/test/java/org/springframework/statemachine/AbstractStateMachineTests.java b/spring-statemachine-core/src/test/java/org/springframework/statemachine/AbstractStateMachineTests.java index cb00cdcf..b725daa1 100644 --- a/spring-statemachine-core/src/test/java/org/springframework/statemachine/AbstractStateMachineTests.java +++ b/spring-statemachine-core/src/test/java/org/springframework/statemachine/AbstractStateMachineTests.java @@ -95,7 +95,7 @@ public abstract class AbstractStateMachineTests { @Configuration public static class BaseConfig { - @Bean + @Bean(name = StateMachineSystemConstants.TASK_EXECUTOR_BEAN_NAME) public TaskExecutor taskExecutor() { return new SyncTaskExecutor(); } @@ -110,7 +110,7 @@ public abstract class AbstractStateMachineTests { @Configuration public static class BaseConfig2 { - @Bean + @Bean(name = StateMachineSystemConstants.TASK_EXECUTOR_BEAN_NAME) public TaskExecutor taskExecutor() { ThreadPoolTaskExecutor taskExecutor = new ThreadPoolTaskExecutor(); taskExecutor.setCorePoolSize(5); diff --git a/spring-statemachine-core/src/test/java/org/springframework/statemachine/config/ContextTests.java b/spring-statemachine-core/src/test/java/org/springframework/statemachine/config/ContextTests.java new file mode 100644 index 00000000..978f40e2 --- /dev/null +++ b/spring-statemachine-core/src/test/java/org/springframework/statemachine/config/ContextTests.java @@ -0,0 +1,160 @@ +/* + * Copyright 2015 the original author or authors. + * + * 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.springframework.statemachine.config; + +import static org.hamcrest.Matchers.instanceOf; +import static org.junit.Assert.assertThat; + +import org.junit.Test; +import org.springframework.context.annotation.AnnotationConfigApplicationContext; +import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.Configuration; +import org.springframework.core.task.SyncTaskExecutor; +import org.springframework.core.task.TaskExecutor; +import org.springframework.scheduling.annotation.EnableScheduling; +import org.springframework.scheduling.annotation.Scheduled; +import org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor; +import org.springframework.statemachine.AbstractStateMachineTests; +import org.springframework.statemachine.ObjectStateMachine; +import org.springframework.statemachine.StateMachineSystemConstants; +import org.springframework.statemachine.TestUtils; +import org.springframework.statemachine.config.builders.StateMachineConfigurationConfigurer; +import org.springframework.statemachine.config.builders.StateMachineStateConfigurer; +import org.springframework.statemachine.config.builders.StateMachineTransitionConfigurer; + +public class ContextTests extends AbstractStateMachineTests { + + @Override + protected AnnotationConfigApplicationContext buildContext() { + return new AnnotationConfigApplicationContext(); + } + + @SuppressWarnings("unchecked") + @Test + public void testTaskExecutor() throws Exception { + context.register(Config2.class); + context.refresh(); + ObjectStateMachine machine = + context.getBean(StateMachineSystemConstants.DEFAULT_ID_STATEMACHINE, ObjectStateMachine.class); + assertThat(TestUtils.readField("taskExecutor", machine), instanceOf(SyncTaskExecutor.class)); + } + + @SuppressWarnings("unchecked") + @Test + public void testTaskExecutorWithScheduling() throws Exception { + context.register(Config1.class, Config2.class); + context.refresh(); + ObjectStateMachine machine = + context.getBean(StateMachineSystemConstants.DEFAULT_ID_STATEMACHINE, ObjectStateMachine.class); + assertThat(TestUtils.readField("taskExecutor", machine), instanceOf(SyncTaskExecutor.class)); + } + + @SuppressWarnings("unchecked") + @Test + public void testTaskExecutorOverrideFromBean() throws Exception { + context.register(Config2.class, Config3.class); + context.refresh(); + ObjectStateMachine machine = + context.getBean(StateMachineSystemConstants.DEFAULT_ID_STATEMACHINE, ObjectStateMachine.class); + assertThat(TestUtils.readField("taskExecutor", machine), instanceOf(ThreadPoolTaskExecutor.class)); + } + + @SuppressWarnings("unchecked") + @Test + public void testTaskExecutorOverrideFromConfig() throws Exception { + context.register(Config4.class); + context.refresh(); + ObjectStateMachine machine = + context.getBean(StateMachineSystemConstants.DEFAULT_ID_STATEMACHINE, ObjectStateMachine.class); + assertThat(TestUtils.readField("taskExecutor", machine), instanceOf(ThreadPoolTaskExecutor.class)); + } + + @Configuration + @EnableScheduling + static class Config1 { + + @Scheduled(fixedRate=500) + public void scheduledMethod() { + } + + } + + @Configuration + @EnableStateMachine + static class Config2 extends StateMachineConfigurerAdapter { + + @Override + public void configure(StateMachineStateConfigurer states) throws Exception { + states + .withStates() + .initial("SI") + .state("S1") + .state("S2"); + } + + @Override + public void configure(StateMachineTransitionConfigurer transitions) throws Exception { + transitions + .withExternal() + .source("SI") + .target("S1") + .event("E1"); + } + + } + + @Configuration + static class Config3 { + + @Bean(name = StateMachineSystemConstants.TASK_EXECUTOR_BEAN_NAME) + public TaskExecutor myTaskExecutor() { + return new ThreadPoolTaskExecutor(); + } + + } + + @Configuration + @EnableStateMachine + static class Config4 extends StateMachineConfigurerAdapter { + + @Override + public void configure(StateMachineConfigurationConfigurer config) throws Exception { + config + .withConfiguration() + .taskExecutor(new ThreadPoolTaskExecutor()); + } + + @Override + public void configure(StateMachineStateConfigurer states) throws Exception { + states + .withStates() + .initial("SI") + .state("S1") + .state("S2"); + } + + @Override + public void configure(StateMachineTransitionConfigurer transitions) throws Exception { + transitions + .withExternal() + .source("SI") + .target("S1") + .event("E1"); + } + + } + +} diff --git a/spring-statemachine-core/src/test/java/org/springframework/statemachine/config/ManualBuilderTests.java b/spring-statemachine-core/src/test/java/org/springframework/statemachine/config/ManualBuilderTests.java index a57208b3..fdae2379 100644 --- a/spring-statemachine-core/src/test/java/org/springframework/statemachine/config/ManualBuilderTests.java +++ b/spring-statemachine-core/src/test/java/org/springframework/statemachine/config/ManualBuilderTests.java @@ -29,6 +29,7 @@ import org.springframework.context.SmartLifecycle; import org.springframework.core.task.SyncTaskExecutor; import org.springframework.scheduling.concurrent.ConcurrentTaskScheduler; import org.springframework.statemachine.StateMachine; +import org.springframework.statemachine.StateMachineSystemConstants; import org.springframework.statemachine.config.StateMachineBuilder.Builder; import org.springframework.statemachine.config.builders.StateMachineConfigBuilder; import org.springframework.statemachine.config.builders.StateMachineConfigurationConfig; @@ -56,7 +57,7 @@ public class ManualBuilderTests { stateMachineConfigurationConfig, stateMachineTransitions, stateMachineStates); StaticListableBeanFactory beanFactory = new StaticListableBeanFactory(); - beanFactory.addBean("taskExecutor", new SyncTaskExecutor()); + beanFactory.addBean(StateMachineSystemConstants.TASK_EXECUTOR_BEAN_NAME, new SyncTaskExecutor()); beanFactory.addBean("taskScheduler", new ConcurrentTaskScheduler()); stateMachineFactory.setBeanFactory(beanFactory); @@ -76,7 +77,7 @@ public class ManualBuilderTests { Builder builder = StateMachineBuilder.builder(); StaticListableBeanFactory beanFactory = new StaticListableBeanFactory(); - beanFactory.addBean("taskExecutor", new SyncTaskExecutor()); + beanFactory.addBean(StateMachineSystemConstants.TASK_EXECUTOR_BEAN_NAME, new SyncTaskExecutor()); beanFactory.addBean("taskScheduler", new ConcurrentTaskScheduler()); builder.configureConfiguration() diff --git a/spring-statemachine-samples/tasks/src/main/java/demo/tasks/Application.java b/spring-statemachine-samples/tasks/src/main/java/demo/tasks/Application.java index b83f8343..6641cd8e 100644 --- a/spring-statemachine-samples/tasks/src/main/java/demo/tasks/Application.java +++ b/spring-statemachine-samples/tasks/src/main/java/demo/tasks/Application.java @@ -27,6 +27,7 @@ import org.springframework.core.task.TaskExecutor; import org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor; import org.springframework.shell.Bootstrap; import org.springframework.statemachine.StateContext; +import org.springframework.statemachine.StateMachineSystemConstants; import org.springframework.statemachine.action.Action; import org.springframework.statemachine.annotation.OnTransition; import org.springframework.statemachine.config.EnableStateMachine; @@ -184,7 +185,7 @@ public class Application { } //tag::snippetAE[] - @Bean + @Bean(name = StateMachineSystemConstants.TASK_EXECUTOR_BEAN_NAME) public TaskExecutor taskExecutor() { ThreadPoolTaskExecutor taskExecutor = new ThreadPoolTaskExecutor(); taskExecutor.setCorePoolSize(5);