Add event into state context

- This now adds getEvent() into StateContext which
  makes it easier to figure out what caused a transition
  and also makes life easier in actions.
This commit is contained in:
Janne Valkealahti
2015-04-09 12:01:42 +01:00
parent c3891fc482
commit b505016455
5 changed files with 46 additions and 7 deletions

View File

@@ -30,6 +30,14 @@ import org.springframework.statemachine.transition.Transition;
*/
public interface StateContext<S, E> {
/**
* Gets the event associated with a context. Event may be null if transition
* is not triggered by a signal.
*
* @return the event
*/
E getEvent();
/**
* Gets the event message headers.
*

View File

@@ -226,7 +226,7 @@ public abstract class AbstractStateMachine<S, E> extends LifecycleObjectSupport
switchToState(initialState, initialEvent, null, this);
// TODO: for now execute outside of switchToState
if (initialTransition != null) {
StateContext<S, E> stateContext = new DefaultStateContext<S, E>(
StateContext<S, E> stateContext = new DefaultStateContext<S, E>(initialEvent != null ? initialEvent.getPayload() : null,
initialEvent != null ? initialEvent.getHeaders() : null, extendedState, initialTransition, this);
initialTransition.transit(stateContext);
}
@@ -414,7 +414,8 @@ public abstract class AbstractStateMachine<S, E> extends LifecycleObjectSupport
log.trace("Exit state=[" + state + "]");
MessageHeaders messageHeaders = event != null ? event.getHeaders() : new MessageHeaders(
new HashMap<String, Object>());
StateContext<S, E> stateContext = new DefaultStateContext<S, E>(messageHeaders, extendedState, transition, stateMachine);
StateContext<S, E> stateContext = new DefaultStateContext<S, E>(event != null ? event.getPayload() : null,
messageHeaders, extendedState, transition, stateMachine);
State<S, E> findDeep = findDeepParent(transition.getTarget());
boolean isTargetSubOfOtherState = findDeep != null && findDeep != currentState;
@@ -444,7 +445,8 @@ public abstract class AbstractStateMachine<S, E> extends LifecycleObjectSupport
log.trace("Enter state=[" + state + "]");
MessageHeaders messageHeaders = event != null ? event.getHeaders() : new MessageHeaders(
new HashMap<String, Object>());
StateContext<S, E> stateContext = new DefaultStateContext<S, E>(messageHeaders, extendedState, transition, stateMachine);
StateContext<S, E> stateContext = new DefaultStateContext<S, E>(event != null ? event.getPayload() : null,
messageHeaders, extendedState, transition, stateMachine);
if (transition != null) {
State<S, E> findDeep1 = findDeepParent(transition.getTarget());
@@ -571,7 +573,7 @@ public abstract class AbstractStateMachine<S, E> extends LifecycleObjectSupport
// go through candidates and transit max one
for (Transition<S, E> t : trans) {
StateContext<S, E> stateContext = new DefaultStateContext<S, E>(
StateContext<S, E> stateContext = new DefaultStateContext<S, E>(queuedEvent != null ? queuedEvent.getPayload() : null,
queuedEvent != null ? queuedEvent.getHeaders() : null, extendedState, t, this);
if (t == null) {
continue;
@@ -607,7 +609,7 @@ public abstract class AbstractStateMachine<S, E> extends LifecycleObjectSupport
if (sourceState != null && targetState != null) {
MessageHeaders messageHeaders = event != null ? event.getHeaders() : new MessageHeaders(
new HashMap<String, Object>());
StateContext<S, E> stateContext = new DefaultStateContext<S, E>(messageHeaders, extendedState, null, this);
StateContext<S, E> stateContext = new DefaultStateContext<S, E>(event != null ? event.getPayload() : null, messageHeaders, extendedState, null, this);
getStateMachineHandlerResults(getStateMachineHandlers(sourceState, targetState), stateContext);
}
}

View File

@@ -23,6 +23,8 @@ import org.springframework.statemachine.transition.Transition;
public class DefaultStateContext<S, E> implements StateContext<S, E> {
private final E event;
private final MessageHeaders messageHeaders;
private final ExtendedState extendedState;
@@ -31,12 +33,18 @@ public class DefaultStateContext<S, E> implements StateContext<S, E> {
private final StateMachine<S, E> stateMachine;
public DefaultStateContext(MessageHeaders messageHeaders, ExtendedState extendedState, Transition<S,E> transition, StateMachine<S, E> stateMachine) {
public DefaultStateContext(E event, MessageHeaders messageHeaders, ExtendedState extendedState, Transition<S,E> transition, StateMachine<S, E> stateMachine) {
this.event = event;
this.messageHeaders = messageHeaders;
this.extendedState = extendedState;
this.transition = transition;
this.stateMachine = stateMachine;
}
@Override
public E getEvent() {
return event;
}
@Override
public MessageHeaders getMessageHeaders() {

View File

@@ -25,6 +25,8 @@ import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.ApplicationListener;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.messaging.Message;
import org.springframework.messaging.support.MessageBuilder;
import org.springframework.statemachine.AbstractStateMachineTests;
import org.springframework.statemachine.StateContext;
import org.springframework.statemachine.StateMachine;
@@ -313,5 +315,24 @@ public class DocsConfigurationSampleTests extends AbstractStateMachineTests {
public static class Config9 extends EnumStateMachineConfigurerAdapter<States, Events> {
}
// end::snippetN[]
static class DummyShowSendEvent {
// tag::snippetO[]
@Autowired
StateMachine<States, Events> stateMachine;
void signalMachine() {
stateMachine.sendEvent(Events.E1);
Message<Events> message = MessageBuilder
.withPayload(Events.E2)
.setHeader("foo", "bar")
.build();
stateMachine.sendEvent(message);
}
// end::snippetO[]
}
}

View File

@@ -59,7 +59,7 @@ public class SpelExpressionGuardTests extends AbstractStateMachineTests {
Map<String, Object> map = new HashMap<String, Object>();
map.put("foo", "bar");
MessageHeaders headers = new MessageHeaders(map);
DefaultStateContext<TestStates, TestEvents> stateContext = new DefaultStateContext<TestStates, TestEvents>(headers, null, null, null);
DefaultStateContext<TestStates, TestEvents> stateContext = new DefaultStateContext<TestStates, TestEvents>(null, headers, null, null, null);
assertThat(guard.evaluate(stateContext), is(true));
}