热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

《人人都是架构师》笔记

警惕Dubbo因超时和重试引起的系统雪崩答:1、超时时间一定要设置,要根据业务场景而定,设置太短容易引发重试,设置太长容易引发请求堆积。2、超时设置过短的后果:Dubbo默认失败重试
警惕Dubbo因超时和重试引起的系统雪崩
答:
1、超时时间一定要设置,要根据业务场景而定,设置太短容易引发重试,设置太长容易引发请求堆积。
2、超时设置过短的后果:Dubbo默认失败重试2次,所以假设有1000个并发,都超时了,则会重试2次,变成3000个请求,导致请求流量翻了3倍。
3、重试设置:写服务一般要考虑幂等性,所以失败后不进行重试。
4、Dubbo重试的集中容错方案:
a、failover(失败重试其他服务节点,通常用于读操作)
b、failfast(失败立即报错,通常用于幂等性的写操作)
c、failsafe(失败直接忽略,通常用于记录日志)
d、failback(失败定时重发,通产惯用于消息通知)
e、forking(并行调用多个节点,成功1个即返回,通常用于实时性要求高的操作)

服务治理的三个基础要素
答:
1、服务的动态注册与发现
2、服务的扩容实现
3、服务的升/降级处理
4、Dubbo的管理控制台中服务治理包含的功能:路由规则、动态配置、服务降级、访问控制、权重调节以及负载均衡等

JVM性能调优的矛盾:吞吐量和低延迟
答:
如果吞吐量优先,那么GC就必然会比较少进行垃圾回收,会达到一定程度才进行垃圾回收,相对的就需要花费更长的暂停时间来执行内存回收;反之,如果低延迟优先,则会频繁地执行垃圾回收,又会导致程序吞吐量的下降。

分布式调用跟踪系统的实现原理(依据Google的Dapper论文)
答:
1、Trace表示一次请求的完整调用链追踪。
2、Span用于体现服务与服务之间的一次调用,所以多个服务之间调用,Span就能体现具体的依赖关系。
3、每一次请求都会分配一个全局唯一的TraceID,整个调用链中所有的Span都会获取到同一个TraceID。
4、一般采集的数据信息包括TraceID、SpanID和ParentSpanID、RpcContext中包含的数据信息、服务执行异常时的对战信息、以及Trace中各个Span过程的开始和结束时间,这些数据信息都是需要在Trace的上下文信息中进行传递的。

基于Dubbo实现分布式调用跟踪系统方案
答:
1、目前主流的跟踪系统有:淘宝的EagleEye,嵌入HSF框架、Twitter的Zipkin,嵌入Finagle框架。
2、Dubbo提供了专门用于拦截RPC请求的Filter接口,不过目前Dubbo的Filter并没有纳入Spring的IOC容器管理,所以配置可以查看文档或书pg26
3、主要的类:由Invocation派生可以传递当前Trace上下文信息的RpcInvocation和临时状态记录器RpcContext
4、执行流程:
a、当服务调用方向服务提供方发起RPC请求时,Filter会对服务调用方法进行拦截,然后视图从ThreadLocal中获取当前线程的Trace上下文信息,当服务调用方向服务提供方发起RPC请求时,Filter会对服务调用方法进行拦截,然后视图从ThreadLocal中获取当前线程的Trace上下文信息,如果不存在则说明是根调用,需要生成TraceID,然后将生成的TraceID、SpanID设置在Invocation中传递给服务提供方,接着执行前置数据上报(开始时间维度为Client Send Time)。当调用Invoker接口的invoke()方法执行完远程服务方法后,再执行后置数据收集上报(结束时间维度为Clinet Receive Time)。
b、当RPC请求到达服务提供方后,Filter会对其拦截,然后从Invocation中获取由服务调用方传递过来的Trace上下文信息,并将其存储到当前线程的ThreadLocal中,然后执行前置数据收集上报(开始时间维度为Server Receive Time)。当调用Invoker接口的invoke()方法执行完服务方法后,再执行后置数据收集上报(结束时间维度为Server Send Time),最后还要删除存储在ThreadLocal中当前线程的Trace上下文信息。
c、收集到的信息通过发送消息队列,再异步持久化到数据库中。数据量大的放Hbase,量不大的可以放mysql即可,不过需要定时清除。
5、当并发量太大时,全跟踪记录损耗较大,可以只对其中一些请求进行采样跟踪(比如1/1000,1000个请求才记录1个),采样率可以配置在配置中心动态更改。

大流量和高并发的常规应对手段
答:
扩容、动静分离、缓存、服务降级和限流

