我们正在使用hbase版本1.1.4。 DB有大约40个表,每个表数据都指定了一个TimeToLive。它部署在5节点集群上,以下是hbase-site.xml
<property>
<name>phoenix.query.threadPoolSize</name>
<value>2048</value>
</property>
<property>
<name>hbase.hregion.max.filesize</name>
<value>21474836480</value>
</property>
<property>
<name>hbase.hregion.memstore.block.multiplier</name>
<value>4</value>
</property>
<!-- default is 64MB 67108864 -->
<property>
<name>hbase.hregion.memstore.flush.size</name>
<value>536870912</value>
</property>
<!-- default is 7, should be at least 2x compactionThreshold -->
<property>
<name>hbase.hstore.blockingStoreFiles</name>
<value>240</value>
</property>
<property>
<name>hbase.client.scanner.caching</name>
<value>10000</value>
</property>
<property>
<name>hbase.bucketcache.ioengine</name>
<value>offheap</value>
</property>
<property>
<name>hbase.bucketcache.size</name>
<value>40960</value>
</property>
问题是每个区域服务器上的区域数量在不断增长。目前我们只使用
合并区域merge_region in the hbase shell.
有没有办法在每台服务器上只有固定数量的区域,或者自动合并区域?
答案 0 :(得分:2)
有没有办法在每个区域只有固定数量的区域 服务器,或合并区域的自动方式?
我实现这一点的一种方法是使用预分区创建表。例如
create 'test_table', 'f1', SPLITS=> ['1', '2', '3', '4', '5', '6', '7', '8', '9']
设计好的rowkey,将以1-9
开头你可以像下面一样使用番石榴杂音哈希。
import com.google.common.hash.HashCode;
import com.google.common.hash.HashFunction;
import com.google.common.hash.Hashing;
/**
* getMurmurHash.
*
* @param content
* @return HashCode
*/
public static HashCode getMurmurHash(String content) {
final HashFunction hf = Hashing.murmur3_128();
final HashCode hc = hf.newHasher().putString(content, Charsets.UTF_8).hash();
return hc;
}
final long hash = getMurmur128Hash(Bytes.toString(yourrowkey as string)).asLong();
final int prefix = Math.abs((int) hash % 9);
现在将此前缀附加到您的rowkey
例如
1rowkey1 //将进入第一个区域
2rowkey2 //将进入第二区域
3rowkey3 //将进入第三区域
...
9rowkey9 //将进入第九区域
如果您正在进行预拆分,并且想要手动管理区域拆分,则还可以通过将hbase.hregion.max.filesize
设置为较大的数字并将拆分策略设置为ConstantSizeRegionSplitPolicy
来禁用区域拆分。但是,您应该使用类似100GB的安全值,以便区域不会超出区域服务器的功能。您可以考虑禁用自动拆分并依赖预分割的初始区域集,例如,如果您使用统一哈希作为键前缀,并且可以确保每个区域的读/写负载及其大小在表格中的各个区域是统一的。
另外,请查看at
答案 1 :(得分:1)
它主要取决于您的数据:它是如何在密钥之间分配的。假设您的值对于所有键的大小几乎相同,则可以使用分区:
例如,如果您的表格密钥为String
且您想要100个区域,请使用此
public static byte[] hashKey(String key) {
int partition = Math.abs(key.hashCode() % 100);
String prefix = partitionPrefix(partition);
return Bytes.add(Bytes.toBytes(prefix), ZERO_BYTE, key);
}
public static String partitionPrefix(int partition) {
return StringUtils.leftPad(String.valueOf(partition), 2, '0');
}
在这种情况下,所有键都将以数字00-99为前缀,因此100个区域有100个分区。现在您可以禁用区域分割:
HTableDescriptor td = new HTableDescriptor(TableName.valueOf("myTable"));
td.setRegionSplitPolicyClassName("org.apache.hadoop.hbase.regionserver.DisabledRegionSplitPolicy");
或通过shell
alter 'myTable', {TABLE_ATTRIBUTES => {METADATA => {'SPLIT_POLICY' => 'org.apache.hadoop.hbase.regionserver.DisabledRegionSplitPolicy'}}