1717package org .springframework .boot .actuate .endpoint .invoker .cache ;
1818
1919import java .security .Principal ;
20+ import java .util .Arrays ;
2021import java .util .Collections ;
2122import java .util .HashMap ;
2223import java .util .Map ;
2324
2425import org .junit .jupiter .api .Test ;
26+ import reactor .core .publisher .Flux ;
27+ import reactor .core .publisher .Mono ;
2528
2629import org .springframework .boot .actuate .endpoint .InvocationContext ;
2730import org .springframework .boot .actuate .endpoint .SecurityContext ;
31+ import org .springframework .boot .actuate .endpoint .invoke .MissingParametersException ;
2832import org .springframework .boot .actuate .endpoint .invoke .OperationInvoker ;
2933
3034import static org .assertj .core .api .Assertions .assertThat ;
3943 * Tests for {@link CachingOperationInvoker}.
4044 *
4145 * @author Stephane Nicoll
46+ * @author Christoph Dreis
47+ * @author Phillip Webb
4248 */
4349class CachingOperationInvokerTests {
4450
@@ -62,6 +68,30 @@ void cacheInTtlWithNullParameters() {
6268 assertCacheIsUsed (parameters );
6369 }
6470
71+ @ Test
72+ void cacheInTtlWithMonoResponse () {
73+ MonoOperationInvoker .invocations = 0 ;
74+ MonoOperationInvoker target = new MonoOperationInvoker ();
75+ InvocationContext context = new InvocationContext (mock (SecurityContext .class ), Collections .emptyMap ());
76+ CachingOperationInvoker invoker = new CachingOperationInvoker (target , 500L );
77+ Object response = ((Mono <?>) invoker .invoke (context )).block ();
78+ Object cachedResponse = ((Mono <?>) invoker .invoke (context )).block ();
79+ assertThat (MonoOperationInvoker .invocations ).isEqualTo (1 );
80+ assertThat (response ).isSameAs (cachedResponse );
81+ }
82+
83+ @ Test
84+ void cacheInTtlWithFluxResponse () {
85+ FluxOperationInvoker .invocations = 0 ;
86+ FluxOperationInvoker target = new FluxOperationInvoker ();
87+ InvocationContext context = new InvocationContext (mock (SecurityContext .class ), Collections .emptyMap ());
88+ CachingOperationInvoker invoker = new CachingOperationInvoker (target , 500L );
89+ Object response = ((Flux <?>) invoker .invoke (context )).blockLast ();
90+ Object cachedResponse = ((Flux <?>) invoker .invoke (context )).blockLast ();
91+ assertThat (FluxOperationInvoker .invocations ).isEqualTo (1 );
92+ assertThat (response ).isSameAs (cachedResponse );
93+ }
94+
6595 private void assertCacheIsUsed (Map <String , Object > parameters ) {
6696 OperationInvoker target = mock (OperationInvoker .class );
6797 Object expected = new Object ();
@@ -122,4 +152,32 @@ void targetInvokedWhenCacheExpires() throws InterruptedException {
122152 verify (target , times (2 )).invoke (context );
123153 }
124154
155+ private static class MonoOperationInvoker implements OperationInvoker {
156+
157+ static int invocations ;
158+
159+ @ Override
160+ public Object invoke (InvocationContext context ) throws MissingParametersException {
161+ return Mono .fromCallable (() -> {
162+ invocations ++;
163+ return Mono .just ("test" );
164+ });
165+ }
166+
167+ }
168+
169+ private static class FluxOperationInvoker implements OperationInvoker {
170+
171+ static int invocations ;
172+
173+ @ Override
174+ public Object invoke (InvocationContext context ) throws MissingParametersException {
175+ return Flux .fromIterable (() -> {
176+ invocations ++;
177+ return Arrays .asList ("spring" , "boot" ).iterator ();
178+ });
179+ }
180+
181+ }
182+
125183}
0 commit comments