springcloud学习总结

Posted Java中的战斗机

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了springcloud学习总结相关的知识,希望对你有一定的参考价值。

springcloud

构建微服务项目步骤

  1. 导入依赖
  2. 编写配置文件
  3. 开启这个功能 @Enablexxx
  4. 配置类
  • 于2023年2月24日下午17点38分开始学习
  • 于2023年3月17日晚上20点26分学完总结
  • 代码地址:https://gitee.com/liang-weihao/StudySpringcloud
  • 学习笔记地址:https://www.kuangstudy.com/bbs/1374942542566551554

简介

SpringCloud,基于SpringBoot提供了一套微服务解决方案,包括服务注册与发现,配置中心,全链路监控,服务网关,负载均衡,熔断器等组件,除了基于NetFlix的开源组件做高度抽象封装之外,还有一些选型中立的开源组件。

  • springcloud就是为了分布式,通过rpc远程调用或http来互相通信访问
  • spring boot的核心自动装配,约定大于配置
  • 常用组件

Spring cloud有哪些常用组件,作用是什么?

  1. Eureka:注册中心
  2. Nacos:注册中心、配置中心
  3. Consul: 注册中心、配置中心
  4. Spring Cloud Config:配置中心
  5. Feign/OpenFeign:RPC调用
  6. Kong:服务网关
  7. Zuul:服务网关
  8. Spring Cloud Gateway: 服务网关
  9. Ribbon:负载均衡
  10. Spring CLoud sleuth: 链路追踪
  11. Zipkin:链路追踪
  12. Seata:分布式事务
  13. Dubbo:RPC调用
  14. Sentinel: 服务熔断
  15. Hystrix:服务熔断

springcloud和springboot的关系

  • SpringBoot专注于快速方便的开发单个个体微服务。 -Jar
  • SpringCloud是关注全局的微服务协调整理治理框架,它将SpringBoot开发的一个个单体微服务整合并管理起来,为各个微服务之间提供: 配置管理,服务发现,断路器,路由,微代理,事件总线,全局锁,决策竞选,分布式会话等等集成服务。
  • SpringBoot可以离开SpringClooud独立使用,开发项目,但是SpringCloud离不开SpringBoot,属于依赖关系
  • SpringBoot专注于快速、方便的开发单个个体微服务,SpringCloud关注全局的服务治理框架

dubbo

  • rpc框架
  • dubbo专门的rpc远程调用
  • spring cloudNetflix 2018年停更

  • 微服务就是将传统一站式根据业务拆分成一个一个服务,彻底去耦合,一个微服务处理一件事情
  • 微服务的优缺点
  • 每个进程一个端口
  • 微服务的技术栈
  • 返回类型就是类点class

RestTemplate远程服务调用

 @Autowired
    //返回类型:(url,实体map,返回类型Class<T> responseType)
private RestTemplate restTemplate;//提供多种便捷访问http服务的方法,简单的restful服务模板
package com.liang.springcloud.controller;

import com.liang.springcloud.pojo.Dept;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.client.RestTemplate;

import java.util.List;

@Controller
@ResponseBody
public class DeptConsumerController 

    //理解:消费者,不应该有service层
    //RestTemplate很多方法给我们直接调用,注册到spring中

    @Autowired
    //返回类型:(url,实体map,返回类型Class<T> responseType)
    private RestTemplate restTemplate;//提供多种便捷访问http服务的方法,简单的restful服务模板

    private static final String REST_URL_PREFIX = "http://localhost:8001";

    @RequestMapping("/consumer/dept/add")
    public boolean add(Dept dept)
        return restTemplate.postForObject(REST_URL_PREFIX+"/dept/add",dept, Boolean.class);
    

    //http://localhost:8001/dept/list要从这个地址拿到数据
    @RequestMapping("/consumer/dept/get/id")
    public Dept get(@PathVariable("id") Long id)
        return restTemplate.getForObject(REST_URL_PREFIX+"/dept/get/"+id,Dept.class);
    

    @RequestMapping("/consumer/dept/list")
    public List<Dept> list()
        return restTemplate.getForObject(REST_URL_PREFIX+"dept/list", List.class);
    

