From 408415cb48acd90ef3f4284c73637c245be4e0df Mon Sep 17 00:00:00 2001 From: Dave Syer Date: Fri, 17 Jul 2015 01:48:24 +0000 Subject: [PATCH] Sync docs from master to gh-pages --- spring-cloud-stream.html | 64 ++++++++++++++++++++++++++++++++-------- 1 file changed, 52 insertions(+), 12 deletions(-) diff --git a/spring-cloud-stream.html b/spring-cloud-stream.html index 62b3510bb..7de443558 100644 --- a/spring-cloud-stream.html +++ b/spring-cloud-stream.html @@ -417,7 +417,7 @@ body.book #toc,body.book #preamble,body.book h1.sect0,body.book .sect1>h2{page-b
-

This project allows a user to develop and run messaging microservices using Spring Integration and run them locally, or in the cloud, or even on Spring XD. Just create MessageChannels "input" and/or "output" and add @EnableModule and run your app as a Spring Boot app (single application context). You just need to connect to the physical broker for the bus, which is automatic if the relevant bus implementation is available on the classpath. The sample uses Redis.

+

This project allows a user to develop and run messaging microservices using Spring Integration and run them locally, or in the cloud, or even on Spring XD. Just add @EnableModule and run your app as a Spring Boot app (single application context). You just need to connect to the physical broker for the bus, which is automatic if the relevant bus implementation is available on the classpath. The sample uses Redis.

Here’s a sample source module (output channel only):

@@ -425,8 +425,7 @@ body.book #toc,body.book #preamble,body.book h1.sect0,body.book .sect1>h2{page-b
@SpringBootApplication
-@EnableModule
-@ComponentScan(basePackageClasses=ModuleDefinition.class)
+@ComponentScan(basePackageClasses=TimerSource.class)
 public class ModuleApplication {
 
   public static void main(String[] args) throws InterruptedException {
@@ -436,18 +435,14 @@ public class ModuleApplication {
 }
 
 @Configuration
-public class ModuleDefinition {
+@EnableModule(Source.class)
+public class TimerSource {
 
   @Value("${format}")
   private String format;
 
   @Bean
-  public MessageChannel output() {
-    return new DirectChannel();
-  }
-
-  @Bean
-  @InboundChannelAdapter(value = "output", autoStartup = "false", poller = @Poller(fixedDelay = "${fixedDelay}", maxMessagesPerPoll = "1"))
+  @InboundChannelAdapter(value = Source.OUTPUT, autoStartup = "false", poller = @Poller(fixedDelay = "${fixedDelay}", maxMessagesPerPoll = "1"))
   public MessageSource<String> timerMessageSource() {
     return () -> new GenericMessage<>(new SimpleDateFormat(format).format(new Date()));
   }
@@ -468,13 +463,58 @@ spring:
       outputChannelName: ${spring.application.name:ticker}
+
+

@EnableModule is parameterized by an interface (in this case Source) which declares input and output channels. Source, Sink and Processor are provided off the shelf, but you can define others. Here’s the definition of Source

+
+
+
+
public interface Source {
+  @Output("output")
+  MessageChannel output();
+}
+
+
+
+

The @Output annotation is used to identify output channels (messages leaving the module) and @Input is used to identify input channels (messages entering the module). It is optionally parameterized by a channel name - if the name is not provided the method name is used instead. An implementation of the interface is created for you and can be used in the application context by autowiring it, e.g. into a test case:

+
+
+
+
@RunWith(SpringJUnit4ClassRunner.class)
+@SpringApplicationConfiguration(classes = ModuleApplication.class)
+@WebAppConfiguration
+@DirtiesContext
+public class ModuleApplicationTests {
+
+	@Autowired
+	private Source source
+
+	@Test
+	public void contextLoads() {
+		assertNotNull(this.sink.output());
+	}
+
+}
+
+
+
+ + + + + +
+
Note
+
+In this case there is only one Source in the application context so there is no need to qualify it when it is autowired. If there is ambiguity, e.g. if you are composing one module from some others, you can use @ModuleChannels qualifier to inject a specific channel set. The @ModuleChannels qualifier takes a parameter which is the class that carries the @EnableModule annotation (in this case the TimerSource). +
+

Multiple Input or Output Channels

-

A module can have multiple input or output channels. Instead of just one channel named "input" or "output" you can add multiple MessageChannel beans named input. or output. and the names are converted to external channel names on the broker. The external channel names are the spring.cloud.streams.[input|output]ChannelName plus the MessageChannel bean name, period separated. In addition, the bean name can be input.[queue|topic|tap]:* or output.[queue|topic]:* (i.e. with a channel type as a colon-separated prefix), and the semantics of the external bus channel changes accordingly (a tap is like a topic). For example, you can have two MessageChannels called "output" and "output.topic:foo" in a module with outputChannelName=bar, and the result is 2 external channels called "bar" and "topic:foo.bar".

+

A module can have multiple input or output channels all defined either as @Input and @Output methods in an interface (preferrable) or as bean definitions. Instead of just one channel named "input" or "output" you can add multiple MessageChannel methods annotated input. or output. and the names are converted to external channel names on the broker. The external channel names are the spring.cloud.channels.[input|output]ChannelName plus the MessageChannel bean name, period separated. In addition, the bean name can be input.[queue|topic|tap]:* or output.[queue|topic]:* (i.e. with a channel type as a colon-separated prefix), and the semantics of the external bus channel changes accordingly (a tap is like a topic). For example, you can have two MessageChannels called "output" and "output.topic:foo" in a module with outputChannelName=bar, and the result is 2 external channels called "bar" and "topic:foo.bar".

@@ -583,7 +623,7 @@ The main set of samples are "vanilla" in the sense that they are not deployable