SpringCloud微服务实战系列教程

  Spring Cloud Stream 消息驱动组件帮助我们更快速,更⽅便,更友好的去构建消息驱动微服务的。当时定时任务和消息驱动的⼀个对⽐。(消息驱动:基于消息机制做⼀些事情)MQ:消息队列/消息中间件/消息代理,产品有很多,ActiveMQ RabbitMQ RocketMQ Kafka

一、 Stream解决的痛点问题

  MQ消息中间件⼴泛应⽤在应⽤解耦合、异步消息处理、流量削峰等场景中。不同的MQ消息中间件内部机制包括使⽤⽅式都会有所不同,⽐如RabbitMQ中有Exchange(交换机/交换器)这⼀概念,kafka有Topic、Partition分区这些概念,MQ消息中间件的差异性不利于我们上层的开发应⽤,当我们的系统希望从原有的RabbitMQ切换到Kafka时,我们会发现切换⽐较困难,很多要操作可能重来(因为⽤程序和具体的某⼀款MQ消息中间件耦合在⼀起了)。
  Spring Cloud Stream进⾏了很好的上层抽象,可以让我们与具体消息中间件解耦合,屏蔽掉了底层具体MQ消息中间件的细节差异,就像Hibernate屏蔽掉了具体数据库(Mysql/Oracle⼀样)。如此⼀
来,我们学习、开发、维护MQ都会变得轻松。⽬前Spring Cloud Stream⽀持RabbitMQ和Kafka。

二、Stream重要概念

  Spring Cloud Stream 是⼀个构建消息驱动微服务的框架。应⽤程序通过inputs(相当于消息消费者consumer)或者outputs(相当于消息⽣产者producer)来与Spring Cloud Stream中的binder对象交互,⽽Binder对象是⽤来屏蔽底层MQ细节的,它负责与具体的消息中间件交互。

  Binder绑定器是Spring Cloud Stream 中⾮常核⼼的概念,就是通过它来屏蔽底层不同MQ消息中间件的细节差异,当需要更换为其他消息中间件时,我们需要做的就是更换对应的Binder绑定器⽽不需要修改任何应⽤逻辑(Binder绑定器的实现是框架内置的,Spring Cloud Stream⽬前⽀持Rabbit、Kafka两种消息队列)

三、Stream消息通信⽅式

  Stream中的消息通信⽅式遵循了发布—订阅模式。在Spring Cloud Stream中的消息通信⽅式遵循了发布-订阅模式,当⼀条消息被投递到消息中间件之后,它会通过共享的 Topic 主题进⾏⼴播,消息消费者在订阅的主题中收到它并触发⾃身的业务逻辑处理。这⾥所提到的 Topic 主题是Spring Cloud Stream中的⼀个抽象概念,⽤来代表发布共享消息给消费者的地⽅。在不同的消息中间件中, Topic 可能对应着不同的概念,⽐如:在RabbitMQ中的它对应了Exchange、在Kakfa中则对应了Kafka中的Topic。

四、基于RabbitMQ应用

  第一步:构建消息生产者

    1、引入依赖pom.ml

        <!--eureka client 客户端依赖引⼊-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
</dependency>
<!--spring cloud stream 依赖(rabbit)-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-stream-rabbit</artifactId>
</dependency>

    2、添加配置

    注意:标红的位置应设置相同的binder,蓝色位置必须为output,被默认框架定义好的

server:
port: 9090
spring:
application:
name: stream-provider
cloud:
stream:
binders: # 绑定MQ服务信息(此处我们是RabbitMQ)
cityRabbitBinder: # 给Binder定义的名称,⽤于后⾯的关联
type: rabbit # MQ类型,如果是Kafka的话,此处配置kafka
environment: # MQ环境配置(⽤户名、密码等)
spring:
rabbitmq:
host: localhost
port: 5672
username: guest
password: guest
bindings: # 关联整合通道和binder对象
output: # output是我们定义的通道名称,此处不能乱改
destination: cityExchange # 要使⽤的Exchange名称(消息队列主题名称)
content-type: text/plain # application/json # 消息类型设置,⽐如json
binder: cityRabbitBinder # 关联MQ服务
eureka:
client:
serviceUrl: # eureka server的路径
defaultZone: http://localhost:8761/eureka/
instance:
prefer-ip-address: true #使⽤ip注册

  3、消息发送通过source对象

