架构师之路-微服务的学习

Spring Cloud微服务框架

Spring Cloud是一系列框架的有序集合。
近些年来,微服务架构逐渐取代了单体架构,且这种趋势将会越来越流行。Spring Cloud是目前最常用的微服务开发框架。
设计目标
协调各个微服务,简化分布式系统开发。
优点:

  • 产出于Spring大家族,Spring在企业级开发框架中无人能敌,来头很大,可以保证后续的更新、完善
  • 组件丰富,功能齐全。Spring Cloud 为微服务架构提供了非常完整的支持。例如、配置管理、服务发现、断路器、微服务网关等;
  • Spring Cloud 社区活跃度很高,教程很丰富,遇到问题很容易找到解决方案
  • 服务拆分粒度更细,耦合度比较低,有利于资源重复利用,有利于提高开发效率
  • 可以更精准的制定优化服务方案,提高系统的可维护性
  • 减轻团队的成本,可以并行开发,不用关注其他人怎么开发,先关注自己的开发
  • 微服务可以是跨平台的,可以用任何一种语言开发
  • 适于互联网时代,产品迭代周期更短

缺点:

  • 微服务过多,治理成本高,不利于维护系统
  • 分布式系统开发的成本高(容错,分布式事务等)对团队挑战大

Spring Cloud 的核心组件

  • Spring Cloud Config
    集中配置管理工具,分布式系统中统一的外部配置管理,默认使用Git来存储配置,可以支持客户端配置的刷新及加密、解密操作。
  • Spring Cloud Netflix
    Netflix OSS 开源组件集成,包括Eureka、Hystrix、Ribbon、Feign、Zuul等核心组件。
  • Spring Cloud Bus
    用于传播集群状态变化的消息总线,使用轻量级消息代理链接分布式系统中的节点,可以用来动态刷新集群中的服务配置。
  • Spring Cloud Consul
  • Spring Cloud Security
    安全工具包,对Zuul代理中的负载均衡OAuth2客户端及登录认证进行支持。
  • Spring Cloud Sleuth
    Spring Cloud应用程序的分布式请求链路跟踪,支持使用Zipkin、HTrace和基于日志(例如ELK)的跟踪。
  • Spring Cloud Stream
    轻量级事件驱动微服务框架,可以使用简单的声明式模型来发送及接收消息,主要实现为Apache Kafka及RabbitMQ。
  • Spring Cloud Task
    用于快速构建短暂、有限数据处理任务的微服务框架,用于向应用中添加功能性和非功能性的特性。
  • Spring Cloud Gateway
    Spring Cloud Gateway是Spring Cloud官方推出的第二代网关框架,取代Zuul网关。网关作为流量的,在微服务系统中有着非常作用,网关常见的功能有路由转发、权限校验、限流控制等作用。
Eureka(注册中心)
gateway (网关)

1.1 什么是API网关
API网关可以看做系统与外界联通的入口,我们可以在网关进行处理一些非业务逻辑的逻辑,比如权限验证,监控,缓存,请求路由等等。
1.2 为什么需要API网关
RPC协议转成HTTP。
请求路由
统一鉴权
统一监控
流量控制,熔断降级
1.3 统一API网关
统一技术组件升级
统一服务接入
节约资源
2.1 异步化请求
Tomcat/Jetty+NIO+servlet3
Netty+NIO
2.2 链式处理
在我们的各个框架中对此模式都有实现,比如servlet里面的filter,springmvc里面的Interceptor。
在Netflix Zuul中也应用了这种模式
这种模式在网关的设计中我们可以借鉴到自己的网关设计:
preFilters:前置过滤器,用来处理一些公共的业务,比如统一鉴权,统一限流,熔断降级,缓存处理等,并且提供业务方扩展。
routingFilters: 用来处理一些泛化调用,主要是做协议的转换,请求的路由工作。
postFilters: 后置过滤器,主要用来做结果的处理,日志打点,记录时间等等。
errorFilters: 错误过滤器,用来处理调用异常的情况。
2.3 业务隔离
2.3.1 信号量隔离
2.3.2 线程池隔离
2.3.3 集群隔离
2.4 请求限流
2.5 熔断降级
2.6 泛化调用
2.7 管理平台

ribbon(负载均衡)

负载平衡旨在优化资源使用,最大化吞吐量,最小化响应时间并避免任何单一资源的过载。使用多个组件进行负载平衡而不是单个组件可能会通过冗余来提高可靠性和可用性。

Hystrix(熔断器)

