Kafka、Zookeeper、Flume、Hbase基本知识合集

目录

1.5 Kafka

1.5.0 Kafka基本组成:(重点)

1.5.1 kafka工作流程:(重点)

1.5.2 Kafka压测

1.5.3 Kafka的机器数量

1.5.4 Kafka的日志保存时间

1.5.5 Kafka的硬盘大小

1.5.6 Kafka监控

1.5.7 Kakfa分区数

1.5.8 副本数设定

1.5.9 多少个Topic

1.5.13 Kafka中数据量计算

1.5.11  Kafka的ISR副本同步队列(重点)

1.5.12 Kafka分区分配策略(重点)

1.5.16 Kafka幂等性

1.5.18 Kafka数据重复(重点)

1.5.14 Kafka挂掉

1.5.10 Kafka丢不丢数据(重点)

1.5.15 Kafka消息数据积压,Kafka消费能力不足怎么处理? 

1.5.19 Kafka参数优化

1.5.20 Kafka高效读写数据(重点)

1.5.17 Kafka事务(重点)

1.5.21 Kafka支持传输

1.5.22 Kafka过期数据清理

1.5.23 Kafka可以按照时间消费数据

1.5.24 Zookeeper中存储kafka哪些信息(重点)

1.5.25 kafka和RabbitMQ区别:

Zookeeper

角色及功能:(重点)

工作原理:

选举机制:(重点)

监听原理:(重点)

客户端命令行操作

为什么Zookeeper集群数一般为奇数:

Flume

1. 知道 Flume 的 Channel 是啥吗

2. 介绍⼀下 Memory Channel

3. 说说 File Channel

4. 说说 Kafka Channel

5. 介绍⼀下 Kafka ⼏种 Sink

6. 说说 Flume 的拦截器

7. 介绍⼀下什么是选择器

8. 了解 Flume 的负载均衡和故障转移吗

Hbase

1.7.2 RowKey设计原则

1.7.3 RowKey如何设计

1.HBase的操作数据的步骤

2.HDFS和HBase各⾃使⽤场景(重点)

3.热点现象及解决办法。(重点)

4.RowKey的设计原则?(重点)

5.hbase.hregion.max.filesize应该设置多少合适

6.autoflush=false的影响

7对于传统关系型数据库中的⼀张table,在业务转换到hbase上建模时,从性能的⾓度应该 如何设置family和qualifier呢?

8.Hbase⾏健/列族的概念,物理模型,表的设计原则?

9.HBase存储单元Cell?(重点)

10.说说HBase物理模型?(重点)

11.HBase的客户端Client?

12.介绍HBase⼆级索引?

13.每天百亿数据存⼊HBase,如何保证数据的存储正确和在规定的时间⾥全部录⼊完毕,不残留数据?

14.你知道哪些HBase优化⽅法(重点)

15.HRegionServer宕机如何处理?

16.HBase简单读写流程

17.HBase和Hive的对⽐(重点)

18.HBase与传统关系型数据库(如MySQL)的区别(重点)

19.什么时候适合使⽤HBase(应⽤场景)?(重点)

20.Client会缓存.META.的数据,该数据更新了怎么办?

21.请描述如何解决Hbase中region太⼩和region太⼤带来的冲突?

22.解释下 hbase 实时查询的原理(重点)

23.HBase 宕机如何处理?


1.5 Kafka


1.5.0 Kafka基本组成:(重点)

producer、comsumer、broker、zookeeper

1.5.1 kafka工作流程:(重点)

kafka中消息以topic分类,生产者生产消息,消费者消费消息,都是面向topic的

topic是逻辑的概念,而partition是物理的概念,每个partition对应于一个log文件,

该log文件中存储的就是producer生产的数据,Producer生产的数据会不断的追加到该log的末端,且每条数据都有自己的offset,

消息者组中每个消费者,都会实时记录自己消费到哪个offset,以便出错时,从上次的位置继续消费。

1.5.2 Kafka压测

Kafka官方自带压力测试脚本(kafka-consumer-perf-test.sh、kafka-producer-perf-test.sh)。Kafka压测时,可以查看到哪个地方出现了瓶颈(CPU,内存,网络IO)。一般都是网络IO达到瓶颈

1.5.3 Kafka的机器数量

Kafka机器数量=2*(峰值生产速度*副本数/100)+1

1.5.4 Kafka的日志保存时间

3(默认7天,生产环境下通常3天)

1.5.5 Kafka的硬盘大小

每天的数据量*3天/70%

1.5.6 Kafka监控

公司自己开发的监控器;

开源的监控器:KafkaManager、KafkaMonitorKafkaEagle

1.5.7 Kakfa分区数

1)创建一个只有1个分区的topic

2)测试这个topic的producer吞吐量和consumer吞吐量。

3)假设他们的值分别是Tp和Tc,单位可以是MB/s。

4)然后假设总的目标吞吐量是Tt,那么分区数=Tt / min(Tp,Tc)

例如:producer吞吐量=20m/s;consumer吞吐量=50m/s,期望吞吐量100m/s

分区数=100 / 20 =5分区

https://blog.csdn.net/weixin_42641909/article/details/89294698

分区数一般设置为:3-10

1.5.8 副本设定

一般我们设置成2个或3个,很多企业设置为2个

1.5.9 多少个Topic

   通常情况:多少个日志类型就多少个Topic也有日志类型进行合并的。

1.5.13 Kafka中数据量计算

每天总数据量100g,每天产生1亿日志, 10000万/24/60/60=1150条/秒钟

平均每秒钟:1150

低谷钟:50

