SpringCloud-实用篇(1)

Eureka注册中心

微服务远程调用

Eureka

-提供者与消费者

  • 服务提供者:一次业务中,被其他微服务调用的服务。【提供接口给其他微服务】

  • 服务消费者:一次业务中,调用其他微服务的服务。【调用其他微服务提供的接口】

  • 提供者与消费者角色其实是相对的

Eureka的作用

36ecee84289c448abead589613ce7d69.png

在Eureka架构中,微服务角色有两类:

EurekaServer:服务端,注册中心

  • 记录服务信息

  • 心跳监控

EurekaClient:客户端

1. Provider:服务提供者

  • 注册自己的信息到EurekaServer

  • 每隔30秒向EurekaServer发送心跳

2. Consumer:服务消费者

  • 根据服务名称从EurekaServer拉取服务列表

  • 基于服务列表做负载均衡,选中一个微服务后发起远程调用

EurekaServer搭建

33e641363e214ecc84b50492606e5e9a.png

注册eureka

ca4d7822d7a04cef9cb6a6789980fbc9.png

在order-service完成服务拉取

服务拉取是基于服务名称获取服务列表,如何在对服务列表做负载均衡

c8bc6ff4cb77491295b35351256d6c22.png

小结

dd908bb6b2b14e678bd0da4fa914dfa8.png

Ribbon负载均衡

负载均衡流程

a5ba9d3024f6422c9b4ef66cab7408e1.png

1d55a804b5364345b81b5767996317c5.png

负载均衡策略

内置负载均衡规则类规则描述
RoundRobinRule简单轮询服务列表来选择服务器。它是Ribbon默认的负载均衡规则
AvailabilityFilteringRule对以下两种服务器进行忽略:(1)在默认情况下,这台服务器如果3次连接失败,这台服务器就会被设置“短路”状态。短路状态将持续30秒,如果再次连接失败,短路的持续时间就会几何级的增加。(2)并发数过高的服务器。如果一个服务器的并发连接数过高,配置了AvaliabilityFilteringRule规则的客户端也会将其忽略。并发连接数的上线,可以由客户端的<clientName>.<clientConfigNameSpace>.ActiveConnectionsLimit属性
weightedResponseTimeRule为每个服务器赋予一个权重值。服务器响应时间越长,这个服务器的权重越小。这个规则会随机选择服务器,这个权重值会影响服务器的选择。
ZoneAvoidanceRule以区域可用的服务器为基础进行服务器的选择。使用Zone对服务器进行分类,这个Zone可以理解为一个机房,一个机架等。而后在对Zone内的多个服务器做轮询
BestAvailableRule忽略哪些短路的服务器,并选择并发数较低的服务器
RandomRule随机选择一个可用的服务器
RetryRule重试机制的选择逻辑

通过定义IRule【高版本Cloud已弃用】实现可以修改负载均衡规则,有两种方式:

  1. 代码方式:定义一个新的IRule

  2. 配置文件方式:

     userservice:
      ribbon:
         NFloadBalancerRuleClassName: com.netflix.loadbalancerr.RandomRule #负载均衡规则

     

饥饿加载

Ribbon默认是采用懒加载,即第一次访问时才会去创建LoadBalanceClient,请求时间会很长

而饥饿加载则会在项目启动时创建,降低第一次访问的耗时,通过下面的配置开启饥饿加载:

 ribbon:
  eager-load:
   enabled: true #开启饥饿加载
   clients: userservice #指定对userservice这个服务饥饿加载

Nacos注册中心

认识Nacos

Nacos是阿里巴巴的产品,现在是SpringCloud中的一个组件。相比于Eureka功能更加丰富,在国内受欢迎程度较高

Nacos服务分级存储模型

95b08842fa264ff4ab3133e90683f9d3.png

  1. Nacos服务分级存储模型

  • 一级是服务,例如userservice

  • 二级是集群,例如杭州。上海

  • 三级是实例,例如杭州机房的某台部署userservice的服务器

  1. 如何设置实例的集群属性

    修改application.yml文件,添加spring.cloud.nacos.discovery.cluster-name属性即可

Nacos负载均衡策略

NacosRule负载均衡策略

  • 优先选择同集群服务实例列表

  • 本地集群找不到提供者,才回去其他集群中寻找,并且会报警告

  • 确定了可用实例列表之后,再采取随即负载均衡挑选实例