限流的常用算法和实践思路
答:
1、目前主流的算法主要有三种:令牌桶算法、漏桶算法和计数器算法
2、令牌桶算法:主要限制流量的流入速率,允许出现一定程度的突发流量。Nginx的限流模块就是使用的这种算法实现的。
a、每秒会有r个令牌按照固定速率放入桶中
b、桶的容量是固定不变的,如果桶满了再放入令牌,则溢出
c、若桶中的可用令牌不足,则改请求会被进行限流处理(被抛弃或缓存)
3、漏桶算法:主要限制流量的流出速率,并且流出速率是固定不变的
a、可以以任意速率向桶中流入水滴
b、桶的容量是固定不变的,如果桶满了则溢出
c、按照固定的速率从桶中流出水滴
4、Google的Guava也实现了基于令牌桶算法那样的平均速率限流,RateLimiter抽象类。
5、Nginx可以使用限流模块在接入层实现令桶牌算法限流,
a、limit_zone 定义每个IP的session空间大小
b、limit_zeq_zone 定义每个IP每秒允许发起的请求数
c、limit_conn 定义每个IP能够发起的并发连接数
d、limit_req 等待处理的请求队列数量
6、生产环境中的商品抢购可以使用计数器算法,具体不同的sku限流规则配置在配置中心内,支持动态更改。可抢购次数的扣减操作,既可以用redis,也可以用JVM。如果是集群并且选择用JVM,则要根据总并发数量除以集群数量,得出单台机器的并发数。(比如总并发数5000,集群机器10台,则每台机器的并发为5000/10=500).

ActiveMQ和RocketMQ的对比
答:
1、两者都能用于分布式系统的解耦,ActiveMQ使用于企业级内部系统,RocketMQ使用大流量、高并发的互联网项目,所以还起到了流量削峰的作用。
2、ActiveMQ定位用于企业级应用服务,所以使用于用户规模较小的场景。遵循JMS规范,由JMS Provider、Provider和Consumer三者构成,其中JMS Provider负责消息路由和消息传递。主要支持的消息模型:点对点和发布/订阅两种模型。
3、RocketMQ的基本流程参考pg63,由NameServer(注册中心)、Boker(消息服务端)、Producer和Consumer构成。具有的基本特点:
a、支持顺序消息
b、支持事务消息
c、支持集群(点对点)与广播(发布/订阅)模式
d、亿级消息堆积能力
e、完善的分布式特性
f、支持Push与Pull两种消息订阅模式

用Zookeeper实现配置中心
答:
1、Zookeeper提供了配置管理(发布/订阅)、分布式协调/通知、分布式锁以及命名等服务,利用Zookeeper提供的一系列接口,能够实现一致性、Leader选举以及分布式配置管理平台等功能。
2、Zookeeper的数据模型中,每个子节点成为Znode,每个Znode都有一个全局唯一的路径作为标识,进行数据的读写操作。每个Znode都会维护一个版本号,版本号会随着每次数据的变更自动递增,这个特性可以避免并发带来的不一致性问题。
3、实现方案:将配置信息发布到Znode目录上后,有客户端负责信息订阅,利用长连接进行Watch,一旦配置信息发生变更,实现Watchr接口的process()方法将会感知到相应的时间,并进行相应的处理。Zookeeper采用的是类似于UNIX的文件系统目录,每个Znode都可以存储数据信息,并且还可以包含子节点(瞬时节点除外)

堆外内存off-heap的使用
答:
NIO网络通信框架Netty和消息中间件RocketMQ等都使用了ByteBuffer.allocateDirect()方法来操作实际的物理内存资源

Redis集群
答:
1、吞吐量:Redis单点TPS达到8万/秒,QPS达到10万/秒。
2、集群原理:Redis集群节点(主节点)中一共包含16384个Slot,不同的Redis节点内各自维护其中一小段Slot用于存储不同区间的数据。当根据key进行读/写操作时,redis会根据crc16的算法得出一个结果然后把结果对16384求余数,这样每个key都会对应一个编号在0-16383之间的哈希槽,通过这个值,去找到对应的插槽所对应的节点,然后直接自动跳转到这个对应的节点上进行存取操作。
3、集群投票机制:所有master参与,如果半数以上master节点与master节点通信超时,认为当前master节点挂掉。每一个节点都存有这个集群所有主节点以及从节点的信息。节点与节点之间通过ping-pong来进行心跳连接。
4、集群不可用的情况:
a、集群中任意master挂掉,且当前master没有slave
b、集群中超过半数以上master挂掉