Eureka服务注册与发现

  • 主需要在主启动类上加注解@EnableEurekaServer
@SpringBootApplication
@EnableEurekaServer //服务端的启动类,可以接受别人注册进来
public class EurekaService_7001 

    public static void main(String[] args) 
        SpringApplication.run(EurekaService_7001.class,args);
    

  • 在其他服务配置文件,配置好eureka配置,然后在主启动类加上注解自动注册
@EnableEurekaClient//cs架构,自动在服务启动后自动注册到eureka中


什么是eureka?

Eureka: 怎么读?

  • Netflix 在设计Eureka时,遵循的就是AP原则
    Eureka是Netflix的一个子模块,也是核心模块之一。Eureka是一个基于REST的服务,用于定位服务,以实现云端中间层服务发现和故障转移,服务注册与发现对于微服务来说是非常重要的,有了服务发现与注册,只需要使用服务的标识符,就可以访问到服务,而不需要修改服务调用的配置文件了,功能类似于Dubbo的注册中心,比如Zookeeper;

  • 心跳监测机制,五秒不回复证明挂掉,就会把服务节点移掉

  • 自我保护机制(宁可保留全部服务,也不盲目注销任何健康的服务)

  • 注意yml文件,编写要空一格

  • 搭建eureka集群,对应配置文件加上绑定互联

  • 创建三个服务端口分别为,注册中心(7001,7002,7003)

server:
  port: 7003

# eureka配置
eureka:
  instance:
    hostname: eureka7003.com #Eureka服务端的实例名称
  client:
    register-with-eureka: false # 表示是否向eureka注册中心注册自己
    fetch-registry: false # fetch-registry 如果为false,则表示自己为注册中心
    service-url: # 监控页面
      defaultZone: http://eureka7002.com:7002/eureka/,http://eureka7001.com:7001/eureka/
  • 集群信息
  • 把注册的提供服务8001启动,就会注册到对应的服务里

server:
  port: 8001