Hystrix 是一个延迟和容错库,旨在隔离远程系统,服务和第三方库的访问点,当出现故障是不可避免的故障时,停止级联故障并在复杂的分布式系统中实现弹性。

雪崩

A为服务提供者, B为A的服务调用者, C和D是B的服务调用者. 当A的不可用,引起B的不可用,并将不可用逐渐放大C和D时, 服务雪崩就形成了。

熔断 降级 限流 区别

熔断
在分布式系统中,我们往往需要依赖下游服务,不管是内部系统还是第三方服务,如果下游出现问题,我们不在盲目地去请求,在一个周期内失败达到一定次数,不在请求,及时失败。过一段时间,在逐步放开请求,这样既能防止不断的调用,使下游服务更坏,保护了下游方,还能降低自己的执行成本,快速的响应,减少延迟,增加吞吐量。比如:Hystrix
降级
降级就是为了解决资源不足和访问量增加的矛盾
在有限的资源情况下,为了能抗住大量的请求,就需要对系统做出一些牺牲,有点“弃卒保帅”的意思。放弃一些功能,保证整个系统能平稳运行。比如:抢购可以占时限流评论,将流量让给秒杀业务
限流
通过对并发访问进行限速。最简单的方式,把多余的请求直接拒绝掉,做的高大上一些,可以根据一定的用户规则进行拒绝策略

RPC

什么是RPC?

RPC 就是 Remote Procedure Call,远程过程调用,它相对应的是本地过程调用。

RPC的实现原理

整个调用过程,主要经历如下几个步骤:
1、建立通信
2、服务寻址
3、网络传输 序列化 反序列化
4、服务调用

PRC架构组件

一个基本的RPC架构里面应该至少包含以下4个组件:
1、客户端(Client):服务调用方(服务消费者)
2、客户端存根(Client Stub):存放服务端地址信息,将客户端的请求参数数据信息打包成网络消息,再通过网络传输发送给服务端
3、服务端存根(Server Stub):接收客户端发送过来的请求消息并进行解包,然后再调用本地服务进行处理
4、服务端(Server):服务的真正提供者

RPC调用过程

在这里插入图片描述

1、服务消费者(client客户端)通过本地调用的方式调用服务
2、客户端存根(client stub)接收到调用请求后负责将方法、入参等信息序列化(组装)成能够进行网络传输的消息体
3、客户端存根(client stub)找到远程的服务地址,并且将消息通过网络发送给服务端
4、服务端存根(server stub)收到消息后进行解码(反序列化操作)
5、服务端存根(server stub)根据解码结果调用本地的服务进行相关处理
6、本地服务执行具体业务逻辑并将处理结果返回给服务端存根(server stub)
7、服务端存根(server stub)将返回结果重新打包成消息(序列化)并通过网络发送至消费方
8、客户端存根(client stub)接收到消息,并进行解码(反序列化)
9、服务消费方得到最终结果

RPC主流框架

RMI:
JAVA自带的远程方法调用工具,不过有一定的局限性,毕竟是JAVA语言最开始时的设计,后来很多框架的原理都基于RMI,RMI的使用
Hessian:
基于HTTP协议传输,在性能方面还不够完美,负载均衡和失效转移依赖于应用的负载均衡器
架构图:
在这里插入图片描述

Dubbo:
开源的基于TCP的RPC框架
基于Netty的高性能RPC框架,是阿里巴巴开源的
架构图:
在这里插入图片描述

RPC使用了哪些关键技术?

1、动态代理
成 client stub和server stub需要用到 Java 动态代理技术 ,我们可以使用JDK原生的动态代理机制,可以使用一些开源字节码工具框架 如:CgLib、Javassist等。
2、序列化
为了能在网络上传输和接收 Java对象,我们需要对它进行 序列化和反序列化操作。

  • 序列化:将Java对象转换成byte[]的过程,也就是编码的过程;
  • 反序列化:将byte[]转换成Java对象的过程;
    可以使用Java原生的序列化机制,但是效率非常低,推荐使用一些开源的、成熟的序列化技术,例如:protobuf、Thrift、hessian、Kryo、Msgpack
    关于序列化工具性能比较可以参考:jvm-serializers
    3、NIO
    当前很多RPC框架都直接基于netty这一IO通信框架,比如阿里巴巴的HSF、dubbo,Hadoop Avro,推荐使用Netty 作为底层通信框架。
    4、服务注册中心

RPC框架需要解决的问题?