高峰每秒钟:1150*(2-20=2300条-23000条

每条日志大小0.5k-2k(取1k

每秒多少数据量:2.0M-20MB

1.5.11  Kafka的ISR副本同步队列(重点)

ISR(In-Sync Replicas),副本同步队列。ISR中包括Leader和Follower。如果Leader进程挂掉,会在ISR队列中选择一个服务作为新的Leader。有replica.lag.max.messages(延迟条数)和replica.lag.time.max.ms(延迟时间)两个参数决定一台服务是否可以加入ISR副本队列,在0.10版本移除了replica.lag.max.messages参数,防止服务频繁的进去队列。

任意一个维度超过阈值都会把Follower剔除出ISR,存入OSR(Outof-Sync Replicas)列表,新加入的Follower也会先存放在OSR中。

1.5.12 Kafka分区分配策略(重点)

在 Kafka内部存在两种默认的分区分配策略:Range和 RoundRobin。

Range是默认策略。Range是对每个Topic而言的(即一个Topic一个Topic分),首先对同一个Topic里面的分区按照序号进行排序,并对消费者按照字母顺序进行排序。然后用Partitions分区的个数除以消费者线程的总数来决定每个消费者线程消费几个分区。如果除不尽,那么前面几个消费者线程将会多消费一个分区。

例如我们有10个分区,两个消费者(C1,C2),3个消费者线程,10 / 3 = 3而且除不尽。

C1-0 将消费 0, 1, 2, 3 分区

C2-0 将消费 4, 5, 6 分区

C2-1 将消费 7, 8, 9 分区

第一步:将所有主题分区组成TopicAndPartition列表,然后对TopicAndPartition列表按照hashCode进行排序,最后按照轮询的方式发给每一个消费线程。

1.5.16 Kafka幂等性

Producer的幂等性指的是当发送同一条消息时,数据在Server端只会被持久化一次,数据不丟不重,但是这里的幂等性是有条件的:

1)只能保证Producer在单个会话内不丟不重,如果Producer出现意外挂掉再重启是无法保证的(幂等性情况下,是无法获取之前的状态信息,因此是无法做到跨会话级别的不丢不重)。

2)幂等性不能跨多个Topic-Partition,只能保证单个Partition内的幂等性,当涉及多个 Topic-Partition时,这中间的状态并没有同步。

1.5.18 Kafka数据重复(重点)

幂等性+ack-1+事务

Kafka数据重复,可以再下一级:SparkStreamingredis或者hive中dwd层去重去重的手段:分组、按照id开窗只取第一个值;

1.5.14 Kafka挂掉

1)Flume记录

2)日志有记录

3)短期没事

重启即可

1.5.10 Kafka丢不丢数据(重点)

Ack=0,相当于异步发送,消息发送完毕即offset增加,继续生产。

Ack=1,leader收到leader replica 对一个消息的接受ack才增加offset,然后继续生产。

Ack=-1,leader收到所有replica 对一个消息的接受ack才增加offset,然后继续生产。

默认ack=1

1.5.15 Kafka消息数据积压,Kafka消费能力不足怎么处理? 

1如果是Kafka消费能力不足,则可以考虑增加Topic的分区数,并且同时提升消费组的消费者数量,消费者数=分区数。(两者缺一不可)

2)如果是下游的数据处理不及时:提高每批次拉取的数量。批次拉取数据过少(拉取数据/处理时间<生产速度),使处理的数据小于生产的数据,也会造成数据积压。

1.5.19 Kafka参数优化

 1)Broker参数配置(server.properties

1、网络和io操作线程配置优化

# broker处理消息的最大线程数(默认为3)

num.network.threads=cpu核数+1

# broker处理磁盘IO的线程数

num.io.threads=cpu核数*2

2、log数据文件刷盘策略

# 每当producer写入10000条消息时,刷数据到磁盘

log.flush.interval.messages=10000

# 每间隔1秒钟时间,刷数据到磁盘

log.flush.interval.ms=1000

3、日志保留策略配置

# 保留三天,也可以更短 (log.cleaner.delete.retention.ms)

log.retention.hours=72

4、Replica相关配置

offsets.topic.replication.factor:3

# 这个参数指新创建一个topic时,默认的Replica数量,Replica过少会影响数据的可用性,太多则会白白浪费存储资源,一般建议在2~3为宜。

2)Producer优化(producer.properties

buffer.memory:33554432 (32m)

#在Producer端用来存放尚未发送出去的Message的缓冲区大小。缓冲区满了之后可以选择阻塞发送或抛出异常,由block.on.buffer.full的配置来决定。

compression.type:none

#默认发送不进行压缩,推荐配置一种适合的压缩算法,可以大幅度的减缓网络压力和Broker的存储压力。

4Kafka内存调整(kafka-server-start.sh

默认内存1个G生产环境尽量不要超过6个G。

export KAFKA_HEAP_OPTS="-Xms4g -Xmx4g"

1.5.20 Kafka高效读写数据(重点)

1Kafka本身是分布式集群,同时采用分区技术,并发度高。

2)顺序写磁盘

Kafka的producer生产数据,要写入到log文件中,写的过程是一直追加到文件末端,为顺序写。官网有数据表明,同样的磁盘,顺序写能到600M/s,而随机写只有100K/s。这与磁盘的机械机构有关,顺序写之所以快,是因为其省去了大量磁头寻址的时间。

3)零复制技术

要拷贝的数据直接走内核,不经过应用层了。

1.5.17 Kafka事务(重点)

Kafka从0.11版本开始引入了事务支持。事务可以保证Kafka在Exactly Once语义的基础上,生产和消费可以跨分区和会话,要么全部成功,要么全部失败。

1)Producer事务

为了实现跨分区跨会话的事务,需要引入一个全局唯一的Transaction ID,并将Producer获得的PID和Transaction ID绑定。这样当Producer重启后就可以通过正在进行的Transaction ID获得原来的PID。

为了管理Transaction,Kafka引入了一个新的组件Transaction Coordinator。Producer就是通过和Transaction Coordinator交互获得Transaction ID对应的任务状态。Transaction Coordinator还负责将事务所有写入Kafka的一个内部Topic,这样即使整个服务重启,由于事务状态得到保存,进行中的事务状态可以得到恢复,从而继续进行。

2)Consumer事务

上述事务机制主要是从Producer方面考虑,对于Consumer而言,事务的保证就会相对较弱,尤其时无法保证Commit的信息被精确消费。这是由于Consumer可以通过offset访问任意信息,而且不同的Segment File生命周期不同,同一事务的消息可能会出现重启后被删除的情况。

1.5.21 Kafka支持传输

