cjuexuan / mynote

237 stars 34 forks source link

unicorn可视化系统简析 #63

Open cjuexuan opened 5 years ago

cjuexuan commented 5 years ago

背景

对一个需要数据支撑的业务来说,随着业务的成熟度提高,我们从早期的数据探索阶段(数据格式不固定,业务指标不确定,查询模式多边)到需要各种多维度的报表来帮助业务系统做决策,这里就需要一个可视化系统作为支撑。今天就简单的介绍下我司可视化系统的发展过程吧

雏形

早在16年的时候,我司就购买了tableau来给boss们做可视化,在我们使用tableau的时候,我们发现这一块的权限控制不是特别方便(我们买的账号数量有限),所以我们决定在使用tableau的同时也开始自己可视化系统的研发。当时考虑到系统的便利,我们在调度系统中允许用户配置的输出到报表系统的sql(定制的xqlDriver),调度系统实际执行etl任务的过程中,会将那些配置了输出到看板的sql执行并且写到redis中,然后用户在看板系统中选择对应的数据表,简单配置下即可输出一个简单报表了。

这也就是我们看板系统的雏形,当时这部分功能只是调度的一个附属品,当然也有很多的局限性

datatask

dashboard

起步

大概到18年中,我团队开始接手了这个系统,当时大佬对这个系统也承载了很大的期望,希望我们能把可视化系统做好,做成公司信息化建设的重要一环,我刚开始接手的时候,这个系统就收到了很多分析师以及数仓的建议(意见更多:()。 当时看来,这个系统的局限性也真的是比较大的,所以我们开始完整的重新设计。首先,为了解决操作的不连贯问题,我们增加了数据源和数据模型的配置。数据源主要是配置一些jdbc的连接,xql的连接,数据模型的配置,也就是把当时需要在调度系统中的sql编辑功能放到了unicorn中。这里提一个产品上的功能迭代,最开始的时候,我们想着高度灵活,unicorn的开发者尽量不关心任何用户的数据源配置,这部分都由用户去增加和修改,但是实际使用的过程中,每个分析师都去配置一遍连接也非常繁琐,基本上他们配置的过程中还是来问你用户名和密码等,所以我们后面就改成了由管理员统一在后台配置,通过权限控制让每个角色能看到权限范围内的db,简化了用户的第一步操作门槛。 而数据模型这一块,我们当时等于在unicorn内部又做了一个小的调度,用户操作的连贯性得到了一定程度的解决,但是此时也暴露了一个问题,当时在调度系统的时候任务和任务之间是有着依赖关系的,也就是只有当链路上游的etl任务跑完了,下游给看板出数据的任务才能继续跑,这点导致了一开始的可视化系统用户按照悲观的思路往后配置数据获取任务的触发时间,比如上游可能是7点跑完,这边可能会配置到8点到9点,由于众多可视化任务都在链路的最外层,触发到它们的时间也基本相同,所以导致了早高峰队列阻塞比较严重。 另外由于我们在redis里保存的数据是覆盖的,如果当天数据是有问题的,用户是没办法回溯到前面版本的数据的。

成熟

重写之后的0.x版本其实功能和之前也没太大区别,但是好在团队配置开始成型了,这个时候我们可视化项目组大概有2个前端和1.5个服务端(我只能算半个,毕竟没有把全部精力投进去,2333),1个产品以及1个测试,迭代也比较有计划了,基本都能维护在2周一个迭代,所以我们就可以着手解决用户上面的那些问题了。

首先是最刚需的问题,那就是怎么灵活的支持任意区间的筛选,如果用户的数据基数很大且筛选的区间跨度很大(比如过去一年的任何一天的某个专辑的播放量),但是经过高度聚合之后的数据集很小,或者是一些点查的需求,这种可视化系统中是一定要支持的。刚好我们当时有另一个产品叫sql模版来提供给一些运营做简单取数。这里简单介绍下sql模版,sql模版也就是由分析师定义sql的模版和一些占位符,这些占位符绑定到页面的一些输出控件中去(比如筛选器),由用户的输出来动态改变执行的sql,我们就把这个sql模版的功能融合到数据模型里来了,成为了动态数据模型的雏形。而之前的方式我们定义为静态数据模型。当用户计算复杂且耗时,高度聚合,筛选的跨度有限,通常为最近n日XX指标,我们会建议使用静态数据模型,并且在凌晨配置定时任务触发,当计算以点查为主,数据本身结果多,筛选的跨度大,返回的数据量小,建议使用动态数据模型。动态的数据模型还让我们支持了一些函数,这些函数可以获取到用户opsId和role等,用来做到一个模型n个用户登录看到的内容各不相同

第二个问题是静态数据模型取数的数据很可能依赖上游调度系统的任务,所以我们就在调度系统中开发了一个元数据模块提供给下游系统,用来查询任务的数据时间。然后在unicorn中接入了这个模块,当一个静态数据模型依赖的上游调度任务数据时间没更新之前,该任务哪怕到了执行时间也只能进入等待依赖阶段。这就解决了对调度系统的依赖问题,用户就可以乐观的把任务稍微往前配置一些,大家做到错峰提交。

第三个问题是模型的复用和前端数据量过大的问题,我们的解是基于calcite做了一层内存版本的engine,处理的数据量不是很大(10w以内),压测数据如下图,这个性能还能接受,所以我们的二层engine可以允许分析师做一些二次sql,重命名,还有用户选的纬度和度量,计算字段等功能都基于这个内存版本的engine来做的

bench

效果

数据模型

image

image