Class RSocketMessageHandler

All Implemented Interfaces:
org.springframework.beans.factory.Aware, org.springframework.beans.factory.BeanNameAware, org.springframework.beans.factory.InitializingBean, org.springframework.context.ApplicationContextAware, org.springframework.context.EmbeddedValueResolverAware, ReactiveMessageHandler

public class RSocketMessageHandler extends MessageMappingMessageHandler
Extension of MessageMappingMessageHandler to handle RSocket requests with @MessageMapping and @ConnectMapping methods, also supporting use of @RSocketExchange.

For server scenarios this class can be declared as a bean in Spring configuration and that would detect @MessageMapping methods in @Controller beans. What beans are checked can be changed through a handlerPredicate. Given an instance of this class, you can then use responder() to obtain a SocketAcceptor adapter to register with the RSocketServer.

For a client, possibly in the same process as a server, consider using the static factory method responder(RSocketStrategies, Object...) to obtain a client responder to be registered via RSocketRequester.Builder.

For @MessageMapping and @RSocketExchange methods, this class automatically determines the RSocket interaction type based on the input and output cardinality of the method. See the "Annotated Responders" section of the Spring Framework reference for more details.

Since:
5.2
Author:
Rossen Stoyanchev, Olga Maciaszek-Sharma
  • Constructor Details

    • RSocketMessageHandler

      public RSocketMessageHandler()
  • Method Details

    • setEncoders

      public void setEncoders(List<? extends org.springframework.core.codec.Encoder<?>> encoders)
      Configure the encoders to use for encoding handler method return values.

      When rsocketStrategies is set, this property is re-initialized with the encoders in it, and likewise when this property is set the RSocketStrategies are mutated to change the encoders in it.

      By default this is set to the defaults from RSocketStrategies.

    • getEncoders

      public List<? extends org.springframework.core.codec.Encoder<?>> getEncoders()
      Return the configured encoders.
    • setDecoders

      public void setDecoders(List<? extends org.springframework.core.codec.Decoder<?>> decoders)
      Configure the decoders to use for incoming payloads.

      When rsocketStrategies is set, this property is re-initialized with the decoders in it, and likewise when this property is set the RSocketStrategies are mutated to change the decoders in them.

      By default this is set to the defaults from RSocketStrategies.

      Overrides:
      setDecoders in class MessageMappingMessageHandler
    • setRouteMatcher

      public void setRouteMatcher(@Nullable org.springframework.util.RouteMatcher routeMatcher)
      Set the RouteMatcher to use for mapping messages to handlers based on the route patterns they're configured with.

      By default, SimpleRouteMatcher is used, backed by AntPathMatcher with "." as separator. For greater efficiency consider using the PathPatternRouteMatcher from spring-web instead.

      When rsocketStrategies is set, this property is re-initialized with the route matcher in it, and likewise when this property is set the RSocketStrategies are mutated to change the matcher in it.

      By default this is set to the defaults from RSocketStrategies.

      Overrides:
      setRouteMatcher in class MessageMappingMessageHandler
    • setReactiveAdapterRegistry

      public void setReactiveAdapterRegistry(org.springframework.core.ReactiveAdapterRegistry registry)
      Configure the registry for adapting various reactive types.

      When rsocketStrategies is set, this property is re-initialized with the registry in it, and likewise when this property is set the RSocketStrategies are mutated to change the registry in it.

      By default this is set to the defaults from RSocketStrategies.

      Overrides:
      setReactiveAdapterRegistry in class AbstractMethodMessageHandler<CompositeMessageCondition>
    • setMetadataExtractor

      public void setMetadataExtractor(MetadataExtractor extractor)
      Configure a MetadataExtractor to extract the route along with other metadata.

      When rsocketStrategies is set, this property is re-initialized with the extractor in it, and likewise when this property is set the RSocketStrategies are mutated to change the extractor in it.

      By default this is set to the defaults from RSocketStrategies.

      Parameters:
      extractor - the extractor to use
    • getMetadataExtractor

      public MetadataExtractor getMetadataExtractor()
      Return the configured MetadataExtractor.
    • setRSocketStrategies

      public void setRSocketStrategies(RSocketStrategies rsocketStrategies)
      Configure this handler through an RSocketStrategies instance which can be re-used to initialize a client-side RSocketRequester.

      When this property is set, in turn it sets the following:

      By default this is set to RSocketStrategies.create() which in turn sets default settings for all related properties.

    • getRSocketStrategies

      public RSocketStrategies getRSocketStrategies()
      Return the configured RSocketStrategies.
    • setDefaultDataMimeType

      public void setDefaultDataMimeType(@Nullable org.springframework.util.MimeType mimeType)
      Configure the default content type to use for data payloads if the SETUP frame did not specify one.

      By default this is not set.

      Parameters:
      mimeType - the MimeType to use
    • getDefaultDataMimeType

      @Nullable public org.springframework.util.MimeType getDefaultDataMimeType()
      Return the configured defaultDataMimeType, or null.
    • setDefaultMetadataMimeType

      public void setDefaultMetadataMimeType(org.springframework.util.MimeType mimeType)
      Configure the default MimeType for payload data if the SETUP frame did not specify one.

      By default this is set to "message/x.rsocket.composite-metadata.v0"

      Parameters:
      mimeType - the MimeType to use
    • getDefaultMetadataMimeType

      public org.springframework.util.MimeType getDefaultMetadataMimeType()
      Return the configured defaultMetadataMimeType.
    • afterPropertiesSet

      public void afterPropertiesSet()
      Specified by:
      afterPropertiesSet in interface org.springframework.beans.factory.InitializingBean
      Overrides:
      afterPropertiesSet in class MessageMappingMessageHandler
    • initReturnValueHandlers

      protected List<? extends HandlerMethodReturnValueHandler> initReturnValueHandlers()
      Description copied from class: AbstractMethodMessageHandler
      Return the list of return value handlers to use.

      Subclasses should also take into account custom return value types configured via AbstractMethodMessageHandler.setReturnValueHandlerConfigurer(org.springframework.messaging.handler.invocation.reactive.ReturnValueHandlerConfigurer).

      Overrides:
      initReturnValueHandlers in class MessageMappingMessageHandler
    • getCondition

      @Nullable protected CompositeMessageCondition getCondition(AnnotatedElement element)
      Description copied from class: MessageMappingMessageHandler
      Determine the mapping condition for the given annotated element.
      Overrides:
      getCondition in class MessageMappingMessageHandler
      Parameters:
      element - the element to check
      Returns:
      the condition, or null
    • extendMapping

      protected CompositeMessageCondition extendMapping(CompositeMessageCondition composite, HandlerMethod handler)
      Description copied from class: AbstractMethodMessageHandler
      This method is invoked just before mappings are added. It allows subclasses to update the mapping with the HandlerMethod in mind. This can be useful when the method signature is used to refine the mapping, e.g. based on the cardinality of input and output.

      By default this method returns the mapping that is passed in.

      Overrides:
      extendMapping in class AbstractMethodMessageHandler<CompositeMessageCondition>
      Parameters:
      composite - the mapping to be added
      handler - the target handler for the mapping
      Returns:
      a new mapping or the same
    • handleNoMatch

      protected void handleNoMatch(@Nullable org.springframework.util.RouteMatcher.Route destination, Message<?> message)
      Description copied from class: AbstractMethodMessageHandler
      Invoked when no matching handler is found.
      Overrides:
      handleNoMatch in class AbstractMethodMessageHandler<CompositeMessageCondition>
      Parameters:
      destination - the destination
      message - the message
    • responder

      public io.rsocket.SocketAcceptor responder()
      Return an RSocket SocketAcceptor backed by this RSocketMessageHandler instance that can be plugged in as a client or server RSocket responder.

      The initial ConnectionSetupPayload is handled through @ConnectionMapping methods that can be asynchronous and return Mono<Void> with an error signal preventing the connection. Such a method can also start requests to the client but that must be done decoupled from handling and from the current thread.

      Subsequent requests on the connection can be handled with MessageMapping and RSocketExchange methods.

    • responder

      public static io.rsocket.SocketAcceptor responder(RSocketStrategies strategies, Object... candidateHandlers)
      Static factory method to create an RSocket SocketAcceptor backed by handlers with annotated methods. Effectively a shortcut for:
       RSocketMessageHandler handler = new RSocketMessageHandler();
       handler.setHandlers(handlers);
       handler.setRSocketStrategies(strategies);
       handler.afterPropertiesSet();
      
       SocketAcceptor acceptor = handler.responder();
       

      This is intended for programmatic creation and registration of a client-side responder. For example:

       SocketAcceptor responder =
               RSocketMessageHandler.responder(strategies, new ClientHandler());
      
       RSocketRequester.builder()
               .rsocketConnector(connector -> connector.acceptor(responder))
               .connectTcp("localhost", server.address().getPort());
       

      Note that the given handlers do not need to have any stereotype annotations such as @Controller which helps to avoid overlap with server side handlers that may be used in the same application. However, for more advanced scenarios, e.g. discovering handlers through a custom stereotype annotation, consider declaring RSocketMessageHandler as a bean, and then obtain the responder from it.

      Parameters:
      strategies - the strategies to set on the created RSocketMessageHandler
      candidateHandlers - a list of Objects and/or Classes with annotated handler methods; used to call AbstractMethodMessageHandler.setHandlers(List) with on the created RSocketMessageHandler
      Returns:
      a configurer that may be passed into RSocketRequester.Builder.rsocketConnector(org.springframework.messaging.rsocket.RSocketConnectorConfigurer)
      Since:
      5.2.6