package city.alber;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.cloud.stream.annotation.EnableBinding;
import org.springframework.cloud.stream.messaging.Source;
import org.springframework.messaging.support.MessageBuilder; /**
* @author niunafei
* @function
* @email niunafei0315@163.com
* @date 2020/9/24 2:26 PM
* Source.class⾥⾯就是对输出通道的定义(这是Spring Cloud Stream内置的通道封装)
*/
@EnableBinding(Source.class)
public class ProviderService {
/**
* 将MessageChannel的封装对象Source注⼊到这⾥使⽤
*/
@Autowired
private Source source; public void sendMessage(String content) {
// 向mq中发送消息(并不是直接操作mq,应该操作的是spring cloud stream)
// 使⽤通道向外发出消息(指的是Source⾥⾯的output通道)
source.output().send(MessageBuilder.withPayload(content).build());
}
}

  4、启动类添加@EnableDiscoveryClient 注解,启动

 第二步:构建消息消费者

  下面的内容是和生产者不一致的地方

  1、配置,标蓝地方为不同点

server:
port: 9091
spring:
application:
name: stream-consumer
cloud:
stream:
binders: # 绑定MQ服务信息(此处我们是RabbitMQ)
cityRabbitBinder: # 给Binder定义的名称,⽤于后⾯的关联
type: rabbit # MQ类型,如果是Kafka的话,此处配置kafka
environment: # MQ环境配置(⽤户名、密码等)
spring:
rabbitmq:
host: localhost
port: 5672
username: guest
password: guest
bindings: # 关联整合通道和binder对象
input: # output是我们定义的通道名称,此处不能乱改
destination: cityExchange # 要使⽤的Exchange名称(消息队列主题名称)
content-type: text/plain # application/json # 消息类型设置,⽐如json,自动将对象转为json
binder: cityRabbitBinder # 关联MQ服务
eureka:
client:
serviceUrl: # eureka server的路径
defaultZone: http://localhost:8761/eureka/
instance:
prefer-ip-address: true #使⽤ip注册

    2、接收消费消息类

package city.albert;

import org.springframework.cloud.stream.annotation.EnableBinding;
import org.springframework.cloud.stream.annotation.StreamListener;
import org.springframework.cloud.stream.messaging.Sink;
import org.springframework.messaging.Message; /**
* @author niunafei
* @function
* @email niunafei0315@163.com
* @date 2020/9/24 2:43 PM
*/
@EnableBinding(Sink.class)
public class ConsumerMsg {
@StreamListener(Sink.INPUT)
public void recevieMessages(Message<String> message) {
System.out.println("=========接收到的消息:" + message);
}
}

五、定义输出

  定一使用与上面配置中蓝色字体的input/ouput类似,定义完成配置应该为 inputSysLog/outputSysLog

  1、定义通过接口,目的是给生产者消费者调用

package city.albert;

import org.springframework.cloud.stream.annotation.Input;
import org.springframework.cloud.stream.annotation.Output;
import org.springframework.messaging.MessageChannel;
import org.springframework.messaging.SubscribableChannel; /**
* @author niunafei
* @function
* @email niunafei0315@163.com
* @date 2020/9/24 3:11 PM
*/
public interface CustomStreamConfig { String INPUT_SYS_LOG = "inputSysLog";
String OUTPUT_SYS_LOG = "outputSysLog"; @Input(INPUT_SYS_LOG)
SubscribableChannel inputSysLog(); @Output(OUTPUT_SYS_LOG)
MessageChannel outputSysLog(); /**
* 。。。。。可以跟上面一样定义多个通道信息
*/
}

  2、生产者调用

package city.albert;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.cloud.stream.annotation.EnableBinding;
import org.springframework.cloud.stream.annotation.StreamListener;
import org.springframework.messaging.Message;
import org.springframework.messaging.support.MessageBuilder; /**
* @author niunafei
* @function
* @email niunafei0315@163.com
* @date 2020/9/24 3:14 PM
*
*/
@EnableBinding(CustomStreamConfig.class)
public class CustomStreamProvider { @Autowired
CustomStreamConfig customStreamConfig; public void sendMessage(String content) {
// 向mq中发送消息(并不是直接操作mq,应该操作的是spring cloud stream)
// 使⽤通道向外发出消息(指的是Source⾥⾯的output通道)
customStreamConfig.outputSysLog().send(MessageBuilder.withPayload(content).build());
}
}

  3、消费者调用

package city.albert;

import org.springframework.cloud.stream.annotation.EnableBinding;
import org.springframework.cloud.stream.annotation.StreamListener;
import org.springframework.messaging.Message; /**
* @author niunafei
* @function
* @email niunafei0315@163.com
* @date 2020/9/24 3:14 PM
*
*/
@EnableBinding(CustomStreamConfig.class)
public class CustomStreamConsumer { @StreamListener(CustomStreamConfig.INPUT_SYS_LOG)
public void messages(Message<String> message) {
System.out.println("=========接收到的消息:" + message);
}
}

六、分组

  同组内一条消息,只能一个消费者获取,添加配置即可

 

