Я использую Spring State Machine версии 2.0.3 и пытаюсь динамически обновить конфигурацию конечного автомата.У меня есть класс, помеченный @EnableStateMachineFactory
, который предоставляет конфигурацию для StateMachineService
, именно в этом классе я хочу обновить конфигурацию.
Я буду принимать полезную нагрузку JSON, которая содержит состояние ипередача информации и построение конечного автомата из нее.Проблема заключается в том, что, хотя я могу обновить конфигурацию, ничего, требующего, чтобы компонент получил обновленное StateMachineFactory
.Я подозреваю, что контейнер Spring IoC держит ссылку на базовый StateMachineModel
, и поэтому StateMachineFactory
не создается с новой конфигурацией (потому что он считает, что он уже есть).
Мой код для класса конфигурации находится здесь:
@Configuration
@EnableStateMachineFactory(name = "default_factory")
@Service(value = "default_config")
public class StateMachineConfig extends StateMachineConfigurerAdapter<States, String> {
private boolean update = false;
@Override
public void configure(StateMachineTransitionConfigurer<States, String> transitions) throws Exception {
transitions
.withExternal()
.source(INITIAL).target(NEXT).event("INITIAL_NEXT");
if (update) {
// add some new transition
transitions
.withExternal()
.source(HOSPITAL).target(FINAL).event("HOSPITAL_FINAL").action(specialAction());
}
}
public void updateTransition() {
update = !update;
}
...
}
Мой код для класса, который вызывает конфигурацию и пытается перезагрузить фабрику, приведен ниже:
@Service
public class MachineHandler {
private ApplicationContext context;
private DefaultListableBeanFactory beanFactory;
private Map<String, StateMachineService> machineServices = new HashMap<>();
public MachineHandler(ApplicationContext context, DefaultListableBeanFactory beanFactory) {
this.context = context;
this.beanFactory = beanFactory;
}
public void updateMachine() {
StateMachineConfig config = context.getBean("default_config", StateMachineConfig.class);
config.updateTransition();
beanFactory.destroySingleton("default_factory");
StateMachineFactory<States, String> factory = context.getBean("default_factory", StateMachineFactory.class);\
machineServices.put(id, new DefaultStateMachineService<>(factory, persister));
}
public StateMachineService<States, String> getMachine(String id) {
StateMachineService service = machineServices.get(id);
if (service == null) {
String factoryId = id + "_factory";
StateMachineFactory<States, String> factory = context.getBean(factoryId, StateMachineFactory.class);
service = new DefaultStateMachineService<>(factory);
machineServices.put(id, service);
}
return service;
}
}
У кого-нибудь есть идеи?Как перезагрузить фабрику, чтобы она снова вызывала методы конфигурации, и я получал обновленную фабрику всякий раз, когда получал фабричный бин?Или есть другой способ добиться того, что я пытаюсь сделать?