kafka对于消息体的大小默认为单条最大值是1M但是在我们应用场景中, 常常会出现一条消息大于1M,如果不对kafka进行配置。则会出现生产者无法将消息推送到kafka或消费者无法去消费kafka里面的数据, 这时我们就要对kafka进行以下配置:server.properties

 所以如果传输的日志文件是2M,那么kafka就会卡死。需要重新配置参数。

1.5.22 Kafka过期数据清理

保证数据没有被引用(没人消费他)

日志清理保存的策略只有delete和compact两种

log.cleanup.policy=delete启用删除策略

log.cleanup.policy=compact启用压缩策略

1.5.23 Kafka可以按照时间消费数据

Map<TopicPartition, OffsetAndTimestamp> startOffsetMap = KafkaUtil.fetchOffsetsWithTimestamp(topic, sTime, kafkaProp);

1.5.24 Zookeeper中存储kafka哪些信息(重点)

Kafka的broker的brokerid,comsumer,topics,partitions,副本信息

注意,zookeeper里唯独不存kafka的生产者的信息

1.5.25 kafka和RabbitMQ区别:

1、RabbitMQ,遵循AMQP协议,由内在高并发的erlanng语⾔开发,用在实时的对可靠性要求比较高的消息传递上(有消息确认机制)。
2、kafka是Linkedin于2010年12月份开源的消息发布订阅系统,它主要用于处理活跃的流式数据,大数据量的数据处理上(无消息确认机制,但吞吐量高),kafka用zk做集群负载均衡。

 

Zookeeper


角色及功能:(重点)

Leader+Learner(Follower+observer)

Leader:发起投票和决议,更新系统状态

Follower:接收客户端请求饼返回响应,参与投票

Observer:接受客户端连接,将写操作转发给L饿啊的人,不参与投票,只同步Leader

工作原理:

zookeeper=文件系统+通知机制

核心是原子广播  ---->  zab协议(恢复模式和广播模式)

恢复模式:当服务启动或Leader崩溃时进入恢复模式

广播模式:进行选举,当有了Leader且大多数server与leader同步时进入广播模式。若此时再加入一个节点,会在恢复模式下启动。广播模式需要proposal被按顺序处理——递增的事务id(zxid)+paxos算法(Master编写了个全局写队列,所有写操作必须放入到该队列编号,一旦发现编号执行顺序错乱,立即自动停止并重启同步过程)

选举机制:(重点)

半数通过原则

每个server启动后都询问其他server投给谁

每个server都回复投给自己饼附上自己最大的zxid

每个server计算出收到的最大的zxid并将其附带的server信息设为下一次要投票的对象

票数最多且已过半的server设为leader

监听原理:(重点)

客户端命令行操作

命令基本语法

功能描述

help

显示所有操作命令

ls path [watch]

使用 ls 命令来查看当前znode中所包含的内容

ls2 path [watch]

查看当前节点数据并能看到更新次数等数据

create

普通创建

-s  含有序列

-e  临时(重启或者超时消失)

get path [watch]

获得节点的值

set

设置节点的具体值

stat

查看节点状态

delete

删除节点

rmr

递归删除节点

为什么Zookeeper集群数一般为奇数:

3台和4台的容灾能力一样。zookeeper集群最少3台。

Flume


应用场景:将日志数据信息手机并移交到Hadoop/Kafka平台上去分析

构成:source 、Channel、Sink

事件Agent是 Flume内部传输的基本单元

1. 知道 Flume Channel 是啥吗

        1. Channel 被设计为 Event 中转临时缓冲区,存储 Source 收集并且没有被 Sink 读取的 Event ,为平衡 Source 收集和 Sink 读取的速度,可视为 Flume 内部的消息队列。
        2. Channel 线程安全并且具有事务性,⽀持 Source 写失败写,和 Sink 读失败重复读的操作。常⻅的类型包括 Memory Channel File Channel
Kafka Channel

2. 介绍⼀下 Memory Channel

读写速度快,但是存储数据量⼩, Flume 进程挂掉、服务器停机或者重启都
会导致数据丢失。资源充⾜、不关⼼数据丢失的场景下可以⽤。

3. 说说 File Channel

event 写⼊磁盘⽂件,与 Memory Channel 相⽐存储容量⼤,⽆数据丢失
⻛险。 File Channel 数据存储路径可以配置多磁盘⽂件路径,通过磁盘并⾏写⼊ 提⾼ File Channel 性能。 Flume Event 顺序写⼊到 File Channel ⽂件的末尾。
可以在配置⽂件中通过设置 maxFileSize 参数配置数据⽂件⼤⼩,当被写⼊的⽂
件⼤⼩达到上限的时候, Flume 会重新创建新的⽂件存储写⼊ Event 。当⼀个已
经关闭的只读数据⽂件的 Event 被读取完成,并且 Sink 已经提交读取完成的事
务,则 Flume 把存储该数据的⽂件删除。

4. 说说 Kafka Channel

Memory Channel 有很⼤的丢数据⻛险,⽽且容量⼀般 File Channel 虽然
能缓存更多的消息,但如果缓存下来的消息还没写⼊ Sink ,此时 Agent 出现故
障则 File Channel 中的消息⼀样不能被继续使⽤,直到该 Agent 恢复。⽽ Kafka Channel 容量⼤,容错能⼒强。
有了 Kafka Channel 可以在⽇志收集层只配置 Source 组件和 Kafka 组件,
不需要再配置 Sink 组件,减少了⽇志收集层启动的进程数,有效降低服务器内 存、磁盘等资源的使⽤率。⽽⽇志汇聚层,可以只配置 Kafka Channel
Sink ,不需要再配置 Source
kafka.consumer.auto.offset.reset ,当 Kafka 中没有 Consumer 消费的初始
偏移量或者当前偏移量在 Kafka 中不存在(⽐如数据已经被删除)情况下
Consumer 选择从 Kafka 拉取消息的⽅式, earliest 表示从最早的偏移量开始拉 取, latest 表示从最新的偏移量开始拉取, none 表示如果没有发 Consumer 组之前拉取的偏移量则抛出异常。

5. 介绍⼀下 Kafka ⼏种 Sink

