Fix issues in RSocketMessageHandler initialization

This commit ensures getRSocketStrategies() now reflects the state of
corresponding RSocketMessageHandler properties even if those change
after a call to setRSocketStrategies.

RSocketMessageHandler has default Encoder/Decoder initializations
consistent with the recent changes to RSocketStrategies.
This commit is contained in:
Rossen Stoyanchev
2019-07-24 17:39:31 +01:00
parent 2bb510588d
commit 88016d47d0
6 changed files with 289 additions and 37 deletions

View File

@@ -0,0 +1,102 @@
/*
* Copyright 2002-2019 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
*
* https://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.messaging.rsocket;
import org.junit.Test;
import org.springframework.core.ReactiveAdapterRegistry;
import org.springframework.core.codec.ByteArrayDecoder;
import org.springframework.core.codec.ByteArrayEncoder;
import org.springframework.core.codec.ByteBufferDecoder;
import org.springframework.core.codec.ByteBufferEncoder;
import org.springframework.core.codec.CharSequenceEncoder;
import org.springframework.core.codec.DataBufferDecoder;
import org.springframework.core.codec.DataBufferEncoder;
import org.springframework.core.codec.StringDecoder;
import org.springframework.util.AntPathMatcher;
import org.springframework.util.SimpleRouteMatcher;
import static org.assertj.core.api.Assertions.assertThat;
/**
* Unit tests for {@link RSocketStrategies}.
* @author Rossen Stoyanchev
* @since 5.2
*/
public class DefaultRSocketStrategiesTests {
@Test
public void defaultSettings() {
RSocketStrategies strategies = RSocketStrategies.create();
assertThat(strategies.encoders()).hasSize(4).hasOnlyElementsOfTypes(
CharSequenceEncoder.class,
ByteArrayEncoder.class,
ByteBufferEncoder.class,
DataBufferEncoder.class);
assertThat(strategies.decoders()).hasSize(4).hasOnlyElementsOfTypes(
StringDecoder.class,
ByteArrayDecoder.class,
ByteBufferDecoder.class,
DataBufferDecoder.class);
assertThat(strategies.routeMatcher()).isNotNull();
assertThat(strategies.metadataExtractor()).isNotNull();
assertThat(strategies.reactiveAdapterRegistry()).isNotNull();
}
@Test
public void explicitValues() {
SimpleRouteMatcher matcher = new SimpleRouteMatcher(new AntPathMatcher());
DefaultMetadataExtractor extractor = new DefaultMetadataExtractor();
ReactiveAdapterRegistry registry = new ReactiveAdapterRegistry();
RSocketStrategies strategies = RSocketStrategies.builder()
.encoders(encoders -> {
encoders.clear();
encoders.add(new ByteArrayEncoder());
})
.decoders(decoders -> {
decoders.clear();
decoders.add(new ByteArrayDecoder());
})
.routeMatcher(matcher)
.metadataExtractor(extractor)
.reactiveAdapterStrategy(registry)
.build();
assertThat(strategies.encoders()).hasSize(1);
assertThat(strategies.decoders()).hasSize(1);
assertThat(strategies.routeMatcher()).isSameAs(matcher);
assertThat(strategies.metadataExtractor()).isSameAs(extractor);
assertThat(strategies.reactiveAdapterRegistry()).isSameAs(registry);
}
@Test
public void copyConstructor() {
RSocketStrategies strategies1 = RSocketStrategies.create();
RSocketStrategies strategies2 = strategies1.mutate().build();
assertThat(strategies1.encoders()).hasSameElementsAs(strategies2.encoders());
assertThat(strategies1.decoders()).hasSameElementsAs(strategies2.decoders());
assertThat(strategies1.routeMatcher()).isSameAs(strategies2.routeMatcher());
assertThat(strategies1.metadataExtractor()).isSameAs(strategies2.metadataExtractor());
assertThat(strategies1.reactiveAdapterRegistry()).isSameAs(strategies2.reactiveAdapterRegistry());
}
}

View File

