zoukankan      html  css  js  c++  java
  • (转)Spring Cloud(一)

    (二期)22、微服务框架spring cloud(一)

    【课程22】spirng c...简介.xmind54KB

    【课程22】spirng cl...架构.xmind0.5MB

    【课程22】负载均...eign.xmind46.2KB

    【课程22】基于rest...服务.xmind25.2KB

    【课程22】微服务.xmind63.6KB

    【课程22】注册中...reka.xmind0.7MB

    什么是微服务

    微服务英文名称Microservice,Microservice架构模式就是将整个Web应用组织为一系列小的Web服务。这些小的Web服务可以独立地编译及部署,并通过各自暴露的API接口相互通讯。它们彼此相互协作,作为一个整体为用户提供功能,却可以独立运行扩展。

    需要功能或使用场景

    1:我们把整个系统根据业务拆分成几个子系统

     2:每个子系统可以部署多个应用,多个应用之间使用负载均衡

     3:需要一个服务注册中心,所有的服务都在注册中心注册,负载均衡也是通过在注册中心注册的服务来使用一定策略来实现。

     4:所有的客户端都通过同一个网关地址访问后台的服务,通过路由配置,网关来判断一个URL请求由哪个服务处理。请求转发到服务上的时候也使用负载均衡。

     5:服务之间有时候也需要相互访问。例如有一个用户模块,其他服务在处理一些业务的时候,要获取用户服务的用户数据。

     6:需要一个断路器,及时处理服务调用时的超时和错误,防止由于其中一个服务的问题而导致整体系统的瘫痪。

     7:还需要一个监控功能,监控每个服务调用花费的时间等。

    设计原则
    • 单一职责原则
    • 服务自治原则
    • 轻量级通信机制
    • 跨语言、平台
    • 通信体量轻,如REST
    • 微服务粒度
    基于rest风格的微服务
    项目例子见代码

    可以试用spring的restTemplate做rest远程调用。

    • 主要使用RestTemplate完成rest调用

    (服务提供者)

    (服务调用者)

    优缺点
    • 适用场景有局限,服务提供者对我接口不能发生变化,会直接影响到消费者。
    • 服务容灾不法保证,容易造成服务雪崩
    • 适合较为简单微服务系统
    什么是spirngCloud

    spring cloud 为开发人员提供了快速构建分布式系统的一些工具,包括配置管理、服务发现、断路器、路由、微代理、事件总线、全局锁、决策竞选、分布式会话等等。它运行环境简单,可以在开发人员的电脑上跑。另外说明spring cloud是基于springboot的,所以需要开发中对springboot有一定的了解。

    开发工具集合,含有多个项目。

    简化了分布式开发。

    • 利用Spring boot的开发便利
    • 主要是基于对Netfix开源组件的进一步封装
    核心特性
    • 分布式/版本化配置
    • 服务注册和发现
    • 路由
    • 服务和服务之间的调用
    • 负载均衡
    • 断路器
    • 分布式消息传递

    这些特性都是由不同的组件来完成,在架构的演进过程中扮演着重要的角色

    特点

    1:约定优于配置

    2:开箱即用、快速启动

    3:与springboot紧密结合

    4:轻量级的组件

    5:组件支持丰富,功能齐全

    整体结构图

    从上图可以看出Spring Cloud各个组件相互配合,合作支持了一套完整的微服务架构。 

    • 其中Eureka负责服务的注册与发现,很好将各服务连接起来
    • Hystrix 负责监控服务之间的调用情况,连续多次失败进行熔断保护。
    • Hystrix dashboard,Turbine 负责监控 Hystrix的熔断情况,并给予图形化的展示
    • Spring Cloud Config 提供了统一的配置中心服务
    • 当配置文件发生变化的时候,Spring Cloud Bus 负责通知各服务去获取最新的配置信息
    • 所有对外的请求和服务,我们都通过Zuul来进行转发,起到API网关的作用
    • 监控我们使用Sleuth+Zipkin+springAdmin将所有的请求数据记录下来,方便我们进行后续分析

    Spring Cloud Config:配置管理开发工具包,可以让你把配置放到远程服务器,目前支持本地存储、Git以及Subversion。

    Spring Cloud Bus:事件、消息总线,用于在集群(例如,配置变化事件)中传播状态变化,可与Spring Cloud Config联合实现热部署。

    Spring Cloud Netflix:针对多种Netflix组件提供的开发工具包,其中包括Eureka、Hystrix、Zuul、Archaius等。

    Netflix Eureka:云端负载均衡,一个基于 REST 的服务,用于定位服务,以实现云端的负载均衡和中间层服务器的故障转移。

    Netflix Hystrix:容错管理工具,旨在通过控制服务和第三方库的节点,从而对延迟和故障提供更强大的容错能力。

    Netflix Zuul:边缘服务工具,是提供动态路由,监控,弹性,安全等的边缘服务。

    Netflix Archaius:配置管理API,包含一系列配置管理API,提供动态类型化属性、线程安全配置操作、轮询框架、回调机制等功能。

    Spring Cloud for Cloud Foundry:通过Oauth2协议绑定服务到CloudFoundry,CloudFoundry是VMware推出的开源PaaS云平台。

     Spring Cloud Sleuth:日志收集工具包,封装了Dapper,Zipkin和HTrace操作。 

    Spring Cloud Data Flow:大数据操作工具,通过命令行方式操作数据流。

    Spring Cloud Security:安全工具包,为你的应用程序添加安全控制,主要是指OAuth2。

    Spring Cloud Consul:封装了Consul操作,consul是一个服务发现与配置工具,与Docker容器可以无缝集成。

    Spring Cloud Zookeeper:操作Zookeeper的工具包,用于使用zookeeper方式的服务注册和发现。

    Spring Cloud Stream:数据流操作开发包,封装了与Redis,Rabbit、Kafka等发送接收消息。

    Spring Cloud CLI:基于 Spring Boot CLI,可以让你以命令行方式快速建立云组件。

    注册中心-Eureka

    (心跳检测、健康检查、负载均衡等)

    Spring Cloud解决的第一个问题就是:服务与服务之间的解耦。很多公司在业务高速发展的时候,服务组件也会相应的不断增加。服务和服务之间有着复杂的相互调用关系,经常有服务A调用服务B,服务B调用服务C和服务D ...,随着服务化组件的不断增多,服务之间的调用关系成指数级别的增长。

    这样最容易导致的情况就是牵一发而动全身。经常出现由于某个服务更新而没有通知到其它服务,导致上线后惨案频发。这时候就应该进行服务治理,将服务之间的直接依赖转化为服务对服务中心的依赖。

    两个组件组成

    • Eureka Server注册中心
    • Eureka Client服务注册

    当然服务中心这么重要的组件一但挂掉将会影响全部服务,因此需要搭建Eureka集群来保持高可用性,生产中建议最少两台。随着系统的流量不断增加,需要根据情况来扩展某个服务,Eureka内部已经提供均衡负载的功能,只需要增加相应的服务端实例既可。那么在系统的运行期间某个实例挂了怎么办?Eureka内容有一个心跳检测机制,如果某个实例在规定的时间内没有进行通讯则会自动被剔除掉,避免了某个实例挂掉而影响服务。 

    因此使用了Eureka就自动具有了注册中心、负载均衡、故障转移的功能。 

    编写Eureka Server步骤

    第一步、导入Eurka坐标

    <parent>
       <groupId>org.springframework.boot</groupId>
       <artifactId>spring-boot-starter-parent</artifactId>
       <version>2.0.3.RELEASE</version>
       <relativePath/> <!-- lookup parent from repository -->
    </parent>
    
    
    <properties>
       <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
       <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
       <java.version>1.8</java.version>
       <spring-cloud.version>Finchley.RELEASE</spring-cloud.version>
    </properties>
    
    
    <dependencies>
       <dependency>
          <groupId>org.springframework.cloud</groupId>
          <artifactId>spring-cloud-starter-netflix-eureka-server</artifactId>
       </dependency>
    
    
       <!--actuator用于应用监控管理-->
       <dependency>
          <groupId>org.springframework.boot</groupId>
          <artifactId>spring-boot-starter-actuator</artifactId>
       </dependency>
    
    
       <dependency>
          <groupId>org.springframework.boot</groupId>
          <artifactId>spring-boot-starter-test</artifactId>
          <scope>test</scope>
       </dependency>
    </dependencies>
    
    
    <dependencyManagement>
       <dependencies>
          <dependency>
             <groupId>org.springframework.cloud</groupId>
             <artifactId>spring-cloud-dependencies</artifactId>
             <version>${spring-cloud.version}</version>
             <type>pom</type>
             <scope>import</scope>
          </dependency>
       </dependencies>
    </dependencyManagement>

    第二步、Applcation上添加注解

    #开启Eurka注册中心服务
    @EnableEurekaServer 

    第三步、在aplication.yml上配置Eureka注册信息

    server:
      port: 8761
    eureka:
      client:
        #  表示是否将自己注册到Eureka Servcer。
        register-with-eureka: false
        #  表示是否从Eureka Server获取注册信息
        fetchRegistry: false
        serviceUrl:
         #  设置Eureka Server交互的地址
          defaultZone: http://localhost:8761/eureka/
    spring:
      application:
        name: eureka-server-1

    第四步、启动项目,访问http://localhost:8761 可以访问到Eureka服务界面

    两个注解
    # 开启注册服务发现功能
    @EnableDiscoveryClient
    
    
    # 开启Eureka注册中心服务功能
    @EnableEurekaServer
    自我保护模式

    保护模式主要用于一组客户端和Eureka Server之间存在网络分区场景下的保护。一旦进入保护模式,Eureka Server将会尝试保护其服务注册表中的信息,不再删除服务注册表中的数据(也就是不会注销任何微服务)。

    默认情况下,如果Eureka Server在一定时间内没有接收到某个微服务实例的心跳,Eureka Server将会注销该实例(默认90秒)。但是当网络分区故障发生时,微服务与Eureka Server之间无法正常通信,以上行为可能变得非常危险了——因为微服务本身其实是健康的,此时本不应该注销这个微服务。

    Eureka通过“自我保护模式”来解决这个问题——当Eureka Server节点在短时间内丢失过多客户端时(可能发生了网络分区故障),那么这个节点就会进入自我保护模式。一旦进入该模式,Eureka Server就会保护服务注册表中的信息,不再删除服务注册表中的数据(也就是不会注销任何微服务)。当网络故障恢复后,该Eureka Server节点会自动退出自我保护模式。

    综上,自我保护模式是一种应对网络异常的安全保护措施。它的架构哲学是宁可同时保留所有微服务(健康的微服务和不健康的微服务都会保留),也不盲目注销任何健康的微服务。使用自我保护模式,可以让Eureka集群更加的健壮、稳定。

    自我保护的条件:

    一般情况下,微服务在Eureka上注册后,会30秒定期发送心跳,Eureka 通过心跳来判断微服务是否健康,同时会定期删除超过90秒没有发送心跳的服务。

    有2种情况会导致Eureka Server收不到微服务的心跳,

    1. 是微服务自身原因所致,比如故障或关闭;

    2. 是微服务与eureka之间的网络出现故障。

    通常(微服务自身的故障关闭)只会导致个别服务出现故障,一般不会出现大面积的故障,而(网络故障)通常会导致Eureka Server在短时间内无法收到大批心跳。

    考虑到这个区别,Eureka设定了一个阀值,当判断挂掉的服务的数量超过阀值时,Eureka Server认为很大程度上出现了网络故障,将不再删除心跳过期的服务。

    那这个阀值是多少呢?

    1. 15分钟之内是否低于85%;

    2. Eureka Server在运行期间,会统计心跳失败的比例在15分钟之内是否低于85%

    3. 这种算法叫着Eureka Server的自我保护模式。

    关闭自我保护模式(生产上不建议)

    (关闭了自我保护之后,然后需要几分钟才能把失效的客户端节点删掉)

    高可用

    作为一个注册中心,为了确保微服务能够正常的注册和发现,单机的eureka server肯定不能满足这样的需求,如果注册中心挂掉,那么线上的所有服务都会有影响,那么需要有一个高可用的eureka server来支撑。

    在eureka的服务治理设计中,所有的节点既是服务提供方,也是服务消费方,服务注册中心也是,那么eureka server的高可用实际上是将自己作为服务注册到其他的注册中心,这样可以形成一组相互注册的服务注册中心,可以实现服务清单的同步,达到高可用的目的。

    注册中心节点之间相互注册即可实现高可用部署。

    (相互注册)

    假如3个以上也一样,把其他的都注册到自己的server上面,用逗号隔开。客户端需要配置所有的Eureka server地址。

    (客户端)

    如此可以保证注册节点的高可用。

    原理

    在euerka 集群中如果某台服务器宕机,euerka没有zookeeper的选举leader规则过程,客户端请求会自动切换到新的euerka的节点上,当宕机的服务器从恢复后,euerka会从新将其纳入到euerka服务器集群中(实现高可用)

    注册中心地位

    客户端发现

    • eureka

    服务端发现

    • nginx
    • zookeeper
    添加权限控制

    eureka启动之后,可以通过链接直接访问到eureka。所以需要添加security。

    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-security</artifactId>
    </dependency>

    添加security的账号密码。

    spring:
      security:
        user:
          name: admin
          password: admin

    可以通过spring-boot-starter-sercurity对Eureka Server添加安全认证。默认情况下,将其添加到classpath后,会对每个请求进行CSRF检查。Eureka并不会生成CSRF token,所以需要关掉对/eureka/*路径下的检查:

    @Configuration
    @EnableWebSecurity
    public class WebSecurityConfig extends WebSecurityConfigurerAdapter {
    
    
        @Override
        protected void configure(HttpSecurity http) throws Exception {
            // 关闭csrf
            http.csrf().ignoringAntMatchers("/eureka/**");
            super.configure(http);
        }
    }

    客户端连接eureka的时候,defaultZone需要改动。

    eureka:
      client:
        # 设置Eureka Server交互的地址
        service-url:
          defaultZone: http://admin:admin@localhost:8761/eureka/
    客户端负载均衡-Ribbon

    Spring Cloud Ribbon是基于HTTP和TCP的客户端负载工具,它是基于Netflix Ribbon实现的。通过Spring Cloud的封装,可以轻松地将面向服务的REST模板请求,自动转换成客户端负载均衡服务调用。

    整合步骤

    步骤一:导入Ribbon坐标(其实可以不用加,client直接有)

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

    步骤二:为RestTemplate添加@@LoadBalanced注解,表示使用负载均衡算法

    @Bean
    //为RestTemplate整合Ribbon的负载均衡能力
    @LoadBalanced
    public RestTemplate restTemplate() {
        return new RestTemplate();
    }

    步骤三:eureka-client-2是被调用者的应用名称。名称为eureka-client-2应用的有多个。此时就会根据负载算法调用生产者。

    步骤四:改变负载均衡策略,配置形式,或者注解形式都可以(IRule)

    ORDER:
      ribbon:
        NFLoadBalancerRuleClassName: com.netflix.loadbalancer.RandomRule

    被调用方(生产者)可以通过注入loadBalancerClient查看当前端口。

    @Autowired
    private LoadBalancerClient loadBalancerClient;

    在Eureka server看到的效果:

    @LoadBalanced

    客户端负载均衡的使用

    LoadBalancerInterceptor

    自定义Ribbon配置
    脱离项目使用Ribbon

    service.ribbon.listOfServers

    声明式REST调用-Feign

    Feign可以创建声明式、模板化的HTTP客户端,进行微服务调用。使用简单,创建一个接口,然后在接口上添加一些注解,代码就完成了。

    代码如下:

    第一步、导入Feign坐标,并在Application上添加注解@EnableFeignClients表示开启Feign模块

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

    第二步 :创建一个Feign接口,并添加@FeignClient注解

    import com.itmuch.cloud.microserviceconsumermoviefeign.pojo.User;
    import org.springframework.cloud.openfeign.FeignClient;
    import org.springframework.web.bind.annotation.GetMapping;
    import org.springframework.web.bind.annotation.PathVariable;
    
    
    @FeignClient(name = "microservice-provider-user")
    public interface UserFeignClient {
    
    
        @GetMapping(value = "/{id}")
        User findById(@PathVariable("id") Long id);
    }

    第三步、controller上地方

        @Autowired
        private UserFeignClient userFeignClient;
    
    
        @GetMapping("/user/{id}")
        public User findById(@PathVariable Long id) {
            return this.userFeignClient.findById(id);
        }

    feign常见问题汇总:

  • 相关阅读:
    swift 上的 lazy
    oc runtime
    iOS布局
    ios微信支付 v3
    好用的工具
    自己曾经没注意的东西
    根据文字计算出label的高度
    项目swift的一些问题
    UIAppearance
    书签
  • 原文地址:https://www.cnblogs.com/free-wings/p/10095706.html
Copyright © 2011-2022 走看看