1.应用都基于微服务化,实现资源调用离不开远程调用
2.一个服务可能有多个实例,你在调用时,要如何获取这些实例的地址呢?— 这时候就需要一个服务注册中心,从服务注册中心获取服务的实例列表,再从中选择一个进行调用。
3.选哪个调用好呢?这时候就需要负载均衡了,于是又得考虑如何实现复杂均衡
4.总不能每次调用时都去注册中心查询实例列表吧,这样效率多低呀,于是又有了缓存,有了缓存,就要考虑缓存的更新问题
5.客户端总不能每次调用完都干等着服务端返回数据吧,于是就要支持异步调用;
6.服务端的接口修改了,老的接口还有人在用,怎么办?总不能让他们都改了吧?这就需要版本控制了;
7.服务端总不能每次接到请求都马上启动一个线程去处理吧?于是就需要线程池;
8.服务端关闭时,还没处理完的请求怎么办?是直接结束呢,还是等全部请求处理完再关闭呢?
总结:
远程调用协议,注册中心,负载均衡,缓存,异步,版本控制,线程池,异常处理

RPC和SOA、SOAP、REST的区别

SOA:
SOA(面向服务的软件架构、Service Oriented Architecture),是一种软件设计模式。
因此SOAP、RPC、REST是对SOA的不同实现。
SOAP:
简单对象访问协议是交换数据的一种协议规范,是一种轻量的、简单的、基于XML(标准通用标记语言下的一个子集)的协议,它被设计成在WEB上交换结构化的和固化的信息。
REST:
表征状态转移(Representional State Transfer)。其宗旨是从资源的角度来观察整个网络,分布在各处的资源由URI确定,而客户端的应用通过URI来获取资源的表征。获得这些表征致使这些应用程序转变了其状态。随着不断获取资源的表征,客户端应用不断地在转变着其状态。
RPC:
RPC(Remote Procedure Call Protocol)——远程过程调用协议,它是一种通过网络从远程计算机程序上请求服务,而不需要了解底层网络技术的协议。
RPC协议假定某些传输协议的存在,如TCP或UDP,为通信程序之间携带信息数据

RPC和HTTP的区别

HTTP 只是传输协议,协议只是规范了一定的交流格式。
RPC 对比的是本地过程调用,是用来作为分布式系统之间的通信,它可以用 HTTP 来传输,也可以基于 TCP 自定义协议传输。

Dubbo

Dubbo是阿里巴巴开源的基于Java的高性能RPC分布式服务框架,现已成为 Apache 基金会孵化项目。

为什么要用Dubbo?

因为是阿里开源项目,国内很多互联网公司都在用,已经经过很多线上考验。
内部使用了 Netty、Zookeeper,保证了高性能高可用性。
分布式架构可以承受更大规模的并发流量。

Dubbo 核心功能有哪些?

面向接口的远程方法调用
Remoting:网络通信框架,提供对多种NIO框架抽象封装,包括“同步转异步”和“请求-响应”模式的信息交换方式。
智能容错和负载均衡
Cluster:服务框架,提供基于接口方法的透明远程过程调用,包括多协议支持,以及软负载均衡,失败容错,地址路由,动态配置等集群支持。
服务自动注册和发现
Registry:服务注册,基于注册中心目录服务,使服务消费方能动态的查找服务提供方,使地址透明,使服务提供方可以平滑增加或减少机器。

Dubbo 核心组件(节点角色)有哪些?

registry: 服务注册与发现的注册中心
provider: 服务提供者
consumer: 服务消费者
monitor: 统计服务调用次数,调用时间,监控中心
container: 服务运行容器
Dubbo: 服务器注册与发现的流程?

Dubbo 的整体架构设计有哪些分层?