@@ -16,18 +16,28 @@
package org.springframework.messaging.rsocket.annotation.support;
import java.util.Collections;
import java.util.List;
import java.util.Map;
import io.rsocket.frame.FrameType;
import org.junit.Test;
import org.springframework.core.ReactiveAdapterRegistry;
import org.springframework.core.codec.ByteArrayDecoder;
import org.springframework.core.codec.ByteArrayEncoder;
import org.springframework.core.codec.ByteBufferDecoder;
import org.springframework.core.codec.ByteBufferEncoder;
import org.springframework.core.codec.CharSequenceEncoder;
import org.springframework.core.codec.DataBufferDecoder;
import org.springframework.core.codec.DataBufferEncoder;
import org.springframework.core.codec.StringDecoder;
import org.springframework.messaging.Message;
import org.springframework.messaging.handler.CompositeMessageCondition;
import org.springframework.messaging.handler.DestinationPatternsMessageCondition;
import org.springframework.messaging.handler.HandlerMethod;
import org.springframework.messaging.handler.annotation.MessageMapping;
import org.springframework.messaging.rsocket.DefaultMetadataExtractor;
import org.springframework.messaging.rsocket.RSocketStrategies;
import org.springframework.messaging.rsocket.annotation.ConnectMapping;
import org.springframework.messaging.support.MessageBuilder;
import org.springframework.messaging.support.MessageHeaderAccessor;
@@ -46,6 +56,108 @@ import static org.assertj.core.api.Assertions.assertThatThrownBy;
*/
public class RSocketMessageHandlerTests {
@Test
public void rsocketStrategiesInitializedFromOtherProperties() {
RSocketMessageHandler handler = new RSocketMessageHandler();
handler.setDecoders(Collections.singletonList(new ByteArrayDecoder()));
handler.setEncoders(Collections.singletonList(new ByteArrayEncoder()));
handler.setRouteMatcher(new SimpleRouteMatcher(new AntPathMatcher()));
handler.setMetadataExtractor(new DefaultMetadataExtractor());
handler.setReactiveAdapterRegistry(new ReactiveAdapterRegistry());
handler.afterPropertiesSet();
RSocketStrategies strategies = handler.getRSocketStrategies();
assertThat(strategies).isNotNull();
assertThat(strategies.encoders()).isEqualTo(handler.getEncoders());
assertThat(strategies.decoders()).isEqualTo(handler.getDecoders());
assertThat(strategies.routeMatcher()).isSameAs(handler.getRouteMatcher());
assertThat(strategies.metadataExtractor()).isSameAs(handler.getMetadataExtractor());
assertThat(strategies.reactiveAdapterRegistry()).isSameAs(handler.getReactiveAdapterRegistry());
}
@Test
public void rsocketStrategiesInitializedFromDefaults() {
RSocketMessageHandler handler = new RSocketMessageHandler();
handler.afterPropertiesSet();
RSocketStrategies strategies = handler.getRSocketStrategies();
assertThat(strategies).isNotNull();
assertThat(strategies.encoders()).hasSize(4).hasOnlyElementsOfTypes(
CharSequenceEncoder.class,
ByteArrayEncoder.class,
ByteBufferEncoder.class,
DataBufferEncoder.class);
assertThat(strategies.decoders()).hasSize(4).hasOnlyElementsOfTypes(
StringDecoder.class,
ByteArrayDecoder.class,
ByteBufferDecoder.class,
DataBufferDecoder.class);
assertThat(strategies.routeMatcher()).isSameAs(handler.getRouteMatcher()).isNotNull();
assertThat(strategies.metadataExtractor()).isSameAs(handler.getMetadataExtractor()).isNotNull();
assertThat(strategies.reactiveAdapterRegistry()).isSameAs(handler.getReactiveAdapterRegistry()).isNotNull();
}
@Test
public void rsocketStrategiesSetsOtherProperties() {
RSocketStrategies strategies = RSocketStrategies.builder()
.encoders(List::clear)
.decoders(List::clear)
.encoders(encoders -> encoders.add(new ByteArrayEncoder()))
.decoders(decoders -> decoders.add(new ByteArrayDecoder()))
.routeMatcher(new SimpleRouteMatcher(new AntPathMatcher()))
.metadataExtractor(new DefaultMetadataExtractor())
.reactiveAdapterStrategy(new ReactiveAdapterRegistry())
.build();
RSocketMessageHandler handler = new RSocketMessageHandler();
handler.setRSocketStrategies(strategies);
handler.afterPropertiesSet();
assertThat(handler.getEncoders()).isEqualTo(strategies.encoders());
assertThat(handler.getDecoders()).isEqualTo(strategies.decoders());
assertThat(handler.getRouteMatcher()).isSameAs(strategies.routeMatcher());
assertThat(handler.getMetadataExtractor()).isSameAs(strategies.metadataExtractor());
assertThat(handler.getReactiveAdapterRegistry()).isSameAs(strategies.reactiveAdapterRegistry());
}
@Test
public void rsocketStrategiesReflectsFurtherChangesToOtherProperties() {
RSocketMessageHandler handler = new RSocketMessageHandler();
// RSocketStrategies sets other properties first
handler.setRSocketStrategies(RSocketStrategies.builder()
.encoders(List::clear)
.decoders(List::clear)
.encoders(encoders -> encoders.add(new ByteArrayEncoder()))
.decoders(decoders -> decoders.add(new ByteArrayDecoder()))
.routeMatcher(new SimpleRouteMatcher(new AntPathMatcher()))
.metadataExtractor(new DefaultMetadataExtractor())
.reactiveAdapterStrategy(new ReactiveAdapterRegistry())
.build());
// Followed by further changes to other properties
handler.setDecoders(Collections.singletonList(StringDecoder.allMimeTypes()));
handler.setEncoders(Collections.singletonList(CharSequenceEncoder.allMimeTypes()));
handler.setRouteMatcher(new SimpleRouteMatcher(new AntPathMatcher()));
handler.setMetadataExtractor(new DefaultMetadataExtractor());
handler.setReactiveAdapterRegistry(new ReactiveAdapterRegistry());
handler.afterPropertiesSet();
// RSocketStrategies should reflect current state
RSocketStrategies strategies = handler.getRSocketStrategies();
assertThat(strategies.encoders()).isEqualTo(handler.getEncoders());
assertThat(strategies.decoders()).isEqualTo(handler.getDecoders());
assertThat(strategies.routeMatcher()).isSameAs(handler.getRouteMatcher());
assertThat(strategies.metadataExtractor()).isSameAs(handler.getMetadataExtractor());
assertThat(strategies.reactiveAdapterRegistry()).isSameAs(handler.getReactiveAdapterRegistry());
}
@Test
public void mappings() {
testMapping(new SimpleController(), "path");