Spring Cloud Stream(二)
前面那一节就是讲一下各种概念,接下来就是如何使用咯。
一:编程模型
介绍Spring Cloud Stream的编程模型。Spring Cloud Stream提供了许多预定义的注释,用于声明绑定的输入和输出通道,以及如何收听频道。
1.1 声明和绑定频道
1.1.1 触发绑定@EnableBinding
可以将Spring应用程序转换为Spring Cloud Stream应用程序,将@EnableBinding
注释应用于应用程序的配置类之一。@EnableBinding
注释本身使用@Configuration
进行元注释,并触发Spring Cloud Stream基础架构的配置:
@Import(...)
@Configuration
@EnableIntegration
public @interface EnableBinding {
...
Class<?>[] value() default {};
}
@EnableBinding
注释可以将一个或多个接口类作为参数,这些接口类包含表示可绑定组件(通常是消息通道)的方法。
1.1.2 @Input
和@Output
Spring Cloud Stream应用程序可以在接口中定义任意数量的输入和输出通道为@Input
和@Output
方法:
public interface MyChannel {
@Input
SubscribableChannel orders();
@Output
MessageChannel hotDrinks();
@Output
MessageChannel coldDrinks();
}
使用此接口作为参数@EnableBinding
将分别触发三个绑定的通道名称为orders
,hotDrinks
和coldDrinks
。
@EnableBinding(MyChannel.class)
public class CafeConfiguration {
}
1.1.3 自定义频道名称
使用@Input
和@Output
注释,可以指定频道的自定义频道名称,如以下示例所示:
public interface MyChannel {
@Input("inboundOrders")
SubscribableChannel orders();
}
在这个例子中,创建的绑定通道将被命名为inboundOrders
。
1.1.4 Source
,Sink
和Processor
为了方便寻址最常见的用例,涉及输入通道,输出通道或两者,Spring Cloud Stream提供了开箱即用的三个预定义接口。
Source
可用于具有单个出站通道的应用程序。
public interface Source {
String OUTPUT = "output";
@Output(Source.OUTPUT)
MessageChannel output();
}
Sink
可用于具有单个入站通道的应用程序。
public interface Sink {
String INPUT = "input";
@Input(Sink.INPUT)
SubscribableChannel input();
}
Processor
可用于具有入站通道和出站通道的应用程序。
public interface Processor extends Source, Sink {
}
Spring Cloud Stream不为任何这些接口提供特殊处理; 它们只是开箱即用。
1.2 访问绑定通道
1.2.1 注入绑定界面
对于每个绑定接口,Spring Cloud Stream将生成一个实现该接口的bean。调用其中一个bean的@Input
注释或@Output
注释方法将返回相关的绑定通道。
以下示例中的bean在调用其hello
方法时在输出通道上发送消息。它在注入的Source
bean上调用output()
来检索目标通道。
@Component
public class SendingBean {
private Source source;
@Autowired
public SendingBean(Source source) {
this.source = source;
}
public void sayHello(String name) {
source.output().send(MessageBuilder.withPayload(name).build());
}
}
1.2.2 直接注入渠道
绑定通道也可以直接注入:
@Component
public class SendingBean {
private MessageChannel output;
@Autowired
public SendingBean(MessageChannel output) {
this.output = output;
}
public void sayHello(String name) {
output.send(MessageBuilder.withPayload(name).build());
}
}
如果在声明注释上定制了通道的名称,则应使用该名称而不是方法名称。给出以下声明:
public interface CustomSource {
@Output("customOutput")
MessageChannel output();
}
通道将被注入,如下例所示:
@Component
public class SendingBean {
private MessageChannel output;
@Autowired
public SendingBean(@Qualifier("output1") MessageChannel output) {
this.output = output;
}
public void sayHello(String name) {
output.send(message(name));
}
private static final <T> Message<T> message(T val) {
return MessageBuilder.withPayload(val).build();
}
}
1.3 生产和消费消息
您可以使用Spring Integration注解或Spring Cloud Stream的@StreamListener
注释编写Spring Cloud Stream应用程序。@StreamListener
注释在其他Spring消息传递注释(例如@MessageMapping
,@JmsListener
,@RabbitListener
等)之后建模,但添加内容类型管理和类型强制功能。
1.3.1 本地Spring Integration支持
由于Spring Cloud Stream基于Spring Integration,Stream完全继承了Integration的基础和基础架构以及组件本身。例如,您可以将Source
的输出通道附加到MessageSource
:
@EnableBinding(Source.class)
public class TimerSource {
@Value("${format}")
private String format;
@Bean
@InboundChannelAdapter(value = Source.OUTPUT, poller = @Poller(fixedDelay = "${fixedDelay}", maxMessagesPerPoll = "1"))
public MessageSource<String> timerMessageSource() {
return () -> new GenericMessage<>(new SimpleDateFormat(format).format(new Date()));
}
}
或者您可以在transformer中使用处理器的通道:
@EnableBinding(Processor.class)
public class TransformProcessor {
@Transformer(inputChannel = Processor.INPUT, outputChannel = Processor.OUTPUT)
public Object transform(String message) {
return message.toUpperCase();
}
}
1.3.2 Spring Integration错误通道支持
Spring Cloud Stream支持发布Spring Integration全局错误通道收到的错误消息。发送到errorChannel
的错误消息可以通过为名为error
的出站目标配置绑定,将其发布到代理的特定目标。例如,要将错误消息发布到名为“myErrors”的代理目标,请提供以下属性:spring.cloud.stream.bindings.error.destination=myErrors
1.3.3 使用@StreamListener进行自动内容类型处理
Spring Integration支持Spring Cloud Stream提供自己的@StreamListener
注释,以其他Spring消息传递注释(例如@MessageMapping
,@JmsListener
,@RabbitListener
等) )。@StreamListener
注释提供了一种更简单的处理入站邮件的模型,特别是在处理涉及内容类型管理和类型强制的用例时。
Spring Cloud Stream提供了一种可扩展的MessageConverter
机制,用于通过绑定通道处理数据转换,并且在这种情况下,将调度到使用@StreamListener
注释的方法。以下是处理外部Vote
事件的应用程序的示例:
@EnableBinding(Sink.class)
public class VoteHandler {
@Autowired
VotingService votingService;
@StreamListener(Sink.INPUT)
public void handle(Vote vote) {
votingService.record(vote);
}
}