接口服务层(Service): 该层与业务逻辑相关,根据 provider 和 consumer 的业务设计对应的接口和实现
配置层(Config): 对外配置接口,以 ServiceConfig 和 ReferenceConfig 为中心
服务代理层(Proxy): 服务接口透明代理,生成服务的客户端 Stub 和 服务端的 Skeleton,以 ServiceProxy 为中心,扩展接口为 ProxyFactory
服务注册层(Registry): 封装服务地址的注册和发现,以服务 URL 为中心,扩展接口为 RegistryFactory、Registry、RegistryService
路由层(Cluster): 封装多个提供者的路由和负载均衡,并桥接注册中心,以Invoker 为中心,扩展接口为 Cluster、Directory、Router和LoadBlancce
监控层(Monitor): RPC调用次数和调用时间监控,以 Statistics 为中心,扩展接口为 MonitorFactory、Monitor和MonitorService
远程调用层(Protocal): 封装 RPC 调用,以 Invocation 和 Result 为中心,扩展接口为 Protocal、Invoker和Exporter
信息交换层(Exchange): 封装请求响应模式,同步转异步。以Request和Response为中心,扩展接口为Exchanger、ExchangeChannel、ExchangeClient和ExchangeServer
网络传输层(Transport): 抽象 mina 和 netty 为统一接口,以 Message 为中心,扩展接口为Channel、Transporter、Client、Server和Codec
数据序列化层(Serialize): 可复用的一些工具,扩展接口为Serialization、 ObjectInput、ObjectOutput和ThreadPool
Dubbo的架构设计图:
在这里插入图片描述

Dubbo服务注册与发现的流程?

1)第一步,provider向注册中心去注册
2)第二步,consumer从注册中心订阅服务,注册中心会通知consumer注册好的服务
3)第三步,consumer调用provider
4)第四步,consumer和provider都异步的通知监控中心
在这里插入图片描述

Dubbo支持哪些协议,每种协议的应用场景,优缺点?

dubbo: 单一长连接和NIO异步通讯,适合大并发小数据量的服务调用,以及消费者远大于提供者。传输协议TCP,异步,Hessian序列化;
rmi: 采用JDK标准的rmi协议实现,传输参数和返回参数对象需要实现Serializable接口,使用java标准序列化机制,使用阻塞式短连接,传输数据包大小混合,消费者和提供者个数差不多,可传文件,输协议TCP。多个短连接,TCP协议传输,同步传输,适用常规的远程服务调用和rmi互操作。在依赖低版本的Common-Collections包,java序列化存在安全漏洞;
webservice: 基于WebService的远程调用协议,集成CXF实现,提供和原生WebService的互操作。多个短连接,基于HTTP传输,同步传输,适用系统集成和跨语言调用;
http: 基于Http表单提交的远程调用协议,使用Spring的HttpInvoke实现。多个短连接,传输协议HTTP,传入参数大小混合,提供者个数多于消费者,需要给应用程序和浏览器JS调用;
hessian: 集成Hessian服务,基于HTTP通讯,采用Servlet暴露服务,Dubbo内嵌Jetty作为服务器时默认实现,提供与Hession服务互操作。多个短连接,同步HTTP传输,Hessian序列化,传入参数较大提供者大于消费者,提供者压力较大,可传文件;
memcache: 基于memcached实现的RPC协议
redis: 基于redis实现的RPC协议

Dubbo 有哪些注册中心?

Multicast注册中心: Multicast注册中心不需要任何中心节点,只要广播地址,就能进行服务注册和发现。基于网络中组播传输实现;
Zookeeper注册中心: 基于分布式协调系统Zookeeper实现,采用Zookeeper的watch机制实现数据变更;
redis注册中心: 基于redis实现,采用key/Map存储,住key存储服务名和类型,Map中key存储服务URL,value服务过期时间。基于redis的发布/订阅模式通知数据变更;
Simple注册中心

Dubbo 的注册中心集群挂掉,发布者和订阅者之间还能通信么?

可以的,启动dubbo时,消费者会从zookeeper拉取注册的生产者的地址接口等数据,缓存在本地。
每次调用时,按照本地存储的地址进行调用。

Dubbo集群提供了哪些负载均衡策略?

Random LoadBalance: 随机选取提供者策略,有利于动态调整提供者权重。截面碰撞率高,调用次数越多,分布越均匀;
RoundRobin LoadBalance: 轮循选取提供者策略,平均分布,但是存在请求累积的问题;
LeastActive LoadBalance: 最少活跃调用策略,解决慢提供者接收更少的请求;
ConstantHash LoadBalance: 一致性Hash策略,使相同参数请求总是发到同一提供者,一台机器宕机,可以基于虚拟节点,分摊至其他提供者,避免引起提供者的剧烈变动;

Dubbo的集群容错方案有哪些?

failover cluster 失败自动切换,自动重试其他服务器(默认)
failfast cluster 一次失败就报错
failsafe cluster 忽略异常
failback cluster 失败自动恢复,记录异常,定时重试
forking cluster 并行调用多个服务,一个成功即可返回
broadcast cluster 广播逐个调用,一个报错则报错

Dubbo内置了哪些服务容器?

Spring Container
Jetty Container
Log4j Container

Dubbo有哪几种配置方式?