1. HDFS Sink : Event 写⼊ HDFS ⽂件存储,能够有效⻓期存储⼤量数
据。
2. Kafka Sink : Flume 通过 Kafka Sink Event 写⼊到 Kafka 中的主题,其
他应⽤通过订阅主题消费数据。 kafka.producer.acks 可以设置 Producer
发送消息到 Broker 之后不需要等待 Broker 返回成功送达的信号。 0 表示
Producer 发送消息到 Broker 之后不需要等待 Broker 返回成功送达的信
号,这种⽅式吞吐量⾼,但存在丢失数据的⻛险。 1 表示 Broker 接收到消息
成功写⼊本地 log ⽂件后向 Producer 返回成功 接收的信号,不需要等待所
有的 Follower 全部同步完消息后再做回应,这种⽅式在数据丢失⻛险和吞
吐量之间做了平衡。 -1 表示 Broker 接收到 Producer 的消息成功写⼊本地
log 并且等待所有的 Follower 成功写⼊本地 log 后向 Producer 返回成功接
收的信号,这种⽅式能够保证消息不丢失,但是性能最差(层层递进)。

6. 说说 Flume 的拦截器

Source 将 Event 写⼊到 Channel 之前可以使⽤拦截器对 Event 进⾏各种形
式的处理 Source Channel 之间可以有多个拦截器,不同拦截器使⽤不同的 规则处理 Event ,包括时间、主机、 UUID 、正则表达式等多种形式的拦截器。

7. 介绍⼀下什么是选择器

Source 发送的 Event 通过 Channel 选择器来选择以哪种⽅式写⼊到 Channel
Flume 提供三种类型 Channel 选择器,分别是复制、复⽤和⾃定义选择
器。
1. 复制选择器 : ⼀个 Source 以复制的⽅式将⼀个 Event 同时写⼊到多个
Channel 中,不同的 Sink 可以从不同的 Channel 中获取相同的 Event ,⽐
如⼀份⽇志数据同时写 Kafka HDFS ,⼀个 Event 同时写⼊两个 Channel,然后不同类型的 Sink 发送到不同的外部存储。
2. 复⽤选择器 : 需要和拦截器配合使⽤,根据 Event 的头信息中不同键值数
据来判断 Event 应该写⼊哪个 Channel 中。

8. 了解 Flume 的负载均衡和故障转移吗

⽬的是为了提⾼整个系统的容错能⼒和稳定性。简单配置就可以轻松实现,
⾸先需要设置 Sink 组,同⼀个 Sink 组内有多个⼦ Sink ,不同 Sink 之间可以配 置成负载均衡或者故障转移。

Hbase


1.7.2 RowKey设计原则

1rowkey长度原则

2rowkey散列原则

3rowkey唯一原则

1.7.3 RowKey如何设计

1)生成随机数、hash、散列值

2)字符串反转 

1.HBase的操作数据的步骤

1 Hbase 写数据过程:
        Client写⼊ -> 存⼊ MemStore ,⼀直到 MemStore -> Flush 成⼀个 StoreFile ,直⾄增长到⼀定阈值 -> 出发 Compact 合并操作 -> 多个 StoreFile 合并成⼀个 StoreFile ,同时进⾏版本合并和数据删除 -> StoreFiles Compact 后,逐步形成越来越 ⼤的StoreFile -> 单个 StoreFile ⼤⼩超过⼀定阈值后,触发 Split 操作,把当前 Region Split 2 Region Region 会下线,新 Split出的 2 个孩⼦ Region 会被 HMaster 分配到相应的 HRegionServer 上,使得原先 1 Region 的压⼒得以分流到 2 Region 上。
        由此过程可知,HBase只是增加数据,有所得更新和删除操作,都是在 Compact 阶段做的,所以,⽤户写操作只需要进⼊到内存即可⽴即返回,从⽽保证I/O ⾼性能。
2 Hbase 读数据:
client->zookeeper->.ROOT->.META-> ⽤户数据表 zookeeper 记录了 .ROOT 的路径信息( root 只有⼀个region ), .ROOT ⾥记录了 .META region 信息, ( .META 可能有多个 region ), .META ⾥⾯记录了 region 的信息。

2.HDFSHBase各⾃使⽤场景(重点)

⾸先⼀点需要明⽩:Hbase是基于HDFS来存储的。
HDFS
(1) ⼀次性写⼊,多次读取。
(2) 保证数据的⼀致性。
(3) 主要是可以部署在许多廉价机器中,通过多副本提⾼可靠性,提供了容错和恢复机制。
HBase
(1) 瞬间写⼊量很⼤,数据库不好⽀撑或需要很⾼成本⽀撑的场景。
(2) 数据需要长久保存,且量会持久增长到⽐较⼤的场景
(3) HBase 不适⽤与有 join ,多级索引,表关系复杂的数据模型
(4) ⼤数据量 ( 100s TB 级数据) 且有快速随机访问的需求。
如:淘宝的交易历史记录。数据量巨⼤⽆容置疑,⾯向普通⽤户的请求必然要即时响应。
(5) 容量的优雅扩展
⼤数据的驱使,动态扩展系统容量。例如: webPage DB
(6) 业务场景简单,不需要关系数据库中很多特性(例如交叉列、交叉表,事务,连接等等)
(7) 优化⽅⾯:合理设计 rowkey

3.热点现象及解决办法。(重点)

1. 热点现象:
         ⼤量的client直接访问集群的⼀个或极少数个节点(访问可能是读,写或者其他操作) 。⼤量访问会使热点region所在的单个机器超出⾃⾝承受能
⼒,引起性能下降甚⾄region不可⽤,这也会影响同⼀个RegionServer上的其他region,由于主机⽆法服务其他region的请求。
        某个⼩的时段内,对HBase的读写请求集中到极少数的 Region 上,导致这些 region 所在的 RegionServer 处理请求量骤增,负载量明显偏⼤,⽽其他的RgionServer 明显空闲。

2. 热点现象出现的原因 HBase 中的⾏是按照 rowkey 的字典顺序排序的,这种设计优化了 scan 操作,可以将相关的⾏以及会被⼀起读取的⾏存取在临近位置,便于scan 。然⽽ 糟糕的rowkey设计是热点的源头 。 设计良好的数据访问模式以使集群被充分,均衡的利⽤。
3. 热点现象解决办法 :为了避免写热点,设计 rowkey 使得不同⾏在同⼀个 region ,但是在更多数据情况下,数据应该被写⼊集群的多个region ,⽽不是⼀个。常见的⽅法有以下这些:

