@@ -18,6 +18,7 @@ package demo.turnstilereactive;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.messaging.support.MessageBuilder;
|
||||
import org.springframework.statemachine.StateMachine;
|
||||
import org.springframework.statemachine.StateMachineEventResult;
|
||||
import org.springframework.statemachine.StateMachineEventResult.ResultType;
|
||||
import org.springframework.web.bind.annotation.GetMapping;
|
||||
import org.springframework.web.bind.annotation.PostMapping;
|
||||
@@ -32,22 +33,28 @@ import reactor.core.publisher.Mono;
|
||||
@RestController
|
||||
public class StateMachineController {
|
||||
|
||||
//tag::snippetA[]
|
||||
@Autowired
|
||||
private StateMachine<States, Events> stateMachine;
|
||||
//end::snippetA[]
|
||||
|
||||
//tag::snippetB[]
|
||||
@GetMapping("/state")
|
||||
public Mono<States> state() {
|
||||
return Mono.justOrEmpty(stateMachine.getState().getId());
|
||||
return Mono.defer(() -> Mono.justOrEmpty(stateMachine.getState().getId()));
|
||||
}
|
||||
//end::snippetB[]
|
||||
|
||||
@PostMapping("/event")
|
||||
public Flux<ResultType> event(@RequestBody Mono<EventData> eventData) {
|
||||
//tag::snippetC[]
|
||||
@PostMapping("/events")
|
||||
public Flux<EventResult> events(@RequestBody Flux<EventData> eventData) {
|
||||
return eventData
|
||||
.filter(ed -> ed.getEvent() != null)
|
||||
.map(ed -> MessageBuilder.withPayload(ed.getEvent()).build())
|
||||
.flatMapMany(m -> stateMachine.sendEvent(Mono.just(m)))
|
||||
.map(r -> r.getResultType());
|
||||
.flatMap(m -> stateMachine.sendEvent(Mono.just(m)))
|
||||
.map(EventResult::new);
|
||||
}
|
||||
//end::snippetC[]
|
||||
|
||||
public static class EventData {
|
||||
private Events event;
|
||||
@@ -60,4 +67,21 @@ public class StateMachineController {
|
||||
this.event = event;
|
||||
}
|
||||
}
|
||||
|
||||
public static class EventResult {
|
||||
|
||||
private final StateMachineEventResult<States, Events> result;
|
||||
|
||||
EventResult(StateMachineEventResult<States, Events> result) {
|
||||
this.result = result;
|
||||
}
|
||||
|
||||
public ResultType getResultType() {
|
||||
return result.getResultType();
|
||||
}
|
||||
|
||||
public Events getEvent() {
|
||||
return result.getMessage().getPayload();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -45,17 +45,50 @@ public class TurnstileReactiveTests {
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testEvent() {
|
||||
webClient.post().uri("/event").contentType(MediaType.APPLICATION_JSON)
|
||||
.body(Mono.just("{\"event\":\"PUSH\"}"), String.class).exchange()
|
||||
.expectBody(String.class).value(containsString("DENIED"));
|
||||
webClient.post().uri("/event").contentType(MediaType.APPLICATION_JSON)
|
||||
.body(Mono.just("{\"event\":\"COIN\"}"), String.class).exchange()
|
||||
.expectBody(String.class).value(containsString("ACCEPTED"));
|
||||
webClient.get().uri("/state").exchange()
|
||||
.expectBody(String.class).value(containsString("UNLOCKED"));
|
||||
webClient.post().uri("/event").contentType(MediaType.APPLICATION_JSON)
|
||||
.body(Mono.just("{\"event\":null}"), String.class).exchange()
|
||||
.expectBody(String.class).value(containsString("[]"));
|
||||
public void testPushDenied() {
|
||||
webClient.post().uri("/events")
|
||||
.contentType(MediaType.APPLICATION_JSON)
|
||||
.body(Mono.just("{\"event\":\"PUSH\"}"), String.class)
|
||||
.exchange()
|
||||
.expectBody()
|
||||
.jsonPath("$.length()").isEqualTo(1)
|
||||
.jsonPath("$[0].event").isEqualTo("PUSH")
|
||||
.jsonPath("$[0].resultType").isEqualTo("DENIED");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testCoinAccepted() {
|
||||
webClient.post().uri("/events")
|
||||
.contentType(MediaType.APPLICATION_JSON)
|
||||
.body(Mono.just("{\"event\":\"COIN\"}"), String.class)
|
||||
.exchange()
|
||||
.expectBody()
|
||||
.jsonPath("$.length()").isEqualTo(1)
|
||||
.jsonPath("$[0].event").isEqualTo("COIN")
|
||||
.jsonPath("$[0].resultType").isEqualTo("ACCEPTED");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testNullEvent() {
|
||||
webClient.post().uri("/events")
|
||||
.contentType(MediaType.APPLICATION_JSON)
|
||||
.body(Mono.just("{\"event\":null}"), String.class)
|
||||
.exchange()
|
||||
.expectBody()
|
||||
.jsonPath("$.length()").isEqualTo(0);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testCoinPushAccepted() {
|
||||
webClient.post().uri("/events")
|
||||
.contentType(MediaType.APPLICATION_JSON)
|
||||
.body(Mono.just("[{\"event\":\"COIN\"},{\"event\":\"PUSH\"}]"), String.class)
|
||||
.exchange()
|
||||
.expectBody()
|
||||
.jsonPath("$.length()").isEqualTo(2)
|
||||
.jsonPath("$[0].event").isEqualTo("COIN")
|
||||
.jsonPath("$[0].resultType").isEqualTo("ACCEPTED")
|
||||
.jsonPath("$[1].event").isEqualTo("PUSH")
|
||||
.jsonPath("$[1].resultType").isEqualTo("ACCEPTED");
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,35 @@
|
||||
### to ease using vscode rest-client extension
|
||||
GET http://localhost:8080/state
|
||||
###
|
||||
POST http://localhost:8080/events
|
||||
content-type: application/json
|
||||
|
||||
{
|
||||
"event": "PUSH"
|
||||
}
|
||||
###
|
||||
POST http://localhost:8080/events
|
||||
content-type: application/json
|
||||
|
||||
{
|
||||
"event": "COIN"
|
||||
}
|
||||
###
|
||||
POST http://localhost:8080/events
|
||||
content-type: application/json
|
||||
|
||||
{
|
||||
"event": "PUSH"
|
||||
}
|
||||
###
|
||||
POST http://localhost:8080/events
|
||||
|
||||
content-type: application/json
|
||||
[
|
||||
{
|
||||
"event": "COIN"
|
||||
},
|
||||
{
|
||||
"event": "PUSH"
|
||||
}
|
||||
]
|
||||
Reference in New Issue
Block a user