HBase冷热分离相关命令介绍
此章节主要介绍HBase冷热分离相关命令的使用,包括Shell命令和Java API命令。
Shell命令在HBase客户端执行,需提前安装HBase客户端,详情请参见安装MRS客户端。
设置HBase表的冷热分界线
- Shell
- 创建冷热分离表。
create 'hot_cold_table', {NAME=>'f', COLD_BOUNDARY=>'86400'}
相关参数说明如下:
- NAME:需要冷热分离的列族。
- COLD_BOUNDARY:冷热分离时间点,单位为秒(s)。例如COLD_BOUNDARY值为86400,表示86400秒(一天)前写入的数据会被自动归档到冷存储。
冷热分离时间点需大于Major Compaction执行周期,Major Compaction默认执行周期为7天。
- 取消冷热分离。
- 为已经存在的表设置冷热分离,或者修改冷热分离分界线,单位为秒,可实现数据热存储转为冷存储或冷存储转为热存储,例如:
- 将热存储数据转为冷存储数据:
- 将冷存储数据转为热存储数据:
- 查询是否设置冷热分离或冷热分离是否修改成功。
Table hot_cold_table is ENABLED hot_cold_table COLUMN FAMILIES DESCRIPTION {NAME => 'f', VERSIONS => '1', KEEP_DELETED_CELLS => 'FALSE', DATA_BLOCK_ENCODING => 'NONE', TTL => 'FOREVER', MIN_VERSIONS => '0', REPLICATION_SCOPE => '0', BLOOMFILTER => 'ROW', IN_MEMORY => 'false', COMPRE SSION => 'NONE', BLOCKCACHE => 'true', BLOCKSIZE => '65536', METADATA => {'COLD_BOUNDARY' => '1200'}} 1 row(s) Quota is disabled Took 0.0339 seconds
- 创建冷热分离表。
- Java API方式
- 新建冷热分离表。
COLD_BOUNDARY用于设置冷热分离时间分界点,单位为秒, 示例表示1天之前的数据归档为冷数据。
Admin admin = connection.getAdmin(); TableName tableName = TableName.valueOf("hot_cold_table"); HTableDescriptor descriptor = new HTableDescriptor(tableName); HColumnDescriptor cf = new HColumnDescriptor("f"); cf.setValue(HColumnDescriptor.COLD_BOUNDARY, "86400"); descriptor.addFamily(cf); admin.createTable(descriptor);
- 取消冷热分离。
HTableDescriptor descriptor = admin.getTableDescriptor(tableName); HColumnDescriptor cf = descriptor.getFamily("f".getBytes()); cf.setValue(HColumnDescriptor.COLD_BOUNDARY, null); admin.modifyTable(tableName, descriptor);
- 为已经存在的表设置冷热分离功能,或者修改冷热分离分界线。
COLD_BOUNDARY用于设置冷热分离时间分界点,单位为秒, 示例表示1天之前的数据归档为冷数据。
HTableDescriptor descriptor = admin.getTableDescriptor(tableName); HColumnDescriptor cf = descriptor.getFamily("f".getBytes()); cf.setValue(HColumnDescriptor.COLD_BOUNDARY, "86400"); admin.modifyTable(tableName, descriptor);
- 新建冷热分离表。
数据从热存储到冷存储或从冷存储到热存储,都需执行Major Compaction。
数据写入
冷热分离的表与普通表的数据写入方式完全一致,数据会先存储在热存储(HDFS)中。随着时间的推移,如果一行数据满足:当前时间-时间列值 > COLD_BOUNDARY设置的值,则会在执行Compaction时被归档到冷存储(OBS)中。
数据查询
由于冷热数据都在同一张表中,因此用户所有的查询操作都只需在一张表内进行。在查询时,建议通过配置TimeRange来指定查询的时间范围,系统将会根据指定的时间范围决定查询模式,包括仅查询热存储、仅查询冷存储或同时查询冷存储和热存储。如果查询时未限定时间范围,则会导致查询冷数据。在这种情况下,查询吞吐量会受到冷存储的限制。
- 冷存储中的数据常用于归档,会很少访问。如果冷存储中的数据被大量频繁请求访问,请检查冷热数据边界(COLD_BOUNDARY)配置是否正确。如果频繁查询的大量数据在冷存储中将会限制查询的性能。
- 如果冷存储中存储的一行数据中的某个字段更新,则更新的字段存储在热存储中。如果指定HOT_ONLY或TimeRange参数仅查询热存储中的数据,则只返回更新的字段。如果要返回整行的数据,则必须在不指定HOT_ONLY或TimeRange参数的情况下执行查询,或者确保TimeRange指定的时间范围涵盖从插入行的时间点到最后更新行的时间点的时间段。因此,建议不要更新存储在冷存储中的数据。
- 随机查询Get。
- Shell
- 不指定HOT_ONLY参数来查询数据。在这种情况下,将会查询冷存储中的数据。
- 通过指定HOT_ONLY参数来查询数据。在这种情况下,只会查询热存储中的数据。
- Java API
- 不指定HOT_ONLY参数来查询数据。在这种情况下,将会查询冷存储中的数据。
Get get = new Get("row1".getBytes());
- 通过指定HOT_ONLY参数来查询数据。在这种情况下,只会查询热存储中的数据。
Get get = new Get("row1".getBytes()); get.setAttribute(HBaseConstants.HOT_ONLY, Bytes.toBytes(true));
- 通过指定TimeRange参数来查询数据。在这种情况下,将会比较TimeRange和冷热边界值(COLD_BOUNDARY ),以确定是只查询热存储还是冷存储中的数据,还是同时查询热冷存储中的数据。
Get get = new Get("row1".getBytes()); get.setTimeRange(0, 1568203111265)
TimeRange:查询的时间范围。范围中的时间是UNIX时间戳,表示自1970年1月1日00:00 UTC以来经过的毫秒数。
- 不指定HOT_ONLY参数来查询数据。在这种情况下,将会查询冷存储中的数据。
- Shell
- 范围查询。
- Shell
- Java API
- 不指定HOT_ONLY参数来查询数据。在这种情况下,将会查询冷存储中的数据。
TableName tableName = TableName.valueOf("chsTable"); Table table = connection.getTable(tableName); Scan scan = new Scan(); ResultScanner scanner = table.getScanner(scan);
- 通过指定HOT_ONLY参数来查询数据。在这种情况下,只会查询热存储中的数据。
Scan scan = new Scan(); scan.setAttribute(HBaseConstants.HOT_ONLY, Bytes.toBytes(true));
- 通过指定TimeRange参数来查询数据。在这种情况下,将会比较TimeRange和冷热边界值(COLD_BOUNDARY ),以确定是只查询热存储还是冷存储中的数据,还是同时查询热冷存储中的数据。
Scan scan = new Scan(); scan.setTimeRange(0, 1568203111265);
TimeRange:查询的时间范围。范围中的时间是UNIX时间戳,表示自1970年1月1日00:00 UTC以来经过的毫秒数。
- 不指定HOT_ONLY参数来查询数据。在这种情况下,将会查询冷存储中的数据。
- 优先查询热数据。
在查询客户所有记录等信息的范围查询中,HBase可以扫描热存储和冷存储中的数据。查询结果将根据数据行按写入表时的时间戳降序返回。在大多数情况下,热数据出现在冷数据之前。如果在范围查询中没有配置HOT_ONLY参数,HBase将会扫描热存储和冷存储中的数据,查询响应时间将会增加。如果启用热数据优先特性,HBase会优先查询热存储中的数据。只有当热存储中的行数小于要查询的最小行数时,才会查询冷存储中的数据,减少了冷存储的访问提高了响应速度。
- Java API
TableName tableName = TableName.valueOf("hot_cold_table"); Table table = connection.getTable(tableName); Scan scan = new Scan(); scan.setAttribute(HBaseConstants.COLD_HOT_MERGE, Bytes.toBytes(true)); scanner = table.getScanner(scan);
- Java API
- Major Compaction命令。
- Shell
- Java API
- 合并表所有分区的热数据区。
Admin admin = connection.getAdmin(); TableName tableName = TableName.valueOf("hot_cold_table"); admin. majorCompact (tableName,null, CompactType.NORMAL, CompactionScopeType.HOT);
- 合并表所有分区的冷数据区。
Admin admin = connection.getAdmin(); TableName tableName = TableName.valueOf("hot_cold_table"); admin. majorCompact (tableName,null, CompactType.NORMAL, CompactionScopeType.COLD);
- 合并表所有分区的热冷数据区。
Admin admin = connection.getAdmin(); TableName tableName = TableName.valueOf("hot_cold_table"); admin. majorCompact (tableName,null, CompactType.NORMAL, CompactionScopeType.ALL);
- 合并表所有分区的热数据区。