1)生成随机数、hash、散列值

2)字符串反转 

a. 加盐 :在 rowkey 的前⾯ 增加随机数 ,使得它和之前的 rowkey 的开头不同。分配的前缀种类数量应该和你想使⽤数据
分散到不同的 region 的数量⼀致。加盐之后的 rowkey 就会根据随机⽣成的前缀分散到各个 region 上,以避免热点。
b. 哈希 :哈希可以使负载分散到整个集群,但是读却是可以预测的。使⽤确定的哈希可以让客户端重构完整的rowkey,可以使⽤ get 操作准确获取某⼀个⾏数据
c. 反转: 第三种防⽌热点的⽅法时反转固定长度或者数字格式的 rowkey 。这样可以使得 rowkey 中经常改变的部分(最没有意义的部分)放在前⾯。这样可以有效的随机rowkey ,但是牺牲了 rowkey 的有序性。 反转rowkey的例⼦以⼿机号为rowkey,将⼿机号反转后的字符串作为rowkey ,这样的就避免了以⼿机号那样⽐较固定开头导致热点问题
d. 时间戳反转 ⼀个常见的数据处理问题是快速获取数据的最近版本,使⽤反转的时间戳作为 rowkey 的⼀部分对这个问题⼗分有⽤,可以⽤ Long.Max_Value - timestamp 追加到 key 的末尾,例如 [ key ][ reverse_timestamp ] , [ key ] 的最
新值可以通过 scan [ key ] 获得 [ key ] 的第⼀条记录,因为 HBase rowkey 是有序的,第⼀条记录是最后录⼊的数据。
i. ⽐如需要保存⼀个⽤户的操作记录,按照操作时间倒序排序,在设计 rowkey 的时候,可以这样设计 [ userId 反转 ] [ Long.Max_Value - timestamp ] ,在查询⽤户的所有操作记录数据的时候,直接指定反转后的 userId startRow
[ userId 反转 ][ 000000000000 ], stopRow [ userId 反转 ][ Long.Max_Value - timestamp ]
ii. 如果需要查询某段时间的操作记录, startRow [ user 反转 ][ Long.Max_Value - 起始时间 ] stopRow [ userId 反转][ Long.Max_Value - 结束时间 ]
e. HBase 建表预分区 :创建 HBase 表时,就预先根据可能的 RowKey 划分出多个 region ⽽不是默认的⼀个,从⽽可以将 后续的读写操作负载均衡到不同的region 上,避免热点现象。

4.RowKey的设计原则?(重点)

1. 总的原则 :避免热点现象,提⾼读写性能;
2. 长度原则 rowkey 是⼀个⼆进制码流,可以是任意字符串,最⼤长度 64kb ,实际应⽤中⼀般为 10-100bytes ,以 byte []
形式保存,⼀般设计成定长。 建议越短越好,不要超过16个字节 ,原因如下:数据的持久化⽂件 HFile 中是按照 KeyValue 存储的,如果rowkey 过长,⽐如超过 100 字节, 1000w ⾏数据,光 rowkey 就要占⽤ 100*1000w=10 亿个字节,将近 1G 数据, 这样会极⼤影响HFile 的存储效率; MemStore 将缓存部分数据到内存,如果 rowkey 字段过长,内存的有效利⽤率就会降低,系统不能缓存更多的数据,这样会降低检索效率。⽬前操作系统都是64 位系统,内存 8 字节对齐,控制在 16 个字节, 8 字节的整数倍利⽤了操作系统的最佳特性;
3. 散列原则 :如果 rowkey 按照时间戳的⽅式递增,不要将时间放在⼆进制码的前⾯,建议将 rowkey 的⾼位作为散列字段,由程序随机⽣成,低位放时间字段,这样将提⾼数据均衡分布在每个RegionServer ,以实现负载均衡的⼏率。如果没有散列字段,⾸字段直接是时间信息,所有的数据都会集中在⼀个RegionServer 上,这样在数据检索的时候负载会集中在个别的RegionServer 上,造成热点问题,会降低查询效率;
4. 唯⼀ 原则 :必须在设计上保证其唯⼀性, rowkey是按照字典顺序排序存储的 ,因此,设计 rowkey 的时候,要充分利⽤这个排序的特点, 将经常读取的数据存储到⼀块,将最近可能会被访问的数据放到⼀块
5. Rowkey 设计结合业务 :在满⾜ rowkey 设计原则的基础上,往往需要将经常⽤于查询的字段正和岛 rowkey 上,以提⾼检索查询效率。

5.hbase.hregion.max.filesize应该设置多少合适

        默认是256 HStoreFile 的最⼤值。如果任何⼀个 Column Family (或者说 HStore )的 HStoreFiles 的⼤⼩超过这个值,那么,其所属的HRegion 就会 Split 成两个。
        众所周知hbase 中数据⼀开始会写⼊ memstore ,当 memstore 64MB 以后,会 flush disk 上⽽成为 storefile 。当 storefile数量超过3 时,会启动 compaction 过程将它们合并为⼀个 storefile 。这个过程中会删除⼀些 timestamp 过期的数据,⽐如 update 的数据。⽽当合并后的storefile ⼤⼩⼤于 hfile 默认最⼤值时,会触发 split 动作,将它切分成两个 region

6.autoflush=false的影响

        ⽆论是官⽅还是很多blog 都提倡为了提⾼ hbase 的写⼊速度⽽在应⽤代码中设置 autoflush=false ,然后在在线应⽤中应该