抢购商品高并发读需求
答:
对于一件抢购商品的流量来说,因为key是同一个,所以流量必然会都引入到同一个redis缓存节点中,这时就容易出现单点故障。因此有下面两种解决方式:
1、在每个master节点都挂slave从节点,当主节点挂了可以自动顶上
2、多级Cache方案,多用LocalCache来过滤掉一部分流量。
a、本地缓存一般之缓存一些热点商品数据,缓存内容一般是商品详情和商品库存。
b、本地缓存跟分布式缓存的同步一般有两种方式:一种是定时主动拉取更新策略。这种会存在一定时间的不一致,要视业务情况而定,例如库存,暂时的不一致导致超卖,单到真正下单的时候还会再进行库存的判断,所以影响较小,可以接受。这种方式要注意关掉缓存的定时失效,防止当用户流量突然过大,都到分布式缓存中拉取数据;第二种方式是每次商品更新,都发布一个消息,订阅此消息的节点监听到后再更新本地缓存的内容。

实时热点自动发现方案
答:
可以将交易系统产生的相关数据,以及在上游系统中埋点上报的相关数据异步写入日志系统中,然后通过实时热点自动发现平台对收集到的日志数据做调用次数统计和热点分析。数据符合热点条件后,就立即通知交易系统做好热点保护。

redis使用watch命令实现高并发抢购需求
答:
1、一般高并发这里,不用悲观锁,会迅速增加系统资源;而使用队列,容易造成请求堆积,内存效果过快。所以一般使用乐观锁,可以用redis的watch命令实现
2、watch命令会监视给定的key,当exec时,如果监视的key从调用watch后发生过变化,则事务会失败。注意watch的可以是对整个连接有效的,事务也一样。如果连接断开,监视和事务都会被自动清除。当然exec,discard,unwatch命令都会清除连接中的所有监视。

mysql主从切换过程中保证数据一致性方案
答:
1、在Master的TPS较高的情况下,主从同步的延迟肯定是非常大的,因此为了避免数据库读写分离后应用层无法从Slave拉到实时数据,通常可以在写入Master之前也将数据落到缓存中;
2、在TPS不高的情况下,可以开启mysql5.5版本后开启的半同步复制功能。当事务提交到Master后,Master会等待Slave的回应,待Slave回应收到Binlog后,Master才会响应请求方已经完成事务。但是当Master实例宕机后,Slave成为新的Master时,主从数据库之间数据肯定还是会出现不一致,这时为了避免手动比对Binlog来确保主从数据的一致性,可以是用mysql5.6版本开始提供的GRID(全局事务ID)特性。由于新Master是之前的Slave,而宕机后的Master在重启后可以作为Slave存在,可以依靠GTID特性来保证主从之间数据的最终一致性。

mysql单表在500W数据量的读写性能
答:
1、读会受到慢慢变慢,即使有索引
2、写是顺序写,跟表数据一般没什么关系,主要是跟表的索引多少有关,所以还是差别不大

对于分布式事务或者异构表的数据一致性方案:
答:
1、分布式事务中,要求最终一致性即可,不用强一致性。
2、保障最终一致性的方案一般有监测补偿机制(线上监测补偿和线下监测补偿两种)和异步同步(跟Mysql的主从同步同理),以数据写入表A和表B为例
a、线上监测补偿:当数据成功写入表A后,立即将消息1写入消息队列中。然后再继续将数据写入表B,写入成功后也马上将消息2写入消息队列中。然后有一个消费者监听这两个消息1和2,如果消费者消费到消息1后在指定时间范围内没有收到消息2,则认为数据已经产生不一致,需要执行补偿操作。不一致的窗口期相对较短。
b、线下监测补偿:当数据成功写入表A后,立即将消息1写入到log1中。然后再继续将数据写入表B,写入成功后也马上将消息2写入log2中。然后有一个Job程序不停地增量对比log1和log2,如果出现数据不一致的情况,则进行数据补偿。不一致的窗口期相对较长。
c、参照mysql的主从同步机制,利用Canal订阅mysql的Binlog日志。