在applicatio.yml设置负载均衡的IRule为NacosRule,这个规则优先会寻找与自己同集群的服务:

 userservice #服务名称
  ribbon:
     NFLoadBalancerRuleClassName: com.alibaba.cloud.nacos.ribbon.NacosRule #负载均衡规则

根据权重负载均衡

  1. 在Nacos控制台可以设置实例的权重值,首先选中实例后面的编辑按钮

实例的权重控制

  • Nacos控制台可以设置实例的权重值,0~1之间

  • 同集群之间的多个实例,权重越高被访问的频率越高

  • 权重设置为0则完全不会被访问

环境隔离 -namespace

Nacos中服务存储和数据存储的最外层都是一个名为namespace的东西,用来做最外层隔离

  • namespace用来做环境隔离

  • 每个namespace都有唯一id

  • 不同namespace下的服务不可见

Nacos和Eureka的对比

  1. Nacos与eureka的共同点

    1. 都支持服务注册和服务拉取

    2. 都支持服务提供者心跳方式做健康检测

  2. Nacos和Eureka的区别

    1. Nacos支持服务端主动检测提供者状态:临时实例采用心跳模式,非临时实例采用主动检测模式

    2. 临时实例心跳不正常会被剔除,非临时实例则不会被剔除

    3. Nacos支持服务列表变更的消息推送模式,服务列表更新更及时

    4. Nacos集群默认采用AP方式,当集群中存在非临时实例时,采用CP方式;Eureka采用AP方式

Nacos配置管理

统一配置管理

将配置交给Nacos管理的步骤

  1. 再Nacos中添加配置文件

  2. 在微服务中引入nacos的config依赖

  3. 在微服务中添加bootstrap.yml ,配置nacos地址、当前环境、服务名称、文件后缀名。这些决定了程序启动时nacos读取哪个文件

注:如果启动时报错,需要再pom.xml文件中添加如下依赖

 <dependency>
      <groupId>org.springframework.cloud</groupId>
      <artifactId>spring-cloud-starter-bootstrap</artifactId>
 </dependency>

配置热更新

Nacos中的配置文件变更后,微服务无需重启就可以感知。不过需要通过下面两种配置实现:

方式一:

在@Value注入的变量所在类上添加注解@RefreshScope

3b3260132afc44b89abbb98ac90c94e3.png

方式二:

使用@ConfigurationProperties注解

6203aac194f04bb596e3db5bfa85f11e.png

总结:

c3b0ebae640843d8802835c25806b02d.png

多种配置的优先级:

服务名-profile.yaml > 服务名称.yaml > 本地配置

bd083303fe4944b7ad56a4b5258d52da.png

nacos集群搭建:

见nacos集群搭建

HTTP客户端Feign

Feign是一个声明式的http客户端,其作用就是帮助我们优雅的实现http请求的发送。

定义和使用Feign客户端

使用Feign的步骤如下:

  1. 引入依赖

     <dependency>
         <groupId>org.springframework.cloud</groupId>
         <artifactId>spring-cloud-starter-openfeign</artifactId>
     </dependency>

     

  2. 在需要的启动类上添加@EnableFeignClients 开启Feign的功能

  3. 编写Feign客户端

    50aad4dc60bd4ece86c2ed535e7e7e50.png

主要是基于SpringMVC的注解来声明远程调用的信息,比如:

  • 服务名称:userservice

  • 请求方式:GET

  • 请求路径:/user/{id}

  • 请求参数:Longd id

  • 返回值类型: User

自定义Feign的配置

类型作用说明
feign.Logger.Level修改日志级别包含四种不同的级别:NONE、BASIC、HEADERS、FULL
feign.code.Decoder响应结果的解析器http远程调用的结果做解析例如解析json字符串为Java对象
feign.code.Encoder请求参数编码将请求参数编码,便于通过http请求发送
feign.Contract支持的注解格式默认是SpringMVC的注解
feign.Retryer失败重试机制请求失败的重试机制,默认是没有,不过会使用Ribbon的重试

一般我们需要配置的就是日志级别

配置Feign日志有两种方式:

方式一:配置文件方式

d42f852658f348ee9101e6eb5a7afabe.png

方式二:Java代码的方式,需要先声明一个Bean:

6f32c0a4282b4f79a0839cfaf57a142b.png

Feign的性能调优

Feign底层的客户端实现:

  • URLConnection:默认实现,不支持连接池

  • Apache HttpClient:支持连接池

  • OKHttp:支持连接池

