在上一篇文章《指标计算实践》中,我们分析了指标开发过程,并给出了一些如何复用代码的建议。在一系列指标开发出来之后,如何管理好它们,使之容易访问,并方便的对外提供服务,这是数据平台建设中不得不解决的另一个问题。这里我们将这些问题统一称为指标管理问题。本文希望分享一些相关经验。
指标管理要解决的问题
指标查找
假设现在有一个销售报表的开发需求,报表需要展示不同角度的销售数据,如总销量、月增量、年增量、同比、环比等。为实现这个报表,需要分几步完成:
- 首先是去查找当前是否已有相关指标实现。如果已有指标实现,就可以考虑是否可以直接使用这个结果
- 如果我们找到了对应的指标,接下来还需要确认该指标的计算维度是否和我们需要的维度一样
- 如果没有找到对应指标,则需要去查找相似指标,并找出相似指标的计算口径,以便可以正确的迁移到目标指标的计算上来
根据这里的分析,指标管理需要支持指标的多维度搜索,并需要提供功能展示指标对应的计算代码。
指标查询支持
指标的数据查询是指标管理的另一重要功能。
在前面的文章《数据平台数据管理实践》中,对于指标开发和指标对外服务,我们提到了两条有用的经验。即:
- 把计算过程相似的指标合并到一起计算,并只输出为一张表
- 将获得的指标表合并为一张数据库宽表输出
如果可以应用这两条原则,对于指标的使用人员而言,只需要查询最后的指标宽表即可。由于常常只是单表查询,这看起来似乎不是什么问题。但是在指标宽表中进行指标查询并不简单,主要会涉及到维度如何处理的问题。
举个例子,现在有一个活跃客户数量的指标,需要按照省市区及经销店维度进行统计。
活跃客户数量在这些维度间并没有汇总关系,因为客户可能会动态的移动。
比如,客户A在成都市购买了空调,但是后来搬家到了绵阳市,这个客户不再联系成都市的经销店了,但是也并没有完全失去联系,他改为联系绵阳市的经销店了。站在成都市的该经销店来看,此客户已不再活跃。站在四川省的范围来看,该客户还是活跃状态。
对于这类没有汇总关系的维度,在计算指标时,我们不得不计算每一个维度组合的指标结果。如果将不同维度的指标看做不同的指标,此时我们将得到五个指标:经销店活跃客户数、城市活跃客户数、市级活跃客户数、省级活跃客户数、全国活跃客户数。
按照前面合并存储的想法,我们可以将它们全部存储到一张数据库表中。如下图:
由于五个指标都存储到了一张表,在查询时就需要注意:
- 查询某经销店活跃用户数:
select 活跃客户数 from table where 经销商='A'
- 查询某城市区域活跃用户数:
select 活跃客户数 from table where 经销商 is null and 区='高新区' and 市='成都市'
- 查询某市级活跃用户数:
select 活跃客户数 from table where 区 is null and 市='成都市'
- …
上面的维度存在层级关系,即全国->省->市->区域->经销店。还有一些维度,它们之间没有层级关系,比如产品的型号和颜色。如果要统计这类维度的数据,那么维度存储上还需要稍加变化。
比如对于产品型号和颜色的销售指标,我们只支持全国->省->市的分析维度,其在数据库表中的存储如下:
对应的查询为:
- 查询某A型号产品市级活跃用户数:
select 活跃客户数 from table where 市='成都市' and 区='高新区' and 经销商 is null and 型号='A' and 颜色 is null
- 查询某白色产品市级活跃用户数:
select 活跃客户数 from table where 市='成都市' and 区='高新区' and 经销商 is null and 型号 is null and 颜色='白色'
这样的查询是比较复杂的,如果需要在开发报表的时候还需要先根据指标存储逻辑来构造这个复杂SQL
,那是很低效的,同时也容易出错。
从上面的分析中可以发现,在设计指标管理系统时,不仅需要在界面上支持数据查询,最好还要支持自动生成对应的查询语句。这个功能可以带来很多好处,比如:1. 可以便于开发人员从命令行查询数据;2. 可以便于下游系统进行数据集成等。
指标管理系统设计
有了上面的分析,下面来看一下如何设计一个指标管理系统。
核心概念
首先来看一下指标管理系统的几个核心概念。根据上面的分析,可以知道,这几个概念是比较重要的,即指标、维度、计算口径。
它们将包含这样一些属性:
- 指标:名称、分类、分析域、计算频率、所支持的维度组、描述、关联的计算口径、关联的代码文件、所在表、对应字段等
- 维度:名称、英文名、分类、分析域、描述、说明等
- 计算口径:名称、规则、技术说明、关联指标等
其中,某一个指标常常可以支持多个维度组合,我们可以将其称为维度组。比如,上面的活跃用户数指标就支持这样几个维度组:
- 全国维度组:(无)
- 省级维度组:省
- 城市级维度组:省、市
- 区级维度组:省、市、区
- 产品型号维度组:省、市、区、产品型号
- 产品颜色维度组:省、市、区、产品颜色
对指标进行查询时,查询将需要在某一个维度组中执行。同时,维度组中的维度如果存在聚合关系,还应该可以支持聚合查询。比如,有了产品颜色维度组
,我们事实上可以支持区级维度组
的数据查询,只需要将数据按照省、市、区
分组,并将指标数据求和即可(对应SQL
代码为group by
与sum
聚合函数)。
在指标管理系统中,需要支持上述概念对应的实体的信息查询及展示。同时,还需要按照上面的指标维度逻辑进行系统功能设计。
维度和计算口径相关功能
对于维度和计算口径,这两类实体在系统中只需要支持信息的展示、搜索,一个简单的设计是分别用两个页面来支持这些功能,即搜索页和详情页。其示意实现可以如下。
维度搜索页和详情页:
计算口径(或规则)搜索页和详情页:
指标相关功能
对于指标而言,根据上面的分析,可以同样的设计一个搜索页和详情展示页。如下:
除了信息展示之外,还需要在这里支持指标查询的SQL
生成。同时,由于生成了SQL
,我们可以在指标管理系统中直接支持数据查询。可以设计一个指标查询页面,包含以下功能:
- 可以输入数据库连接信息,以便进行指标数据查询
- 可以选择维度组进行查询
- 可以从维度组中选择想要查询的维度(可以支持按照某些汇总)
- 可以设置维度搜索条件,并发起数据查询
- 实时的根据维度选项及维度搜索条件生成
SQL
- 支持拷贝
SQL
,并支持跳转到BI
工具进行可视化
一个示例的设计图如下:
首页
上面这些功能,如果都以独立的页面存在,将无法以统一的视角展示给用户。所以,一般而言,还需要一个指标管理系统的首页。可以在首页上展示一些统计信息,并提供到达各个功能页的入口。
一个示例的设计图如下:
总结
本文分析了数据平台中的指标管理相关问题。为了应对这些问题,同时提高团队效率,我们需要建设一个指标管理系统。站在产品设计的角度,本文分析了一个基本的指标管理系统的功能构成,还给出了一个基本的产品设计。
在数据平台建设过程中,除了常规的数据开发工作,常常还需要有针对性的设计一些辅助系统,本文中的指标管理系统就是一个典型的实例。有了这些辅助系统,我们就可以借助它们将一些重要的经验逐步沉淀下来,同时借助它们提高团队效率。从定位上来说,这类数据辅助软件系统是处于数据平台更上层的。
从我们整个数据平台建设过程来看,上层软件系统建设也是其中非常重要的一环。
附录
宽表合并输出的必要性
可能有人觉得指标宽表查询太不方便了,易用性大打折扣,是否可以直接查询合并前的独立的指标表呢?这在实践中会有一些其他问题。
一般而言,在BI
系统进行数据展示时,不能直接从Hive
数据仓库中读取数据(否则,由于Hive
需要临时启动计算任务来执行查询,延迟将非常高)。常见的做法是将这些数据输出到某一个外部的数据库中,如MySQL
、PostgreSQL
或ClickHouse
等,然后让BI
系统去对接这样的外部系统执行查询。
如果不合并指标宽表,直接将数量庞大的指标表同步到外部数据库中,这会带来以下问题:
- 需要将很多张(可能有数百张)数据库表从
Hive
同步到指标服务数据库,同步速度将非常慢 - 外部指标服务数据库占用大量的存储空间(存在很多重复的维度数据)
而合并指标宽表将能有效的减少数据量(主要是去除了重复的维度数据),并有效减少需要同步的数据表数量,从而缓解上述问题。
在实践过程中,为了在易用性和易维护性上取得平衡,我们也可以仅选择将维度相同(或相近)的指标进行宽表合并,从而得到少量(而不是只有一张)的指标宽表。