1)Spring 配置方式
2)Java API 配置方式

Dubbo 配置文件是如何加载到 Spring 中的?

Spring容器在启动的时候,会读取到Spring默认的一些schema以及Dubbo自定义的schema,
每个schema都会对应一个自己的NamespaceHandler,NamespaceHandler里面通过BeanDefinitionParser来解析配置信息并转化为需要加载的bean对象

可以配置的 Consumer 端的属性有哪些?

1)timeout:方法调用超时
2)retries:失败重试次数,默认重试 2 次
3)loadbalance:负载均衡算法,默认随机
4)actives 消费者端,最大并发调用限制

Dubbo核心的配置有哪些?

在这里插入图片描述

Dubbo 超时设置有哪些方式?

服务提供者端设置超时时间,在Dubbo的用户文档中,推荐如果能在服务端多配置就尽量多配置,因为服务提供者比消费者更清楚自己提供的服务特性。
服务消费者端设置超时时间,如果在消费者端设置了超时时间,以消费者端为主,即优先级更高。因为服务调用方设置超时时间控制性更灵活。如果消费方超时,服务端线程不会定制,会产生警告。

服务调用超时会怎么样?

dubbo在调用服务不成功时,默认是会重试两次的。

Dubbo 使用的是什么通信框架?

默认使用NIO Netty框架

服务上线怎么兼容旧版本?

可以用版本号(version)过渡,多个不同版本的服务注册到注册中心,版本号不同的服务相互间不引用。这个和服务分组的概念有一点类似。

Dubbo telnet 命令能做什么?

dubbo 服务发布之后,我们可以利用 telnet 命令进行调试、管理。Dubbo2.0.5 以上版本服务提供端口支持 telnet 命令
telnet localhost 20880 //键入回车进入 Dubbo 命令模式。

dubbo>ls
com.test.TestService
dubbo>ls com.test.TestService
create
delete
query
  • ls (list services and methods)
  • ls : 显示服务列表。
  • ls -l : 显示服务详细信息列表。
  • ls XxxService:显示服务的方法列表。
  • ls -l XxxService:显示服务的方法详细信息列表。

Dubbo 支持服务降级吗?

服务降级方式:
服务接口拒绝服务:无用户特定信息,页面能访问,但是添加删除提示服务器繁忙。页面内容也可在Varnish或CDN内获取。
页面拒绝服务:页面提示由于服务繁忙此服务暂停。跳转到varnish或nginx的一个静态页面。
延迟持久化:页面访问照常,但是涉及记录变更,会提示稍晚能看到结果,将数据记录到异步队列或log,服务恢复后执行。
随机拒绝服务:服务接口随机拒绝服务,让用户重试,目前较少有人采用。因为用户体验不佳。
通过mock的配置,可以很好的实现dubbo服务降级
(1)将接口进行归类,查询类和变更操作类:对于查询的分为一个接口类,变更的归类为其他的接口类,这样对于查询的可以使用mock="return null"进行降级操作;对于变更类的,可以仍旧使用try……catch进行异常捕获处理;
(2)配置mock=“true”,同时mock实现接口,接口名要注意命名规范:接口名+Mock后缀。此时如果调用失败会调用Mock实现。mock实现需要保证有无参的构造方法。

Dubbo 如何优雅停机?

Dubbo 是通过 JDK 的 ShutdownHook 来完成优雅停机的,所以如果用户使用 kill -9 PID 等强制关闭指令,是不会执行优雅停机的,只有通过 kill PID 时,才会执行。
优雅停机流程:

  • 首先,从注册中心中取消注册自己,从而使消费者不要再拉取到它。
  • 然后,sleep 10 秒( 可配 ),等到服务消费,接收到注册中心通知到该服务提供者已经下线,加大了在不重试情况下优雅停机的成功率。
  • 优先关闭自身对外提供的服务,然后关闭外部的引用,最后关闭幽灵链接(ghostClient)。【下面4-8步,是第3步的细分】
  • sendChannelReadOnlyEvent():将channel标记为只读, 内部实现是广播 READONLY 事件给所有 Consumer 们,告诉它们不要在调用我了!!!目的是如果此处注册中心挂掉的情况,依然能达到告诉 Consumer ,我要下线了的功能。
  • sleep 10 毫秒,保证 Consumer 们,尽可能接收到该消息。
  • 关闭心跳检测,不接收新请求,注册中心也检测不到该服务。
  • 检测线程池中的线程是否正在运行,如果有,等待所有线程执行完成,除非超时,则强制关闭。
  • 关闭真正的netty的通信通道,如果你是用的netty的话。