谨慎进⾏该设置,原因如下:
(1) autoflush=false 的原理是当客户端提交 delete put 请求时,将该请求在客户端缓存,直到数据超过 2M( hbase.client.write.buffer 决定 ) 或⽤户执⾏了 hbase.flushcommits () 时才向 regionserver 提交请求。因此即使htable.put () 执⾏返回成功,也并⾮说明请求真的成功了。假如还没有达到该缓存⽽ client 崩溃,该部分数据将由于未发送到regionserver ⽽丢失。这对于零容忍的在线服务是不可接受的。
(2) autoflush=true 虽然会让写⼊速度下降 2-3 倍,但是对于很多在线应⽤来说这都是必须打开的,也正是 hbase 为什么
让它默认值为 true 的原因。当该值为 true 时,每次请求都会发往 regionserver , regionserver 接收到请求后第⼀件事就
是写 hlog ,因此对 io 的要求是⾮常⾼的,为了提⾼ hbase 的写⼊速度,应该尽可能⾼地提⾼ io 吞吐量,⽐如增加磁盘、
使⽤ raid 卡、减少 replication 因⼦数等。

7对于传统关系型数据库中的⼀张table,在业务转换到hbase上建模时,从性能的⾓度应该 如何设置familyqualifier呢?

1、最极端的,①每⼀列都设置成⼀个 family ,②⼀个表仅有⼀个 family ,所有列都是其中的⼀个 qualifier ,那么有什么区别 呢?
1. 从读的⽅⾯考虑:
a. family 越多,那么获取每⼀个 cell 数据的优势越明显,因为 io 和⽹络都减少了。如果只有⼀个 family ,那么每⼀
次读都会读取当前 rowkey 的所有数据,⽹络和 io 上会有⼀些损失。
b. 当然如果要获取的是固定的⼏列数据,那么把这⼏列写到⼀个 family 中⽐分别设置 family 要更好,因为只需⼀次
请求就能拿回所有数据。 2. 从写的⾓度考虑:
   a. 内存⽅⾯来说,对于⼀个 Region ,会为每⼀个表的每⼀个 Family 分配⼀个 Store ,⽽每⼀个 Store ,都会分配⼀
MemStore ,所以更多的 family 会消耗更多的内存。
   b. flush compaction ⽅⾯说,⽬前版本的 hbase ,在 flush compaction 都是以 region 为单位的,也就是说当
⼀个 family 达到 flush 条件时,该 region 的所有 family 所属的 memstore 都会 flush ⼀次,即使 memstore 中只有很少的数
据也会触发 flush ⽽⽣成⼩⽂件。这样就增加了 compaction 发⽣的机率,⽽ compaction 也是以 region 为单位的,这样
就很容易发⽣ compaction 风暴从⽽降低系统的整体吞吐量。
   c. split ⽅⾯考虑,由于 hfile 是以 family 为单位的,因此对于多个 family 来说,数据被分散到了更多的 hfile 中,减
⼩了 split 发⽣的机率。这是把双刃剑。更少的 split 会导致该 region 的体积⽐较⼤,由于 balance 是以 region 的数⽬⽽不
是⼤⼩为单位来进⾏的,因此可能会导致 balance 失效。⽽从好的⽅⾯来说,更少的 split 会让系统提供更加稳定的在线
服务。⽽坏处我们可以通过在请求的低⾕时间进⾏⼈⼯的 split balance 来避免掉。
2、因此对于写⽐较多的系统,如果是离线应该,我们尽量只⽤⼀个 family 好了,但如果是在线应⽤,那还是应该根据应⽤
的情况合理地分配 family

8.Hbase⾏健/列族的概念,物理模型,表的设计原则?

1. ⾏健:是 hbase 表⾃带的,每个⾏健对应⼀条数据。
2. 列族:是创建表时指定的,为列的集合,每个列族作为⼀个⽂件单独存储,存储的数据都是字节数组,其中的数据可以有很多,通过时间戳来区分。
3. 物理模型:整个 hbase 表会拆分为多个 region ,每个 region 记录着⾏健的起始点保存在不同的节点上,查询时就是对各个节点的并⾏查询,当region 很⼤时使⽤ .META 表存储各个 region 的起始点, -ROOT 又可以存储 .META 的起始点。
4. rowkey 的设计原则:各个列簇数据平衡,长度原则、相邻原则,创建表的时候设置表放⼊ regionserver 缓存中,避免⾃动增长和时间,使⽤字节数组代替string ,最⼤长度 64kb ,最好 16 字节以内,按天分表,两个字节散列,四个字节存储时分毫秒。
5. 列族的设计原则:尽可能少(按照列族进⾏存储,按照 region 进⾏读取,不必要的 io 操作),经常和不经常使⽤的两类数据放⼊不同列族中,列族名字尽可能短。

9.HBase存储单元Cell?(重点)

1. 单元 {row key column ( =<family>+<label> ), version}
2. 唯⼀性;数据是没有类型的,以字节码形式存储
3. 表: ( key ,列族 + 列名,版本 ( timestamp )) ->

10.说说HBase物理模型?(重点)

( 1 ) Table 中的所有⾏都按照 row-key 的字典序排列;
( 2 ) Table 在⾏的⽅向上分割为多个 Region
( 3 ) Region 按⼤⼩分割的,每个表开始只有⼀个 region ,随着数据增多, region 不断增⼤,当增⼤到⼀个阈值的时
候, region 就会等分成两个新的 region ,之后会有越来越多的 region
( 4 ) Region是HBase中分布式存储和负载均衡的最⼩单元 。不同 region 分布到不同的 regionserver 上;
( 5 ) region虽然是分布式存储的最⼩单元,但并不是存储的最⼩单元。
Region由⼀个或者多个store组成,每个store保存⼀个columns family;
每个store又由⼀个memstore和0⾄多个storeFile组成;
Memstore存储在内存中,storefile存储在HDFS上;
(6) 每个 column family 存储在 HDFS 上的⼀个单独⽂件中;
(7) Key version number 在每个 column family 中都保存⼀份;
(8) 空值不会被保存。

11.HBase的客户端Client

1. 整个 HBase 集群的访问⼊⼜;
2. 使⽤ HBase RPC 机制与 HMaster HRegionServer 进⾏通信;
3. 与 HMaster 通信进⾏管理类操作;
4. 与 HRegionServer 进⾏数据读写类操作;
5. 包含访问 HBase 接⼜,并维护 cache 来加快对 HBase 的访问。

