电信通话语音详单存储设计(二) | 「掘金日新计划 · 12 月更文挑战」

51 阅读2分钟

开启掘金成长之旅!这是我参与「掘金日新计划 · 12 月更文挑战」的第28天

一、本篇笔记重点内容:

  • rowkey设计
  • 应用接口开发

二、 详细知识点介绍:

rowkey设计

HBase中rowkey是主键,其设计也至关重要,入库数据会更根据rowkey进行排序, 数据分布式按照rowkey范围来划分。为了将数据均匀分布到每台机器上,防止热region导致数据堆积在某一台或者多台机器上,rowkey中的号码组成部分需要反序,这样数据分布均匀程度会高很多,同时随机插入的数据会被分配到对应region 中。

HBase 的表数据按照rowkey 规则分布, 分布规则如下图所示。

image.png HBase 的表由region 组成,region 默认均匀分布在不同机器上。region 二个重要的属性: StartKey 与EndKey,表示这个region 维护的rowkey 范围, 当要读/写数据时, 如果rowkey 落在某个start-end key 范围内, 那么就会定位到目标region 并且读/写到相关的数据。

对于rowkey 的设计,还需要结合数据实际查询场景,通过rowkey能满足主要的查询需求。在本案例中,用户登录后,需要根据用户的手机号行来查询通话记录信息,所以行健里边应该包含手机号,这样同一个人的通话记录会存储在一个连续的物理位置。仅仅这样还不够,考虑到客户查询通话记录往往是按照时间去检索,所以行健里边也要包含日期信息,这样相同手机号、相同日期的数据会存储在一个连续的物理位置,相同手机号、前一天的的数据和后一天的数据会存储在相邻的位置。最后,为了保持行健的唯一性,根据时间先后顺序,可以为同一个手机号在同一天产生的语音详单数据生成一个自增的整数值。

根据上面的思想,行键的构造:手机号-呼叫日期-自增序号。最终的行健数据信息如下。

image.png

应用接口开发

应用接口包括如下几个类。

1)首先是HBase表的元数据信息:


// hbase数据库连接信息

public static final String HBASE_ROOTDIR = "hdfs://192.168.190.165:8020/hbase";

public static final String HBASE_ZOOKEEPER_QUORUM = "192.168.190.165"; // .META.

public static final String HBASE_ZOOKEEPER_PROPERTY_CLIENTPORT = "2181";

 

// callrecord1表

public static final String TABLE_CALL_RECORD = "callrecord"; // 表名

public static final String INFO_CF1 = "baseinfo"; // 列族  versions=5

public static final String INFO_CF2 = "otherinfo"; // 列族  versions=3

}

2)用来构造行键的工具类:

import java.util.HashMap;

import java.util.Map;

 

// 用来构造行键的工具类

public class RowKeyConverter {

private static final int STATION_ID_LENGTH = 2;

private static Map<String,Long> phoneId = new HashMap<>();

public static String makeRowKey(String phoneNumber, String calltime) {

Long id = phoneId.get(phoneNumber);

if(null == id) {

id = 1L;

}else {

id += 1;

}

phoneId.put(phoneNumber, id);   // 写回

String date = calltime.split(" ")[0].replace("-", "");

String rowkey = phoneNumber + "-" + date + "-" + id;

return rowkey;

}

}