Dubbo SPI 和 Java SPI 区别?

JDK SPI
JDK 标准的 SPI 会一次性加载所有的扩展实现,如果有的扩展吃实话很耗时,但也没用上,很浪费资源。所以只希望加载某个的实现,就不现实了
DUBBO SPI
1,对 Dubbo 进行扩展,不需要改动 Dubbo 的源码
2,延迟加载,可以一次只加载自己想要加载的扩展实现。
3,增加了对扩展点 IOC 和 AOP 的支持,一个扩展点可以直接 setter 注入其
它扩展点。
4,Dubbo 的扩展机制能很好的支持第三方 IoC 容器,默认支持 Spring Bean。

Dubbo 支持分布式事务吗?

目前暂时不支持,可与通过 tcc-transaction 框架实现
分布式事务模型

  • TCC 模型:TCC-Transaction、Hmily
  • XA 模型:Sharding Sphere、MyCAT
  • 2PC 模型:raincat、lcn
  • MQ 模型:RocketMQ
  • BED 模型:Sharding Sphere
  • Saga 模型:ServiceComb Saga

Dubbo 可以对结果进行缓存吗?

为了提高数据访问的速度。Dubbo 提供了声明式缓存,以减少用户加缓存的工作量<dubbo:reference cache=“true” />
其实比普通的配置文件就多了一个标签 cache=“true”

Dubbo 必须依赖的包有哪些?

Dubbo 必须依赖 JDK,其他为可选。

Dubbo 支持哪些序列化方式?

Dubbo 在安全方面有哪些措施?

服务调用是阻塞的吗?

服务提供者能实现失效踢出是什么原理?
同一个服务多个注册的情况下可以直连某一个服务吗?
Dubbo 服务降级,失败重试怎么做?
Dubbo 使用过程中都遇到了些什么问题?

Dubbo与Spring的关系?

Dubbo采用全Spring配置方式,透明化接入应用,对应用没有任何API侵入,只需用Spring加载Dubbo的配置即可,Dubbo基于Spring的Schema扩展进行加载。

Dubbo支持哪些序列化方式?

默认使用Hessian序列化,还有Duddo、FastJson、Java自带序列化。

Dubbo和Spring Cloud的关系?

Dubbo是 SOA 时代的产物,它的关注点主要在于服务的调用,流量分发、流量监控和熔断。而 Spring Cloud诞生于微服务架构时代,考虑的是微服务治理的方方面面,另外由于依托了 Spirng、Spirng Boot
的优势之上,两个框架在开始目标就不一致,Dubbo 定位服务治理、Spirng Cloud 是一个生态。

Dubbo 和 Spring Cloud 有什么哪些区别?

最大的区别:
Dubbo底层是使用Netty这样的NIO框架,是基于TCP协议传输的,配合以Hession序列化完成RPC通信。
而SpringCloud是基于Http协议+Rest接口调用远程过程的通信,相对来说,Http请求会有更大的报文,占的带宽也会更多。但是REST相比RPC更为灵活,服务提供方和调用方的依赖只依靠一纸契约,不存在代码级别的强依赖,这在强调快速演化的微服务环境下,显得更为合适,至于注重通信速度还是方便灵活性,具体情况具体考虑。
最大的区别:Spring Cloud抛弃了Dubbo 的RPC通信,采用的是基于HTTP的REST方式

Dubbo Monitor 实现原理?

Consumer 端在发起调用之前会先走 filter 链;provider 端在接收到请求时也是先走 filter 链,然后才进行真正的业务逻辑处理。默认情况下,在 consumer 和 provider 的 filter 链中都会有 Monitorfilter。
1、MonitorFilter 向 DubboMonitor 发送数据
2、DubboMonitor 将数据进行聚合后(默认聚合 1min 中的统计数据)暂存到ConcurrentMap<Statistics, AtomicReference> statisticsMap,然后使用一个含有 3 个线程(线程名字:DubboMonitorSendTimer)的线程池每隔 1min 钟,调用 SimpleMonitorService 遍历发送 statisticsMap 中的统计数据,每发送完毕一个,就重置当前的 Statistics 的 AtomicReference
3、SimpleMonitorService 将这些聚合数据塞入 BlockingQueue queue 中(队列大写为 100000)
4、SimpleMonitorService 使用一个后台线程(线程名为:DubboMonitorAsyncWriteLogThread)将 queue 中的数据写入文件(该线程以死循环的形式来写)
5、SimpleMonitorService 还会使用一个含有 1 个线程(线程名字:DubboMonitorTimer)的线程池每隔 5min 钟,将文件中的统计数据画成图表