12.介绍HBase⼆级索引?

        1. HBase 提供了检索数据的功能,不过原有系统仅提供了通过 rowkey 检索数据的功能,过于单⼀,不灵活,⼀旦查询条改变了往往涉及到要全表扫描过滤,极⼤浪费机器物理资源,又达不到实时的⼀个效果。HBase ⼆级索引功能解决了原有HBase 系统中仅能够通过 rowkey 检索数据的问题,使得⽤户能够指定多种条件,在 HBase 表中进⾏数据的实时检索与统计。
        2. HBase 只提供了⼀个基于字典排序的主键索引,在查询中只能通过⾏键查询或者扫描全表来获取数据。
        3. HBase 基于 rowkey 的全局索引: Zookeeper znode 节点 /hbase/meta-region-server-->hbase:mata

13.每天百亿数据存⼊HBase,如何保证数据的存储正确和在规定的时间⾥全部录⼊完毕,不残留数据?

看到这个题⽬的时候我们要思考的是它在考查什么知识点?
我们来看看要求:
1 )百亿数据:证明数据量⾮常⼤
2 )存⼊ HBase :证明是跟 HBase 的写⼊数据有关
3 )保证数据的正确:要设计正确的数据结构保证正确性
4 )在规定时间内完成:对存⼊速度是有要求的
那么针对以上的四个问题我们来⼀⼀分析
1 )数据量百亿条,什么概念呢?假设⼀整天 60x60x24 = 86400 秒都在写⼊数据,那么每秒的写⼊条数⾼达 100
条, HBase 当然是⽀持不了每秒百万条数据的,所以这百亿条数据可能不是通过实时地写⼊,⽽是批量地导⼊。批量导⼊推荐使⽤BulkLoad ⽅式( 推荐阅读: Spark 之读写 HBase ),性能是普通写⼊⽅式⼏倍以上
2 )存⼊ HBase :普通写⼊是⽤ JavaAPI put 来实现,批量导⼊推荐使⽤ BulkLoad
3 )保证数据的正确:这⾥需要考虑 RowKey 的设计、预建分区和列族设计等问题
4 )在规定时间内完成也就是存⼊速度不能过慢,并且当然是越快越好,使⽤ BulkLoad

14.你知道哪些HBase优化⽅法(重点)

优化⼿段主要有以下四个⽅⾯
1)减少调整
减少调整这个如何理解呢? HBase 中有⼏个内容会动态调整,如 region (分区)、 HFile ,所以通过⼀些⽅法来减少这些会带来I/O 开销的调整。Region
如果没有预建分区的话,那么随着 region 中条数的增加, region 会进⾏分裂,这将增加 I/O 开销,所以解决⽅法就是 根据你的RowKey设计来进⾏预建分区,减少region的动态分裂 HFile 。HFile是数据底层存储⽂件,在每个 memstore 进⾏刷新时会⽣成⼀个 HFile ,当 HFile 增加到⼀定程度时,会将属于⼀个region HFile 进⾏合并,这个步骤会带来开销但不可避免,但是合并后 HFile ⼤⼩如果⼤于设定的值,那么HFile 会重新分裂。为了减少这样的⽆谓的 I/O 开销,建议估计项⽬数据量⼤⼩,给 HFile 设定⼀个合适的值
2)减少启停
数据库事务机制就是为了更好地实现批量写⼊,较少数据库的开启关闭带来的开销,那么 HBase 中也存在频繁开启关闭带来的问题。
关闭Compaction,在闲时进⾏⼿动Compaction
因为 HBase 中存在 Minor Compaction Major Compaction ,也就是对 HFile 进⾏合并,所谓合并就是 I/O 读写,⼤量的HFile 进⾏肯定会带来 I/O 开销,甚⾄是 I/O ⻛暴,所以为了避免这种不受控制的意外发⽣,建议关闭⾃动  Compaction,在闲时进⾏ compaction
批量数据写⼊时采⽤BulkLoad
如果通过 HBase-Shell 或者 JavaAPI put 来实现⼤量数据的写⼊,那么性能差是肯定并且还可能带来⼀些意
想不到的问题,所以当需要写⼊⼤量离线数据时建议使⽤ BulkLoad
3)减少数据量
虽然我们是在进⾏⼤数据开发,但是如果可以通过某些⽅式在保证数据准确性同时减少数据量,何乐⽽不为呢?
开启过滤,提⾼查询速度
开启 BloomFilter BloomFilter 是列族级别的过滤,在⽣成⼀个 StoreFile 同时会⽣成⼀个 MetaBlock ,⽤于 查询时过滤数据
使⽤压缩 :⼀般推荐使⽤ Snappy LZO 压缩
4)合理设计
在⼀张 HBase 表格中 RowKey ColumnFamily 的设计是⾮常重要,好的设计能够提⾼性能和保证数据的准确性
RowKey设计 :应该具备以下⼏个属性
散列性:散列性能够保证相同相似的 rowkey 聚合,相异的 rowkey 分散,有利于查询
简短性 rowkey 作为 key 的⼀部分存储在 HFile 中,如果为了可读性将 rowKey 设计得过⻓,那么将会增加存储
压⼒
唯⼀性 rowKey 必须具备明显的区别性
业务性:举些例⼦
假如我的查询条件⽐较多,⽽且不是针对列的条件,那么 rowKey 的设计就应该⽀持多条件查询
如果我的查询要求是最近插⼊的数据优先,那么 rowKey 则可以采⽤叫上 Long.Max- 时间戳的⽅式,这样
rowKey 就是递减排列
列族的设计
列族的设计需要看应⽤场景
多列族设计的优劣
优势: HBase 中数据时按列进⾏存储的,那么查询某⼀列族的某⼀列时就不需要全盘扫描,只需要扫
描某⼀列族,减少了读 I/O ;其实多列族设计对减少的作⽤不是很明显,适⽤于读多写少的场景
劣势:降低了写的 I/O 性能。原因如下:数据写到 store 以后是先缓存在 memstore 中,同⼀个 region 中存在多个列族则存在多个store ,每个 store 都⼀个 memstore ,当其实 memstore 进⾏ flush 时,属于同⼀个 region的store 中的 memstore 都会进⾏ flush ,增加 I/O 开销

15.HRegionServer宕机如何处理?