推荐阅读
  • 一次上线事故,30岁+的程序员踩坑经验之谈
    本文主要介绍了一位30岁+的程序员在一次上线事故中踩坑的经验之谈。文章提到了在双十一活动期间,作为一个在线医疗项目,他们进行了优惠折扣活动的升级改造。然而,在上线前的最后一天,由于大量数据请求,导致部分接口出现问题。作者通过部署两台opentsdb来解决问题,但读数据的opentsdb仍然经常假死。作者只能查询最近24小时的数据。这次事故给他带来了很多教训和经验。 ... [详细]
  • [译]技术公司十年经验的职场生涯回顾
    本文是一位在技术公司工作十年的职场人士对自己职业生涯的总结回顾。她的职业规划与众不同,令人深思又有趣。其中涉及到的内容有机器学习、创新创业以及引用了女性主义者在TED演讲中的部分讲义。文章表达了对职业生涯的愿望和希望,认为人类有能力不断改善自己。 ... [详细]
  • 本文介绍了Hyperledger Fabric外部链码构建与运行的相关知识,包括在Hyperledger Fabric 2.0版本之前链码构建和运行的困难性,外部构建模式的实现原理以及外部构建和运行API的使用方法。通过本文的介绍,读者可以了解到如何利用外部构建和运行的方式来实现链码的构建和运行,并且不再受限于特定的语言和部署环境。 ... [详细]
  • 解决Cydia数据库错误:could not open file /var/lib/dpkg/status 的方法
    本文介绍了解决iOS系统中Cydia数据库错误的方法。通过使用苹果电脑上的Impactor工具和NewTerm软件,以及ifunbox工具和终端命令,可以解决该问题。具体步骤包括下载所需工具、连接手机到电脑、安装NewTerm、下载ifunbox并注册Dropbox账号、下载并解压lib.zip文件、将lib文件夹拖入Books文件夹中,并将lib文件夹拷贝到/var/目录下。以上方法适用于已经越狱且出现Cydia数据库错误的iPhone手机。 ... [详细]
  • phpcomposer 那个中文镜像是不是凉了 ... [详细]
  • 2018深入java目标计划及学习内容
    本文介绍了作者在2018年的深入java目标计划,包括学习计划和工作中要用到的内容。作者计划学习的内容包括kafka、zookeeper、hbase、hdoop、spark、elasticsearch、solr、spring cloud、mysql、mybatis等。其中,作者对jvm的学习有一定了解,并计划通读《jvm》一书。此外,作者还提到了《HotSpot实战》和《高性能MySQL》等书籍。 ... [详细]
  • Activiti7流程定义开发笔记
    本文介绍了Activiti7流程定义的开发笔记,包括流程定义的概念、使用activiti-explorer和activiti-eclipse-designer进行建模的方式,以及生成流程图的方法。还介绍了流程定义部署的概念和步骤,包括将bpmn和png文件添加部署到activiti数据库中的方法,以及使用ZIP包进行部署的方式。同时还提到了activiti.cfg.xml文件的作用。 ... [详细]
  • Sleuth+zipkin链路追踪SpringCloud微服务的解决方案
    在庞大的微服务群中,随着业务扩展,微服务个数增多,系统调用链路复杂化。Sleuth+zipkin是解决SpringCloud微服务定位和追踪的方案。通过TraceId将不同服务调用的日志串联起来,实现请求链路跟踪。通过Feign调用和Request传递TraceId,将整个调用链路的服务日志归组合并,提供定位和追踪的功能。 ... [详细]
  • 2021最新总结网易/腾讯/CVTE/字节面经分享(附答案解析)
    本文分享作者在2021年面试网易、腾讯、CVTE和字节等大型互联网企业的经历和问题,包括稳定性设计、数据库优化、分布式锁的设计等内容。同时提供了大厂最新面试真题笔记,并附带答案解析。 ... [详细]
  • 生产环境下JVM调优参数的设置实例
     正文前先来一波福利推荐: 福利一:百万年薪架构师视频,该视频可以学到很多东西,是本人花钱买的VIP课程,学习消化了一年,为了支持一下女朋友公众号也方便大家学习,共享给大家。福利二 ... [详细]
  • java布尔字段用is前缀_POJO类中布尔类型的变量都不要加is前缀详解
    前言对应阿里巴巴开发手册第一章的命名风格的第八条。【强制】POJO类中布尔类型的变量都不要加is前缀,否则部分框架解析会引起序列化错误。反例:定义为基本 ... [详细]
  • Java工程师书单(初级,中级,高级)
    简介怎样学习才能从一名Java初级程序员成长为一名合格的架构师,或者说一名合格的架构师应该有怎样的技术知识体系,这是不仅一个刚刚踏入职场的初级程序员也是工作一两年之后开始迷茫的程序 ... [详细]
  • MybatisPlus入门系列(13) MybatisPlus之自定义ID生成器
    数据库ID生成策略在数据库表设计时,主键ID是必不可少的字段,如何优雅的设计数据库ID,适应当前业务场景,需要根据需求选取 ... [详细]
  • 大厂首发!思源笔记docker
    JVMRedisJVM面试内存模型以及分区,需要详细到每个区放什么?GC的两种判定方法GC的三种收集方法:标记清除、标记整理、复制算法的 ... [详细]
  • 前面刚有AWS开战MongoDB,双方“隔空互呛”,这厢又曝出2亿+简历信息泄露——MongoDB的这场开年似乎“充实”得过分了些。长期以来,作为“最受欢迎的NoSQL数据库”,M ... [详细]
author-avatar
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有