Dubbo 类似的分布式框架还有哪些?

别的还有 spring 的 spring cloud,facebook 的 thrift,twitter 的 finagle 等
Apache Thrift 主要用于各个服务之间的RPC通信,支持跨语言。thrift是一个典型的CS结构,客户端和服务端可以使用不同的语言开发,thrift通过IDL(Interface Description Language)来关联客户端和服务端。

Dubbo 用到哪些设计模式?

工厂模式
装饰器模式
观察者模式
动态代理模式

soa 分布式 微服务 之间有什么关系和区别?

分布式架构:面向服务架构(SOA)
SOA的两大基石:RPC和MQ
SOA关注于系统的服务化,不同系统服务间的相互通信就成为了一个重要的话题。并且随着RPC和MQ技术的发展,这两种技术逐渐成为SOA的两大基石,也是分布式技术体系里的重要基础设施。
分布式架构:微服务架构(MSA)
通过几个关键点可以看出微服务重在独立布署和独立业务,而所谓的微服务,并不是越小越好,而是通过团队规模和业务复杂度由粗到细的划分过程,所遵循的原则是松耦合和高内聚。

Zookeeper

ZooKeeper 是一个开源的分布式应用程序协调服务。

Zookeeper 的应用

数据发布/订阅、负载均衡、命名服务、分布式协调/通知、集群管理、Master 选举、分布式锁和分布式队列等功能。

Zookeeper 保证了如下分布式一致性特性

(1)顺序一致性
(2)原子性
(3)单一视图
(4)可靠性
(5)实时性(最终一致性)

Zookeeper 四种类型的数据节点 Znode

节点的特性

  • (1)PERSISTENT-持久节点
    默认的节点类型。创建节点的客户端与zookeeper断开连接后,该节点依旧存在。
  • (2)EPHEMERAL-临时节点
    和持久节点相反,当创建节点的客户端与zookeeper断开连接后,临时节点会被删除
  • (3)PERSISTENT_SEQUENTIAL-持久顺序节点
    在创建节点时,zookeeper根据创建的时间顺序给该节点名称进行编号
  • (4)EPHEMERAL_SEQUENTIAL-临时顺序节点
    在创建节点时,zookeeper根据创建的时间顺序给该节点名称进行编号排序(排序的节点形成一个类似队列)。当创建节点的客户端与zookeeper断开连接后,临时节点会被删除(解锁)

Zookeeper watch的机制

在zk中,可以设置一些监听,来监听节点的一些变化操作,做出响应。
绑定监听:getData、exists、getChildren
触发监听:create、delete、setData
查操作可以绑定监听,增、删、改可以绑定监听,且监听是一次性的,在触发一次会消失,可以循环绑定来达到一直监听的效果

Zookeeper 分布式锁

1、 利用在同级目录下,不能创建相同的节点特性,可以利用多线程去创建一个节点,但是只能有一个线程可以创建成功,所以该线程得到锁。释放锁:释放锁时,通过删除该节点,来触发刚才没有获取到的线程的监听,让他们再次来竞争获取。
结论:可以达到效果,但是如果有1000个线程发起竞争,那么在释放锁时会999个线程触发监听,重新发起创建节点的请求。性能上不够优化。羊群效应,产生过多不必要的开销。
2、利用有序的节点特性,可以让多个线程同时创建多个有序的节点,其中创建的节点最小的线程,可以获取本次的锁,在释放锁以后,删除节点,自动为排序的下一个节点获取锁。
结论:在之前的文章中,我们分析过独占锁的源码,在独占锁中,用阻塞队列来存放线程,同时在公平锁模式下,会优先用队列的第一个线程来获取锁。这里,就很类似,当001被删除后,002 就会顺势获取锁,依次获取。
方案2中的计划,简单实现了分布式锁。但是其中,没有实现重入锁,并且代码中没有只实现了公平锁,没有实现非公平锁。

InterProcessMutex
Curator是ZooKeeper的一个客户端框架,其中封装了分布式互斥锁的实现,最为常用的是InterProcessMutex。
在curator中,提供了各种基于zk的工具,locks、atomic、cache等等。

Zookeeper 通过Leader进行写操作