#mybatis的配置
mybatis:
  type-aliases-package: com.liang.springcloud.pojo
  config-location: classpath:mybatis/mybatis-config.xml
  mapper-locations: classpath:mybatis/mapper/*.xml

#spring的配置
spring:
  application:
    name: springcloud-provider-dept
  datasource:
    type: com.alibaba.druid.pool.DruidDataSource
    driver-class-name: com.mysql.jdbc.Driver
    url: jdbc:mysql://localhost:3306/db01?useUnicode=true&characterEncoding=utf-8
    username: root
    password: root


# Eureka的配置,服务注册到哪里
eureka:
  client:
    service-url:
      defaultZone: http://localhost:7001/eureka/,http://eureka7002.com:7002/eureka/,http://eureka7003.com:7003/eureka/
  instance:
    instance-id: springcloud-provider-dept8001-liangwh #修改的是eureka status默认的描述信息
#info配置
info:
  app.name: liangwh-springcloud
  company.name: liangwh123321.com

zookeeper和eureka的区别

  • cap原则,一个分布式系统不可能同时满足三个

  • 作为服务注册中心,Eureka比Zookeeper好在哪里?

    • 著名的CAP理论指出,一个分布式系统不可能同时满足C(一致性)、A (可用性)、P (容错性)。由于分区容错性P在分布式系统中是必须要保证的,因此我们只能在A和C之间进行权衡

      。Zookeeper保证的是CP;
      。Eureka保证的是AP:

ribbon负载均衡

  • Spring Cloud Ribbon是基于Netflix Ribbon实现的一套客户端负载均衡的工具轮询和随机

  • 简单的说,Ribbon是Netflix发布的开源项目,主要功能是提供客户端的软件负载均衡算法,将NetFlix的中间层服务连接在一起。Ribbon的客户端组件提供一系列完整的配置项如: 连接超时、重试等等。简单的说,就是在配置文件中列出LoadBalancer (简称LB: 负载均衡)后面所有的机器,Ribbon会自动的帮助你基于某种规则(如简单轮询,随机连接等等) 去连接这些机器。我们也很容易使用Ribbon实现自定义的负载均衡算法

  • 负载均衡,把用户的请求平摊到多个服务上,达到高可用

ribbon能干嘛?
。LB,即负载均衡 (Load Balance) ,在微服务或分布式集群中经常用的一种应用。
。负载均衡简单的说就是将用户的请求平摊的分配到多个服务上,从而达到系统的HA(高可用)
。常见的负载均衡软件有 Nginx,Lvs 等等
·dubbo、 SpringCloud中均给我们提供了负载均衡,SpringCloud的负载均衡算法可以自定义
。负载均衡简单分类:
集中式LB0
即在服务的消费方和提供方之间使用独立的LB设施,如nginx(反向代理),由该设施负责把访问请求通过某种策略转发至服务的提供方!
进程式LB,将LB逻辑集成到消费方,消费方从服务注册中心获知有哪些地址可用,然后自己再从这些地址中选出一个合适的服务器
Ribbon就属于进程内LB它只是一个类库,集成于消费方进程,消费方通过它来获取到服务提供方的地址!

  • 注意报错 - @org.springframework.beans.factory.annotation.Autowired(required=true)

表明引用的类没有注入到bean中需要在该类加上注解 @Bean

@Configuration
public class ConfigBean 
//配置负载均衡实现RestTemplate
    @Bean
    @LoadBalanced//ribbon
    public RestTemplate getRestTemplate()
        return  new RestTemplate();
    

  • @Bean一般和@Configuration一起使用

  • idea显示数据库

  • 集群,三个服务提供者对应三个不同的数据库,通过ribbon实现负载均衡访问不同数据库(轮询

ribbon默认算法

//ribbon 和 eureka整合以后,客户端可以直接调用,不用关心ip 和 端口号
//消费者主启动类
@SpringBootApplication
@EnableEurekaClient
//在微服务启动的时候就能去加载我们自定义的ribbon类
@RibbonClient(name = "SPRINGCLOUD-PROVIDER-DEPT",configuration = liangRule.class)
public class DeptConsumer_88 
    public static void main(String[] args) 
        SpringApplication.run(DeptConsumer_88.class, args);
    


  • 注意自定义类要在主启动类上一级
package com.liang.myrule;
import com.netflix.client.config.IClientConfig;
import com.netflix.loadbalancer.AbstractLoadBalancerRule;
import com.netflix.loadbalancer.ILoadBalancer;
import com.netflix.loadbalancer.Server;

import java.util.List;
import java.util.concurrent.ThreadLocalRandom;

public class LiangRandomRule extends AbstractLoadBalancerRule 

    //每个服务,访问6次,换下一个服务(3个)
    //total=0,默认=0,如果=6,指向下一个服务节点
    //index= 0,默认=0,如果total = 5,index+1

    private  int total = 0; //被调用的次数
    private int currentIndex = 0; //当前谁提供的服务
    @SuppressWarnings("RCN_REDUNDANT_NULLCHECK_OF_NULL_VALUE")
    public Server choose(ILoadBalancer lb, Object key) 
        if (lb == null) 
            return null;
         else 
            Server server = null;

            while(server == null) 
                if (Thread.interrupted()) 
                    return null;
                

                List<Server> upList = lb.getReachableServers();//获得可访问服务器
                List<Server> allList = lb.getAllServers();//获取全部服务
                int serverCount = allList.size();
                if (serverCount == 0) 
                    return null;
                

//                int index = this.chooseRandomInt(serverCount);//生成区间随机数
//                server = (Server)upList.get(index);//从活着的服务中,随机获取一个

                // -自定义算法开始==============================

                if (total<5)
                    server = upList.get(currentIndex);
                    total++;
                else 
                    total = 0;
                    currentIndex ++;
                    if (currentIndex>=upList.size())
                        currentIndex = 0;
                    
                    server = upList.get(currentIndex);//从活着的服务中,获得指定的服务来操作


                

                // -自定义算法结束==============================


                if (server == null) 
                    Thread.yield();
                 else 
                    if (server.isAlive()) 
                        return server;
                    

                    server = null;
                    Thread.yield();
                
            

            return server;
        
    

    protected int chooseRandomInt(int serverCount) 
        return ThreadLocalRandom.current().nextInt(serverCount);
    

    public Server choose(Object key) 
        return this.choose(this.getLoadBalancer(), key);
    

    public void initWithNiwsConfig(IClientConfig clientConfig) 
    


@Configuration
public class liangRule 


    @Bean
    public IRule myRule()
        return new LiangRandomRule();//默认是轮询,现在我们自定义访问自己定义的算法
    

Feign负载均衡

简介

  • feign是声明式的web service客户端,它让微服务之间的调用变得更简单了,类似controller调用service。SpringCloud集成了Ribbon和Eureka,可在使用Feign时提供负载均衡的http客户端。
    只需要创建一个接口,然后添加注解即可!
    feign ,主要是社区,大家都习惯面向接口编程。这个是很多开发人员的规范。调用微服务访问两种方法
    1.微服务名字 (ribbon]
    2.接口和注解 [feign ]
  • 主要靠接口和注解就可以使用

在service加上注解

@FeignClient(value = "SPRINGCLOUD-PROVIDER-DEPT")
  • 接口
@Component//注入到容器
@FeignClient(value = "SPRINGCLOUD-PROVIDER-DEPT")
public interface DeptClientService 

    @GetMapping("/dept/get/id")
    public Dept queryById(@PathVariable("id")Long id);

    @GetMapping("/dept/list")
    public List<Dept> queryAll();

    @PostMapping("/dept/add")
    public boolean addDept(Dept dept);


  • controller 层
@RestController
public class DeptConsumerController 

    //理解:消费者,不应该有service层
    //RestTemplate很多方法给我们直接调用,注册到spring中

    @Autowired
    //返回类型:(url,实体map,返回类型Class<T> responseType)
    private RestTemplate restTemplate;//提供多种便捷访问http服务的方法,简单的restful服务模板

    //ribbon(负载均衡) 我们这里的地址应该是一个变量,通过服务访问
//    private static final String REST_URL_PREFIX = "http://localhost:8001";
//    private static final String REST_URL_PREFIX = "http://SPRINGCLOUD-PROVIDER-DEPT";

    @Autowired
    private DeptClientService deptClientService;


    @RequestMapping("/consumer/dept/add")
    public boolean add(Dept dept)
        return this.deptClientService.addDept(dept);
    

    //http://localhost:8001/dept/list要从这个地址拿到数据
    @RequestMapping("/consumer/dept/get/id")
    public Dept get(@PathVariable("id") Long id)
        return deptClientService.queryById(id);
    

    @RequestMapping("/consumer/dept/list")
    public List<Dept> list()
        return this.deptClientService.queryAll();
    
  • 主启动类
@SpringBootApplication
@EnableEurekaClient
@EnableFeignClients(basePackages = "com.liang.springcloud")
public class FeignDeptConsumer_88 
    public static void main(String[] args) 
        SpringApplication.run(FeignDeptConsumer_88.class, args);
    


Hystrix服务熔断降级

简介

Hvstrix是一个用于处理分布式系统的延迟和容错的开源库,在分布式系统里,许多依赖不可避免的会调用失败,比如超时,异常等,Hystrix能够保证在一个依赖出问题的情况下,不会导致整体服务失败,避免级联故障以提高分布式系统的弹性。
"断路器"本身是一种开关装置,当某个服务单元发生故障之后,通过断路器的故障监控(类似熔断保险丝),向调用方返回一个服务预期的,可处理的备选响应(FallBack),而不是长时间的等待或者抛出调用方法无法处理的异常,这样就可以保证了服务调用方的线程不会被长时间,不必要的占用,从而避免了故喷在分布式系统中的蔓延,乃至雪崩

Hystrix能干嘛

。服务降级
。服务熔断
。服务限流
。接近实时的监控

  • 服务雪崩
  • ‘弃车保帅’

服务熔断

服务熔断是什么?

  • 熔断机制是对应雪崩效应的一种微服务链路保护机制
    当扇出链路的某个微服务不可用或者响应时间太长时,会进行服务的降级,进而熔断该节点微服务的调用,快速返回 错误的响应信息当检测到该节点微服务调用响应正常后恢复调用链路。在Springloud框架里熔断机制通过Hystrix实现。Hvstrix会监控微服务间调用的状况,当失败的调用到一定闻值,5秒内20次调用失败就会启动熔断机制
    熔断机制的注解是 @HystrixCommand

  • 在主启动类加上注解@EnableCircuitBreaker//添加对熔断的支持

  • 链式编程注解(在对应实体类加上即可)

@Accessors(chain = true)//链式写法	
@Data
@NoArgsConstructor
@Accessors(chain = true)//链式写法
public class Dept implements Serializable 
    private Long deptno;//主键
    private String dname;

    private String db_source;//一个服务对应一个数据库,数据库存的字段

    public Dept(String dname) 
        this.dname = dname;
    

  • 写法
   //备选方法
    @GetMapping("/dept/get/id")
    public Dept hystrixGet(@PathVariable("id") Long id)
        return  new Dept()
                .setDeptno(id)
                .setDname("id=>"+id+"没有对应信息,null==@hystrix")
                .setDb_source("no this database in mysql");
    
  • hystrix服务熔断调用其他方法
    @GetMapping("/dept/get/id")
    @HystrixCommand(fallbackMethod = "hystrixGet")//只要失败就调用其他方法
    public Dept get(@PathVariable("id") Long id)
        Dept dept = deptService.queryById(id);
        if (dept == null)
            throw  new RuntimeException("id=>"+id+"不存在这个id");
        
        return  dept;
    

    //备选方法
    public Dept hystrixGet(@PathVariable("id") Long id)
        return  new Dept()
                .setDeptno(id)
                .setDname("id=>"+id+"没有对应信息,null==@hystrix")
                .setDb_source("no this database in mysql");
    

1. SpringCloud Bus 之 消息总线 介绍

  • 2. SpringCloud Bus 之 搭建RabbitMQ
  • 3. SpringCloud Bus 之 动态刷新全局广播的设计思想和选型
  • 4. SpringCloud Bus 之 动态刷新全局广播配置实现
  • 5. SpringCloud Stream 之 消息驱动 介绍
  • 6. SpringCloud Stream 之 设计思想
  • 7. SpringCloud Stream 之 消息驱动 搭建生产者
  • 8. SpringCloud Stream 之 消息驱动 搭建消费者
  • 9. SpringCloud Stream 之 多台消费者重复消费的问题
  • 10. SpringCloud Stream 之 消息持久化
  • 10. SpringCloud Sleuth 之 分布式请求链路跟踪
  • 11. SpringCloud Sleuth 之 zipkin搭建安装
  • 11. SpringCloud Sleuth 之 链路监控展现
  • 1. SpringCloud Bus 之 消息总线 介绍


    SpringCloud Bus的作用:

    • 分布式自动刷新配置功能。
    • Spring Cloud Bus 配合 Spring Cloud Config 使用可以实现配置的动态刷新。

    Bus支持两种消息代理:RabbitMQ 和 Kafka

    SpringCloud Bus介绍:

    总线的概念:

    2. SpringCloud Bus 之 搭建RabbitMQ


    见:https://blog.csdn.net/IT_Holmes/article/details/124251437

    3. SpringCloud Bus 之 动态刷新全局广播的设计思想和选型


    第一种:利用消息总线触发一个客户端/bus/refresh,而刷新所有客户端的配置。

    • 先发给某台客户端,之后由客户端传染给其他客户端,进而刷新所有客户端配置。

    第二种:利用消息总线触发一个服务端ConfigServer的/bus/refresh端点,而刷新所有客户端的配置。 (推荐使用!)

    4. SpringCloud Bus 之 动态刷新全局广播配置实现


    第一步:创建项目,安装依赖。(直接使用之前已经创建好的config server也是可以的!)

    <!--添加rabbitmq支持的bus-->
    <dependency>
        <groupId>org.springframework.cloud</groupId>
        <artifactId>spring-cloud-starter-bus-amqp</artifactId>
    </dependency>
    
    <!--springcloud config配置中心的依赖-->
    <dependency>
        <groupId>org.springframework.cloud</groupId>
        <artifactId>spring-cloud-config-server</artifactId>
    </dependency>
    
    <!--添加eureka-client客户端-->
    <dependency>
        <groupId>org.springframework.cloud</groupId>
        <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
    </dependency>
    
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-web</artifactId>
    </dependency>
    
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-actuator</artifactId>
    </dependency>
    
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-devtools</artifactId>
        <scope>runtime</scope>
        <optional>true</optional>
    </dependency>
    
    <dependency>
        <groupId>org.projectlombok</groupId>
        <artifactId>lombok</artifactId>
        <optional>true</optional>
    </dependency>
    
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-test</artifactId>
        <scope>test</scope>
    </dependency>
    
    <dependency>
        <groupId>com.itholmes.springcloud</groupId>
        <artifactId>cloud-api-commons</artifactId>
        <version>$project.version</version>
    </dependency>
    

    第二步:修改application.yml配置文件。

    • 服务端配置文件:
    server:
      port: 3344
    spring:
      application:
        name: cloud-config-center # 微服务名称
      cloud:
        config:
          server:
            git:
              uri: https://gitee.com/lixiaogou/sprincloud-config.git #GitHub上面的git仓库名字
              search-paths: #搜索目录
                - springcloud-config
          label: master #读取分支
    
    # rabbitmq相关配置
    rabbitmq:
      host: 127.0.0.1
      password: 0818
      username: admin
      port: 5672
    
    # 服务注册到eureka地址
    eureka:
      client:
        service-url:
          defaultZone: http://localhost:7001/eureka
    
    # Rabbitmq相关配置,暴露bus刷新配置的端点
    management:
      endpoint: # 暴露bus刷新配置的端点
        web:
          exposure:
            include: 'bus-refresh'
    
    • 客户端配置文件:(bootstrap.yml)
    server:
      port: 3355
    
    spring:
      application:
        name: config-client
      cloud:
        # SpringCloud Config 客户端配置
        config:
          label: master # 分支名称
          name: config # 配置文件名称
          profile: dev # 读取后缀名称
          # 上述三个综合: master分支上config-dev.yml的配置文件被读取http://config-3344.com:3344/master/config-dev.yml
          uri: http://localhost:3344 # 配置中心地址
    
    # 服务注册到eureka地址
    eureka:
      client:
        service-url:
          defaultZone: http://localhost:7001/eureka
    
    # 暴露监控端点
    management:
      endpoints:
        web:
          exposure:
            include: "*"
    

    运维工程师得发布通知公式(刷新顶点通知):

    • 下面得destination指得是:微服务名称:端口。

    5. SpringCloud Stream 之 消息驱动 介绍


    SpringCloud Stream是一个构建消息驱动微服务的框架。

    Stream消息驱动的作用:屏蔽底层消息中间件的差异,降低切换成本,统一消息的编程模型。

    Stream原理就是通过binder对象与消息中间件交互。

    6. SpringCloud Stream 之 设计思想


    通过定义绑定器Binder作为中间层,完美实现应用程序与消息中间件细节之间的隔离。

    input对应生产者。

    output对应消费者。

    Stream的架构图如下:

    Stream中的小心通信方式遵循了发布-订阅模式。

    官方给出的理念架构理解:

    Stream标准流的三个流程:

    • Binder:连接中间件,屏蔽差异。
    • Channel:通道,实现存储和转发的媒介,通过Channel对队列进行配置。
    • Source和Sink:从Stream发布消息就是输出,接收消息就是输入。

    7. SpringCloud Stream 之 消息驱动 搭建生产者


    第一步:创建项目,配置依赖。

    • 导入rabbit就导入stream-rabbit;导入kafka就导入stream-kafka。
    <!--导入stream-rabbit-->
    <dependency>
        <groupId>org.springframework.cloud</groupId>
        <artifactId>spring-cloud-starter-stream-rabbit</artifactId>
    </dependency>
    
    <!--添加eureka-client客户端-->
    <dependency>
        <groupId>org.springframework.cloud</groupId>
        <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
    </dependency>
    
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-web</artifactId>
    </dependency>
    
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-actuator</artifactId>
    </dependency>
    
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-devtools</artifactId>
        <scope>runtime</scope>
        <optional>true</optional>
    </dependency>
    
    <dependency>
        <groupId>org.projectlombok</groupId>
        <artifactId>lombok</artifactId>
        <optional>true</optional>
    </dependency>
    
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-test</artifactId>
        <scope>test</scope>
    </dependency>
    
    <dependency>
        <groupId>com.itholmes.springcloud</groupId>
        <artifactId>cloud-api-commons</artifactId>
        <version>$project.version</version>
    </dependency>
    

    第二步:配置yml文件。

    • 要注意mq是本地还是云服务器。
    server:
      port: 8801
    
    
    # 如果是使用的自己的服务器来配置,则需要修改配置文件,将rabbitmq的配置信息移动到application.yml中的spring节点下
    spring:
      application:
        name: cloud-stream-provider
      # 设置云服务器的mq
      rabbitmq:
        host: 150.158.199.52
        port: 5672
        username: "admin"
        password: "0818"
      cloud:
        stream:
          binders: # 在此处配置要绑定的rabbitmq的服务信息;
            defaultRabbit: # 表示定义的名称,用于于binding整合
              type: rabbit # 消息组件类型
          #          environment: # 设置本地rabbitmq的相关的环境配置
          #            spring:
          #              rabbitmq:
          #                host: localhost
          #                port: 5672
          #                username: guest
          #                password: guest
          bindings: # 服务的整合处理
            output: # 这个名字是一个通道的名称
              destination: studyExchange # 表示要使用的Exchange名称定义
              content-type: application/json # 设置消息类型,本次为json,文本则设置“text/plain”
              binder: defaultRabbit  # 设置要绑定的消息服务的具体设置
    
    eureka:
      client: # 客户端进行Eureka注册的配置
        service-url:
          defaultZone: http://localhost:7001/eureka
    #  instance:
    #    lease-renewal-interval-in-seconds: 2 # 设置心跳的时间间隔(默认是30秒)
    #    lease-expiration-duration-in-seconds: 5 # 如果现在超过了5秒的间隔(默认是90秒)
    #    instance-id: send-8801.com  # 在信息列表时显示主机名称
    #    prefer-ip-address: true     # 访问的路径变为IP地址
    

    第三步:搭建service层。

    • 使用注解来配置,发送消息如下一样。
    package com.itholmes.springcloud.service.impl;
    
    import com.itholmes.springcloud.service.IMessageProvider;
    import org.springframework.cloud.stream.annotation.EnableBinding;
    import org.springframework.cloud.stream.messaging.Source;
    import org.springframework.messaging.MessageChannel;
    import org.springframework.messaging.support.MessageBuilder;
    
    import javax.annotation.Resource;
    import java.util.UUID;
    
    
    /**
     * @author: itholmes
     * @description:
     *      @EnableBinding注解: 指信道channel和exchange绑定在一起。
     *      Source.class的作用定义消息的推送管道。
     * @date: 2022/8/3 22:52
     */
    @EnableBinding(Source.class)
    public class MessageProviderImpl implements IMessageProvider 
    
        // 消息发送管道
        @Resource
        private MessageChannel output;
    
        @Override
        public String send() 
            String serial = UUID.randomUUID().toString();
            output.send(MessageBuilder.withPayload(serial).build());
            System.out.println("*****serial:" + serial);
            return null;
        
    
    
    

    第四步:注入controller层。

    package com.itholmes.springcloud.controller;
    
    import com.itholmes.springcloud.service.IMessageProvider;
    import org.springframework.web.bind.annotation.GetMapping;
    import org.springframework.web.bind.annotation.RestController;
    
    import javax.annotation.Resource;
    
    /**
     * @author: itholmes
     * @description: TODO
     * @date: 2022/8/3 23:02
     */
    @RestController
    public class SendMessageController 
    	
    	//直接注入进来就可以
        @Resource
        private IMessageProvider messageProvider;
    
        @GetMapping(value = "/sendMessage")
        public String sendMessage()
            return messageProvider.send();
        
    
    
    

    8. SpringCloud Stream 之 消息驱动 搭建消费者


    第一步:创建项目,导入依赖。

    <dependency>
        <groupId>org.springframework.cloud</groupId>
        <artifactId>spring-cloud-starter-stream-rabbit</artifactId>
    </dependency>
    
    <!--添加eureka-client客户端-->
    <dependency>
        <groupId>org.springframework.cloud</groupId>
        <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
    </dependency>
    
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-web</artifactId>
    </dependency>
    
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-actuator</artifactId>
    </dependency>
    
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-devtools</artifactId>
        <scope>runtime</scope>
        <optional>true</optional>
    </dependency>
    
    <dependency>
        <groupId>org.projectlombok</groupId>
        <artifactId>lombok</artifactId>
        <optional>true</optional>
    </dependency>
    
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-test</artifactId>
        <scope>test</scope>
    </dependency>
    
    <dependency>
        <groupId>com.itholmes.springcloud</groupId>
        <artifactId>cloud-api-commons</artifactId>
        <version>$project.version</version>
    </dependency>
    

    第二步:配置application.yml文件。

    • 与上面不同的是,这里是input接受。
    server:
      port: 8802
    
    # 如果是使用的自己的服务器来配置,则需要修改配置文件,将rabbitmq的配置信息移动到application.yml中的spring节点下
    spring:
      application:
        name: cloud-stream-provider
      rabbitmq:
        host: 150.158.199.52
        port: 5672
        username: "admin"
        password: "0818"
      cloud:
        stream:
          binders: # 在此处配置要绑定的rabbitmq的服务信息;
            defaultRabbit: # 表示定义的名称,用于于binding整合
              type: rabbit # 消息组件类型
          bindings: # 服务的整合处理
            input: # 这个名字是一个通道的名称 , 这里是接受!!!
              destination: studyExchange # 表示要使用的Exchange名称定义
              content-type: application/json # 设置消息类型,本地为json,文本就是text/plain
              binder: defaultRabbit # 设置要绑定的消息服务的具体设置
    
    
    # 服务注册到eureka地址
    eureka:
      client:
        service-url:
          defaultZone: http://localhost:7001/eureka
      instance:
        lease-renewal-interval-in-seconds: 2 # 设置心跳的时间间隔(默认30秒)
        lease-expiration-duration-in-seconds: 5 # 如果现在超过了5秒间隔(默认90秒)
        instance-id: receive-8802.com # 在信息列表时显示主机名称
        prefer-ip-address: true # 访问的路径变为IP地址
    
    

    第三步:创建启动类,创建controller层Sink接受。

    package com.itholmes.springcloud.controller;
    
    import org.springframework.beans.factory.annotation.Value;
    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;
    import org.springframework.stereotype.Component;
    
    /**
     * @description:
     *      注解:&

    以上是关于springcloud学习总结的主要内容,如果未能解决你的问题,请参考以下文章

    Spring Cloud 与微服务学习总结(15)—— Spring Cloud 2021.0.1 发布

    SpringCloud学习总结——服务熔断Hystrix高级

    SpringCloud学习总结——服务注册中心Consul

    SpringCloud学习总结——服务注册中心Eureka基础

    spring-cloud-kubernetes官方demo运行实战

    SpringCloud开发学习总结—— 结合注解的AOP示例