Hbase操作实战Hbase特点1.支撑高并发的读写访问。2.数据基于hdfs存放,副本机制可以保证数据可靠3.分布式regionserver-region模型,在横向扩展的基础上可以支撑很大的业务表的操作4.读写相应速度快5.分布式设计策略允许硬件故障Hbase关系数据库区别1.hbase数据操作只有很简单插入,查询,删除,修改,清空等操作,不能实现表与表关联操作。2.hbase基于列式存储,每个列族都有几个文件保存,不同列族的文件是分离的。而关系型数据库基于表格设计和行模式保存。3.hbase修改和删除数据是实现上插入带有特殊标记的新记录,而关系型数据库是数据内容的替换和修改读写相应速度快4.Hbase分布式,关系型数据库只能用其他方式实现5.Hbase支持并发量比关系型数据库大的多,相应时间也比较快Hbase使用场景1.数据量特别大的表。2.读写量比较高。3.数据要求比较高Hbase方式区别-apiApi是hbase最常用的使用方式,通过javaapi操作hbase提供线上业务数据查询数据写入等操作,是当前业务系统最常用的访问方式Hbase方式区别-hbaseshellHbaseshell提供了常用的管理员命令,来满足用户手动创建表删除表,浏览数据测试写入数据等操作,一般用作集群管理Hbase方式区别-MapReducer支持通过mapreducer对hbase的数据写入和导出1.1.Api写入导出2.2.生成hfile文件加载进去(好处:不用把负载加到regionserver)速度比较快,单纯的mr写入3.TableInputFormat对hbase全表或者部分数据的导出(速度秒杀get)Hbase方式区别-phoenixPhoenix查询引擎会将SQL查询转换为一个或多个HBasescan,并编排执行以生成标准的JDBC结果集---后边会单独介绍phoenix1.Sql方式访问使用方便2.Phoenixscan做了很多分桶多路scan的优化性能比原生的scan块很多3.使用了索引支持sumcountgroup等操作HbaseShell介绍1.hbase提供了一个shell的终端给用户交互。通过执行helpget可以看到命令的帮助信息。2.使用方式/bin/hbaseshell配置好path之后可以直接使用hbaseshell命令来使用hbaseshell交互HbaseShell常用操作1.Table操作create,disable,enable,drop,list,describe,exists等2.数据操作put,get,scan,delete等3.其他命令:count(获取表行数),balancer命令负载均衡,splitregion分离等4.注意:不要使用shellscan会对集群造成压力,浏览数据可以加上{LIMIT=10}HbaseApi-htable代码:HTablehtable=newHTable(newConfiguration(),test_t1);1.线程不安全2.创建连接需要花费很多时间3.实现原理与技术瓶颈解决4.自定义代理实现hbase连接池高性能高并发hbase访问5.超时参数对于线上业务的优化1.hbase.rpc.timeout:rpc的超时时间,默认60s,不建议修改,避免影响正常的业务2.ipc.socket.timeout:socket建立链接的超时时间,应该小于或者等于rpc的超时时间,默认为20s3.hbase.client.retries.number:重试次数,默认为14,可配置为34.hbase.client.pause:重试的休眠时间,默认为1s,可减少优化,比如100ms5.使用异步处理(查询异步提高查询速度,taskget自动超时策略)HbaseApi–Get代码:HTablehtable=newHTable(newConfiguration(),test_t1);Getget=newGet(aaa.getBytes());Resultres=htable.get(get);1.线上最靠谱的查询方式2.Blockcache设置优化get查询3.分布式(rowkey分布-hash,逆序)对查询的影响4.多线程get的用法5.获取列对数据查询速度的影响HbaseApi–Scan代码:Scanscan=newScan(Bytes.toBytes(startTime),Bytes.toBytes(endTime));scan.addFamily(Bytes.toBytes(v));ResultScannerscanner=table.getScanner(scan);System.out.println(endscan!!!!!usertime:+(System.currentTimeMillis()-startVisTime));IteratorResultit=scanner.iterator();1.比较慢的查询,但可以一次性查询多条减少请求次数,适用于实时性不高但查询连续数据的应用场景2.线上业务不能忍受scan速度太慢3.对于数据批量导出,mapreducer可以使用hbasescan对数据批量导出4.支持过滤设置start,stop位置HbaseApi–Put代码:HTablehtable=newHTable(newConfiguration(),test_t1);Putput=newPut(Bytes.toBytes(key.toString()));put.add(Bytes.toBytes(v),Bytes.toBytes(COL_NAME),Bytes.toBytes(count));hTable.put(put);1.Put用户向hbase写数据,集群参数memstore大小影响put速度2.大批量写数据客户端优化打开hTable.setAutoFlush(false);3.使用add(listput)4.对于批量写入可以关闭walLogHbaseApi–简单事物操作代码:htable.incrementColumnValue(key,fam,col,bo.getPw(),value);1.Hbase对事物支持不够好,现有的事物操作比较复杂2.简单的累加,减法操作可以直接使用api操作保证事物,性能比lock的方式好的多Hbase快照–介绍快照就是一份元信息的合集,允许管理员恢复到表的先前状态。快照不是表的复制而是一个文件名称列表,因而不会复制数据。完全快照恢复是指恢复到之前的“表结构”以及当时的数据,快照之后发生的数据不会恢复。要想使用snapshot功能,请确认你的hbase-site.xml中的hbase.snapshot.enabled配置项为truenamehbase.snapshot.enabled/namevaluetrue/valueHbase快照–常用操作代码:1.获取指定表的快照使用snapshot命令(不产生文件复制)hbasesnapshot‘tableName’,‘snapshotName’2.列出所有的快照,使用list_snapshot命令。会展示出快照名称,源表,以及创建日期和时间hbaselist_snapshots3.删除快照使用deleted_snapshot命令。删除快照不会影响到克隆表或者之后生成的快照。hbasedelete_snapshot‘snapshotName’4.使用clone_snapshot命令从指定的快照生成新表(克隆)。由于不会产生数据复制,所以最终用到的数据不会是之前的两倍。hbaseclone_snapshot‘snapshotName’,‘newTableName’5.使用restore_snapshot命令将指定快照内容替换当前表结构/数据。hbaserestore_snapshot‘snapshotName’6.使用ExportSnapshot工具将现有快照导出至其他集群。导出工具不会影响到域服务器负载,只是工作在HDFS层面所以需要指定HDFS路径(其他集群的hbase根目录)hbaseorg.apache.hadoop.hbase.snapshot.ExportSnapshot-snapshotSnapshotName-copy-tohdfs:///srv2:8082/hbaseHbase快照–原理问题:我删除了原表还可以恢复吗?答案:yes可以的,那么hbase是怎么做的呢我经过测试发现hbase删除原表的时候他会进行原文件的mv把原表对应的hfile文件mv到/hbase/archive/data/default目录,恢复时候会自动使用这个目录的hfile进行副本归档恢复,反过来如果hfile发生改变或者split操作那么文件又没有恢复是怎么保存快照表的数据的呢原理:其实他并不是完全没有拷贝只是做快照时候没拷贝,当原表hfile进行改变的时候,同样老的hfile会拷贝出去,但这个拷贝过程会分散开而且只拷贝当前发生改变的hfile所以性能要好的多。注意:所以hbase虽然快照用起来很爽但不要产生过多没用的快照因为快照太多会导致一个表在写时候hfile需要拷贝很多份出去(不是一个快照一份,一样的文件用的连接,相信没用人会对完全一样的数据做快照)Hbaseclient–原理Htableclient访问集群的步骤:1.数据直接从regionserver获取不经过hamster2.三层路由策略获取表信息3.本地缓存元数据信息提高查询速度4.集群故障重试清楚cache重新获取新的元数据信息Hbasemaster–作用1.为Regionserver分配region2.负责Regionserver的负载均衡3.创建表,删除表等操作region的分配删除4.发现失效的Regionserver并重新分配其上的region5.HDFS上的垃圾文件回收Hbaseregionserver–作用维护master分配给他的region,处理对这些region的io请求负责切分正在运行过程中变的过大的region可以看到,client访问hbase上的数据并不需要master参与(寻址访问zookeeper和regionserver,数据读写访问regionserver),master仅仅维护table和region的元数据信息(table的元数据信息保存在zookeeper上),负载很低。HRegionServer存取一个子表时,会创建一个HRegion对象,然后对表的每个列族创建一个Store实例,每个Store都会有一个MemStore和0个或多个StoreFile与之对应,每个StoreFile都会对应一个HFile,HFile就是实际的存储文件。因此,一个HRegion有多少个列族就有多少个Store。一个HRegionServer会有多个HRegion和一个HLog。Hbase优化–表设计1.预分区:在创建HBase表的时候会自动创建一个region分区,当导入数据的时候,所有的HBase客户端都向这一个region写数据,直到这个region足够大了才进行切分。一种可以加快批量写入速度的方法是通过预先创建一些空的regions,这样当数据写入HBase时,会按照region分区情况,在集群内做数据的负载均衡2.rowkey分布:是按照字典序存储,因此,设计rowkey时,要充分利用这个排序特点,将经常一起读取的数据存储到一块,将最近可能会被访问的数据放在一块,如果大量get请求于鏊尽可能的打乱数据保证多个region负载均衡,达到最好的性能3.columnfamily:每个columnfamily其实给一个新表没太大区别所以要尽量减少columnfamily的个数InMemory:创建表的时候,可以通过HColumnDescriptor.setInMemory(true)将表放到RegionServer的缓存中,保证在读取的时候被cac