通过Leader进行写操作,主要分为五步:

  1. 客户端向Leader发起写请求
  2. Leader将写请求以Proposal的形式发给所有Follower并等待ACK
  3. Follower收到Leader的Proposal后返回ACK
  4. Leader得到过半数的ACK(Leader对自己默认有一个ACK)后向所有的Follower和Observer发送Commmit
  5. Leader将处理结果返回给客户端

这里要注意
Leader并不需要得到Observer的ACK,即Observer无投票权
Leader不需要得到所有Follower的ACK,只要收到过半的ACK即可,同时Leader本身对自己有一个ACK。上图中有4个Follower,只需其中两个返回ACK即可,因为(2+1) / (4+1) > 1/2
Observer虽然无投票权,但仍须同步Leader的数据从而在处理读请求时可以返回尽可能新的数据

Zookeeper 服务器角色

Leader
(1)事务请求的唯一调度和处理者,保证集群事务处理的顺序性
(2)集群内部各服务的调度者
Follower
(1)处理客户端的非事务请求,转发事务请求给 Leader 服务器
(2)参与事务请求 Proposal 的投票
(3)参与 Leader 选举投票
Observer
(1)3.0 版本以后引入的一个服务器角色,在不影响集群事务处理能力的基础上提升集群的非事务处理能力
(2)处理客户端的非事务请求,转发事务请求给 Leader 服务器
(3)不参与任何形式的投票

Zookeeper下Server 工作状态

服务器具有四种状态,分别是 LOOKING、FOLLOWING、LEADING、OBSERVING
(1)LOOKING:寻 找 Leader 状态。当服务器处于该状态时,它会认为当前集群中没有 Leader,因此需要进入 Leader 选举状态。
(2)FOLLOWING:跟随者状态。表明当前服务器角色是 Follower。
(3)LEADING:领导者状态。表明当前服务器角色是 Leader。
(4)OBSERVING:观察者状态。表明当前服务器角色是 Observer。

Zookeeper 怎么保证主从节点的状态同步?

Zookeeper Atomic Broadcast (Zookeeper原子广播)
Zookeeper 的核心是原子广播机制,这个机制保证了各个 server 之间的同步。实现这个机制的协议叫做 Zab 协议。Zab 协议有两种模式,它们分别是恢复模式和广播模式
恢复模式
当服务启动或者在领导者崩溃后,Zab就进入了恢复模式,当领导者被选举出来,且大多数 server 完成了和 leader 的状态同步以后,恢复模式就结束了。状态同步保证了 leader 和 server 具有相同的系统状态。
广播模式
一旦 leader 已经和多数的 follower 进行了状态同步后,它就可以开始广播消息了,即进入广播状态。这时候当一个 server 加入 ZooKeeper 服务中,它会在恢复模式下启动,发现 leader,并和 leader 进行状态同步。待到同步结束,它也参与消息广播。ZooKeeper 服务一直维持在 Broadcast 状态,直到 leader 崩溃了或者 leader 失去了大部分的 followers 支持。

zk和eureka的区别

CAP理论: C- 数据一致性;A-服务可用性;P-分区容错性

zk保证的是一致性和分区容错性

  • 它不能保证每次服务请求的可用性 (比如网络问题) (网络分割) ZooKeeper是分布式协调服务为ZooKeeper的核心实现算法 Zab,就是解决了分布式系统下数据如何在多个服务之间保持同步问题的。ZooKeeper本身并没有正确的处理网络分割的问题。ZooKeeper重新选取Leader时 ,它们就会从ZooKeeper中断开 就不能提供Service发现服务了。

eureka保证的是可用性和分区容错性

  • eureka的模式是client和server, 各个server之间是相互独立的,不存在leader.不用选举,就算其中一个server宕机了,只要还有一个server或活着,client都会把服务注册到这个活着的server上面,等宕机的活过来,就会把最新的一份信息同步给它,客户端请求会自动切换到新的Eureka节点
  • Eureka内置了心跳服务,用于淘汰一些“濒死”的服务器;(但是当网络分割故障发生时, 这也是非常危险的)
  • 如果Eureka服务节点在短时间里丢失了大量的心跳连 Eureka节点会进入”自我保护模式“,同时保留那些“心跳死亡“的服务注册信息不过期。
  • Eureka还有客户端缓存功能 所以即便Eureka集群中所有节点都失效,或者发生网络分割故障导致客户端不能访问任何一台Eureka服务器;Eureka服务的消费者仍然可以通过 Eureka客户端缓存来获取现有的服务注册信息。
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值