因此优化Feign的性能主要包括:

  • 使用连接池代替默认的URLConnection

  • 日志级别,最好用basic或者none

Feign的性能优化-连接池配置

Feign添加HttpClient的支持

7b5b635fe32c46c2a11c69fb14e86d3b.png

Feign的最佳实践

  • 方式一(继承):给消费者的FeignClient和提供者的controller定义统一的父接口作为标准

  • 方式二(抽取):将FeignClient抽取为独立模块,并且把接口有关的POJO、默认的Feign配置都放到这个模块中,提供给所有消费者用

当定义的FeignClient不在SpringBootApplication的扫描包范围时,这些FeignClient无法使用。有两种方式解决:

eecfc096acb7402ba47281354ea609c7.png

统一网关Gateway

网关的功能:

  • 身份认证和权限校验

  • 服务路由、负载均衡

  • 请求限流

0f339d66928b492b999b10b72353e99b.png

网关的技术实现

在SpringCloud中网关的实现包括两种:

  • gateway

  • zuul

Zuul是基于Servlet的实现,属于阻塞时编程。而SpringCloudGateway则是基于Spring5中提供的WebFlux,属于响应式编程,具备更好的性能

搭建网关服务

步骤:

  1. 创建一个新的module,引入SpringCloudGateway的依赖和nacos的服务发现依赖:

  2. 编写路由配置即nacos地址

1a44e6c3bb2549d3a9e27976470097c2.png

3. 722d9abddae645e7875ea07cb426624c.png

 

 

搭建网关服务

de09d512d2be4ade90ea26d458c065e4.png

路由断言工厂Route Predicate Factory

网关路由可以配置的内容包括:

  • 路由id:路由的唯一标识

  • uri:路由目的地,支持lb和http两种

  • predicates:路由断言,判断请求是否符合要求,符合则转发到路由目的地

  • filters:路由过滤器,处理请求响应

我们在配置文件中写的断言规则只是字符串,这些字符串会被Predicate Factory读取并处理,转变为路由判断的条件

Spring提供了11种基本的Predicate工厂:

2f101283524a4fd483e0a5db3440a9a7.png

路由过滤器(GatewayFilter)

GatewayFilter是网关中提供的一种过滤器,可以对进入网关的请求和微服务返回的响应做处理:

f8b28f3bbdfa46b08a2a329a857c9f86.png

Spring提供了31种不同的路由过滤器工厂。例如:

fb0d205d29ef489b9bc1ef1fbe01fc00.png

全局过滤器 GlobalFilter

全局过滤器的作用是处理一切进入网关的请求和微服务响应,与GatewayFilter的作用一样。

区别在于GatewayFilter通过配置定义,处理逻辑是固定的。而GlobalFilter的逻辑需要自己写代码实现。

定义方式是实现GlobalFilter接口

1dea573cbd5a43ee954aab9d52459c7a.png

小结

  1. 全局过滤器的作用是什么?

  • 对所有路由都生效的过滤器,并且可以自定义处理逻辑

  1. 实现全局过滤器的步骤?

  • 实现GlobalFilter接口

  • 添加@Order注解或实现Ordered接口

  • 编写处理逻辑

过滤器的执行顺序

请求进入网关会碰到三类过滤器:当前路由的过滤器、DefaultFilter、GlobalFilter

请求路由后,会将当前路由过滤器和DefaultFilter、GlobbalFilter,合并到一个过滤器链【集合】中,排序后依次执行每个过滤器

ce9e59524f124cdca1ffcd30faad2ada.png

  • 每一个过滤器都必须指定一个int类型的order的值,order值越小,优先级越高,执行顺序越靠前。

  • GlobalFilter通过实现Ordered接口,或者添加@Order注解来指定order的值,由我们自己指定。

  • 路由过滤器和defaultFilter的order由Spring指定,默认按照声明的顺序从1递增。

  • 当过滤器的order的值是一样时,会按照 defaultFilter > 路由过滤器 > GlobalFilter顺序执行。

跨域问题处理

跨域: 域名不一致就是跨域,主要包括:

跨域问题:浏览器禁止请求的发起者与服务端发生跨域ajax请求,请求被浏览器拦截的问题

解决方案:CORS

网关处理跨域采用的同样是CORS方案,并且只需要简单配置即可实现:

fc2308dc890348fa8ec997043b0174d4.png

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

叫一只啦啦

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值