SpringCloud-Stream消息通信的更多相关文章

  1. SpringCloud Stream 消息驱动

    1.什么是消息驱动 SpringCloud Stream消息驱动可以简化开发人员对消息中间件的使用复杂度,让系统开发人员更多尽力专注与核心业务逻辑的开发.SpringCloud Stream基于Spr ...

  2. 九. SpringCloud Stream消息驱动

    1. 消息驱动概述 1.1 是什么 在实际应用中有很多消息中间件,比如现在企业里常用的有ActiveMQ.RabbitMQ.RocketMQ.Kafka等,学习所有这些消息中间件无疑需要大量时间经历成 ...

  3. SpringCloud学习笔记(九、SpringCloud Stream)

    目录: 什么是SpringCloud Stream 如何使用SpringCloud Stream 消息分流 什么是SpringCloud Stream: SpringCloud Stream是一个用于 ...

  4. Spring Cloud Stream消息总线

    Springcloud 里面对于MQ的整合一个是前一篇的消息总线一个是本文介绍的消息驱动 大体要学习这么几个知识点: 课题:SpringCloud消息驱动Stream1.什么是SpringCloud消 ...

  5. 《springcloud 五》springcloud stream

    什么是消息驱动? SpringCloud Stream消息驱动可以简化开发人员对消息中间件的使用复杂度,让系统开发人员更多尽力专注与核心业务逻辑的开发.SpringCloud Stream基于Spri ...

  6. SpringCloud Stream使用案例

    官方定义 Spring Cloud Stream 是一个构建消息驱动微服务的框架. 应用程序通过 inputs 或者 outputs 来与 Spring Cloud Stream 中binder 交互 ...

  7. SpringCloud学习之Stream消息驱动【自定义通道】(十一)

    如果不清楚本篇内容的,请务必先去看完上一篇再看本篇,否则阅读起来可能会有部分障碍和困难: 上一篇文章<SpringCloud学习之Stream消息驱动[默认通道](十)>我们简单用自定义通 ...

  8. SpringCloud(七)Stream消息驱动

    Stream消息驱动 概述 屏蔽底层消息中间件的差异,降低切换成本,统一消息的编程模型 官网:https://cloud.spring.io/spring-cloud-static/spring-cl ...

  9. SpringCloud 2020.0.4 系列之 Stream 消息广播 与 消息分组 的实现

    1. 概述 老话说的好:事情太多,做不过来,就先把事情记在本子上,然后理清思路.排好优先级,一件一件的去完成. 言归正传,今天我们来聊一下 SpringCloud 的 Stream 组件,Spring ...

随机推荐

  1. Linux文本三剑客总结

    Linux文本处理三剑客 grep 文本过滤(模式:pattern)工具 grep, egrep, fgrep(不支持正则表达式搜索) grep  grep: Global search REgula ...

  2. 肝了很久,冰河整理出这份4万字的SpringCloud与SpringCloudAlibaba学习笔记!!

    写在前面 不少小伙伴让我整理下有关SpringCloud和SpringCloudAlibaba的知识点,经过3天的收集和整理,冰河整理出这份4万字的SpringCloud与SpringCloudAli ...

  3. 使用Tomcat30分钟搭建个人服务器

    目录 一.服务器简介 二.安装教程 三.出现的问题 一.服务器简介 Tomcat服务器是一个Apache软件资金会的开源项目,实现了Servlet,JSP,EL,WebSocket协议. 二.安装教程 ...

  4. 微信小程序弹出框滚动穿透问题

    1.在你的遮罩层最外层加 catchtouchmove="noneEnoughPeople" 里面是你的方法名2.noneEnoughPeople: function () { c ...

  5. 微信小程序封装请求接口

    var rootDocment = 'https://123.com';//你的域名 function postData(url, data, cb) { wx.request({ url: root ...

  6. kubernets资源预留

    一.  Kubelet Node Allocatable Kubelet Node Allocatable用来为Kube组件和System进程预留资源,从而保证当节点出现满负荷时也能保证Kube和Sy ...

  7. pip命令安装python包到指定目录

    pip install wxpython --target=D:\Server\Python38\Lib\site-packages

  8. Linux速通 大纲

    1.Linux操作系统安装及初始化配置(熟悉) 2.Linux操作系统目录组成结构及文件级增删改查操作(重点) 3.Linux操作系统用户.权限管理(重点) 4.开源软件及Linux下软件包的管理(重 ...

  9. Java 虚拟机详解

    深入理解JVM 1   Java技术与Java虚拟机 说起Java,人们首先想到的是Java编程语言,然而事实上,Java是一种技术,它由四方面组成: Java编程语言.Java类文件格式.Java虚 ...

  10. Centos mini系统下的Hadoop集群搭建

    1.事前了解 1.1 Hadoop 百度百科:https://baike.baidu.com/item/Hadoop/3526507?fr=aladdin Hadoop是一个由Apache基金会所开发 ...