1 ZooKeeper 会监控 HRegionServer 的上下线情况,当 ZK 发现某个 HRegionServer 宕机之后会通知 HMaster 进⾏失效备援;
2 )该 HRegionServer 会停⽌对外提供服务,就是它所负责的 region 暂时停⽌对外提供服务
3 HMaster 会将该 HRegionServer 所负责的 region 转移到其他 HRegionServer 上,并且会对 HRegionServer 上存在memstore中还未持久化到磁盘中的数据进⾏恢复
4 )这个恢复的⼯作是由 WAL 重播来完成,这个过程如下:
wal 实际上就是⼀个⽂件,存在 /hbase/WAL/ 对应 RegionServer 路径下
宕机发⽣时,读取该 RegionServer 所对应的路径下的 wal ⽂件,然后根据不同的 region 切分成不同的临时⽂件recover.edits
region 被分配到新的 RegionServer 中, RegionServer 读取 region 时会进⾏是否存在 recover.edits ,如果有则进⾏恢复

16.HBase简单读写流程

读:
找到要读取数据的 region 所在的 RegionServer ,然后按照以下顺序进⾏读取:先去 BlockCache 读取,若 BlockCache
没有,则到 Memstore 读取,若 MemStore 中没有,则到 HFile 中读取。
写:
找到要写⼊数据的 region 所在的 RegionServer ,然后将数据先写到 WAL 中,然后再将数据写到 MemStore 等待刷新,
回复客户端写⼊完成。

17.HBaseHive的对⽐(重点)

18.HBase与传统关系型数据库(如MySQL)的区别(重点)

1. 数据类型: 没有数据类型,都是字节数组 (有⼀个⼯具类 Bytes ,将 java 对象序列化为字节数组)。
2. 数据操作: HBase 只有很简单的插⼊、查询、删除、清空等操作,表和表之间是分离的, 没有复杂的表和表之间的关系 ,⽽传统数据库通常有各式各样的函数和连接操作。
3. 存储模式: Hbase 适合于⾮结构化数据存储, 基于列存储⽽不是⾏
4. 数据维护: HBase的更新操作 不应该叫更新,它 实际上是插⼊了新的数据 ,⽽传统数据库是替换修改
5. 时间版本: Hbase 数据写⼊ cell 时,还会附带时间戳,默认为数据写⼊时 RegionServer 的时间,但是也可以指定⼀个不同的时间。 数据可以有多个版本。
6. 可伸缩性, Hbase 这类分布式数据库就是为了这个⽬的⽽开发出来的,所以 它能够轻松增加或减少硬件的数量 ,并且对错误的兼容性⽐较⾼。⽽传统数据库通常需要增加中间层才能实现类似的功能。

19.什么时候适合使⽤HBase(应⽤场景)?(重点)

1. 半结构化或⾮结构化数据 :
2. 对于数据结构字段不够确定或杂乱⽆章⾮常难按⼀个概念去进⾏抽取的数据适合⽤ HBase ,因为 HBase ⽀持 动态添加列
3. 记录很稀疏:
4. RDBMS 的⾏有多少列是固定的。为 null 的列浪费了存储空间。⽽如上⽂提到的, HBase为null的Column不会被存储 ,这样既节省了空间⼜提⾼了读性能。
5. 多版本号数据
6. 依据 Row key Column key 定位到的 Value 能够有随意数量的版本号值,因此对于 须要存储变动历史记录的数据 ,⽤HBase是很⽅便的。⽐⽅某个⽤户的 Address 变更,⽤户的 Address 变更记录也许也是具有研究意义的。
7. 仅要求最终⼀致性:
8. 对于数据存储事务的要求不像⾦融⾏业和财务系统这么⾼,只要保证最终⼀致性就⾏。(⽐如 HBase+elasticsearch时,可能出现数据不⼀致)
9. ⾼可⽤和海量数据以及很⼤的瞬间写⼊量:
10. WAL 解决⾼可⽤,⽀持 PB 级数据, put 性能⾼
11. 索引插⼊⽐查询操作更频繁的情况。⽐如,对于历史记录表和⽇志⽂件。( HBase 的写操作更加⾼效)
12. 业务场景简单:
13. 不需要太多的关系型数据库特性,列⼊交叉列,交叉表,事务,连接等

20.Client会缓存.META.的数据,该数据更新了怎么办?

其实, Client 的元数据缓存不更新,当 .META. 的数据发⽣更新。⽐如因为 region 重新均衡,某个 Region 的位置发⽣了变化,Client 再次根据缓存去访问的时候,会出现错误,当出现异常达到最⼤重试次数后, client 就会去 .META. 所在的RegionServer获取最新的 Region 信息,如果 .META. 所在 RegionServer 也变了, Client 就会重新去 ZK 上获取 .META. 所在的RegionServer的最新地址。

21.请描述如何解决Hbaseregion太⼩和region太⼤带来的冲突?

Region过⼤会发⽣多次compaction ,将数据读⼀遍并重写⼀遍到 hdfs 上,占⽤ io;
region过⼩会造成多次split ,region会下线,影响访问服务,调整 hbase.hregion.max.filesize 256m.

22.解释下 hbase 实时查询的原理(重点)

  实时查询,可以认为是从内存中查询,⼀般响应时间在 1 秒内。 HBase 的机制是数据先写⼊到内存中,当数据量达到⼀定的量(如 128M ),再写⼊磁盘中, 在内存中,是不进⾏数据的更新或合并操作的,只增加数据,这使得⽤户的写操作只要进⼊内存中就可以⽴即返回,保证了 HBase I/O 的⾼性能。

23.HBase 宕机如何处理?

宕机分为 HMaster 宕机和 HRegisoner 宕机。
a. 如果是 HRegisoner 宕机, HMaster 会将其所管理的 region 重新分布到其他活动的 RegionServer 上,由于数
据和⽇志都持久在 HDFS 中,该操作不会导致数据丢失。所以数据的⼀致性和安全性是有保障的。
b. 如果是 HMaster 宕机, HMaster 没有单点问题, HBase 中可以启动多个 HMaster ,通过 Zookeeper 的Master Election 机制保证总有⼀个 Master 运⾏。即 ZooKeeper 会保证总会有⼀个 HMaster 在对外提供服务。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值