在不少项目中,埋点数据使用表格来统计的,随着项目的进行,数据量愈来愈复杂,愈来愈难以维护。因此不少公司都已经开发了一整套系统,从埋点的录入到代码的输出。node
咱们项目中iOS和Android双方的埋点内容因为沟通以及一些缘由,也没有彻底统一,增长了不少沟通成本,为了规范化和统一化,咱们也须要这样一个相似的系统。可是不少时候一套系统对于一个小项目来讲太过于复杂了,因此这里我作了一个轻量级的本地管理客户端。https://github.com/djs66256/lilyreact
因为咱们实现的是一套本地管理的系统,因此我把程序系统和数据分开了,因此启动的时候须要选择对应的数据目录,好比本项目目录下的/demo-data/,以微信为例。关于目录下文件功能格式会在以后说明。webpack
启动以后,咱们能够看到咱们的埋点数据界面,这里我根据咱们的需求把数据分为3类:git
事件-数据点github
页面web
具体参数正则表达式
数据点包含全部埋点信息,参数是由参数列表选择,能够查看历史和进行编辑。npm
页面包含了咱们的全部页面id,由于一个普通的App拥有的页面不会有太多,因此页面的分级能够少一点。json
参数包含了咱们埋点过程当中全部遇到的参数,考虑到咱们项目中所涉及到的参数比较统一,因此就没有进行分类redux
每行数据的每次改动都会造成一条记录保存在本地,这样咱们就能够追溯历史变动了。这里还把全部参数都列了出来,而不是主页面精简后的了。因为性能问题,这里暂时只显示了最近50条记录。
以上全部列表的数据项都是动态可配的。在设计之初,考虑到数据内容可能会根据须要动态调整,因此把全部内容都设计为动态可配的了,又为了在磁盘上的数据的可读性,把全部数据都采用文本json保存,这样也兼容了动态的数据,具体实现后面会详细讲解。
当选择了一个目录后,点击导航栏的建立能够建立一条新的数据,数据格式内容根据根目录属性配置。
点击一行列表后的编辑按钮进入编辑页面,每次保存都会产生一条修改记录。
可选的参数为在根目录为参数内的全部内容,这样设计的缘由是为了将来可能对埋点数据的自动化验证,从而须要一个格式化的参数列表,而不是一段文字描述。
为了能够对埋点的整理归类,因此作了简单的搜索功能,可搜索字段也是根据事件目录的配置。
全部搜索字段都是使用正则表达式完成,因此若是须要更复杂精确的匹配,这里也能够输入一段正则来匹配。
点击编译,会把全部事件和页面数据自动生成一份代码,这里是根据须要定制的,因此我只作了iOS的一个样例格式。这里咱们从老数据转化过来的时候有重复埋点,因此在转化的逻辑中加入了去重,关于自定义和接入编译系统以后会详细描述。
以demo-data数据配置为例。
在全部的数据中,概念都是节点Node,根据功能分为两类:
目录节点DirNode,负责分级和归类。
数据节点StatNode,负责记录每一个数据的具体内容。
全部数据持久化经过json格式保存为文本文件,因此能够直接查看文件内容。
按照层级结构建立同样的目录层级结构,每一个DirNode下面都有一个config.json文件,包含该节点信息。
在最底层每一个StatNode会产生一个目录,目录下会根据历史生成1.json,2.json,3.json名字依次递增的文件,保存每次修改后的数据。这里目录名字使用id来命名是为了解决数据埋点id可能存在重名的问题。
只能在目录的最底层能够建立数据,这是为了解决展现时候的难以同时展现数据和目录的问题。
每一个文件中都须要具有一些基础属性:
name外部显示的名字,对于目录节点则是目录名字
id要求惟一的id,因为DirNode个数比较少,并且固定,因此没有设计建立的功能,本身修改时须要保证惟一。数据节点则会生成一个MD5来填充。
isDirectory表示是不是DirNode
包含一个columns数组,这是一个很是重要的配置,除了基础属性,全部StatNode里的数据项都是根据该字段动态生成。
这里是一个事件节点例子:
[
{
"type": "text", // 字段类型(暂时只支持text和param)
"required": false, // 是否必填
"title": "描述", // 展现的列名
"key": "description", // 对应于json中的key值
"visible": true, // 在主界面是否隐藏
"editable": true, // 是否可编辑,在编辑和建立界面是否可见
"searchable": true // 是否能够做为搜索参数,影响搜索界面 },
{
"type": "params",
"paramsKey": "params", // 若是是param类型,须要指定`DirNode`的id
"required": false,
"title": "参数",
"dataIndex": "params",
"key": "params",
"visible": true,
"editable": true,
"searchable": false
}
]
能够动态增长或者修改数据项,这样会很是灵活并且能够不经过修改代码就配置数据内容。
节点间的columns是能够被继承的,也就是说子目录的columns一定包含父目录的全部数据内容。惋惜目前的使用场景并无这个要求。
全部其余目录的配置都是相似的。
一样看一个例子
{
"name": "点赞",
"statId": "onPraise",
"description": "包括3D touch页面",
"version_iOS": "1.0",
"version_Android": "1.1",
"createTime": "2017-04-03T12:22:38.372Z",
"params": [
{
"name": "用户ID",
"description": "",
"createTime": "2017-04-03T11:59:13.467Z",
"isDirectory": false,
"id": "814db1c837ac436ebb569d3554b51fb1",
"paramId": "userId"
},
{
"name": "朋友圈状态",
"createTime": "2017-04-03T12:14:06.676Z",
"isDirectory": false,
"id": "866982e498224b15aa4602f2893f7995",
"paramId": "timelineId"
}
],
"isDirectory": false,
"id": "9b538d5bee1c40ed979e5a38143a9829"}
全部数据都是根据上述配置生成,其中param比较特殊,是把选择的数据节点直接拷贝了一份,这样作的缘由是怕其余地方修改或者删除了致使数据不一致的问题,这样作更符合埋点这个需求。
目前编译系统仍是作在了代码中,因为系统自己是有NodeJS实现的,因此要动态配置编译系统仍是很是简单的。
编译系统比较开放,这样能够开放更多的功能,但同时也引入了数据风险,以后须要改进下,让编译系统能够动态接入,而且屏蔽内部数据和编译系统的直接联系。
目前代码放在/script目录下。
这里对整个系统的代码逻辑进行说明。
最基本的功能,须要可以在团队内共享数据,其中最方便的就是利用git系统了,因此在每次修改数据的时候除了本地持久化之外,会自动同步git上的数据文件,这也是为何要数据分离的一个缘由。
若是可以接上埋点系统,那么能够经过该系统去分析结果,这个工做量可能会比较大,是一个设想。
若是可以接上自动化测试或者设备,就可以验证埋点数据是否正确,这个的工做量也可能会比较大。
目前完成了最基础的管理埋点和生成代码功能。
nodejs
Mac能够经过brew install nodejs来安装
须要electron和webpack
npm install -g electron webpack
首先npm install
而后须要连接本地库
cd dd-statnpm linkcd ../statnpm link dd-stat
最后
npm run dev #开启webpack -wnpm run app #启动应用
dd-stat是系统的数据层,包含了数据结构和持久化。
stat是界面层,为了实现简单,目前全部逻辑都是在渲染层作的,由于咱们的数据量按照咱们的需求是不太可能达到如此大的数目,是不太可能出现性能问题的。
stat依赖支付宝的ant design框架来搭建,最初是用redux来组织(/lib),后来发现太过于复杂,应用自己就是个简单的场景,因此后来改成react-router来组织(/lib2)。
/script是数据编译的代码,是导出编译后代码或者导出其余格式的一个出口,能够根据须要扩展。
最初的想法是让程序来自动同步git,由于应用的使用场景比较简单,不太可能出现多人同时编辑同一个数据的问题,因此让程序来自动同步数据是最好的,因为时间问题,暂时没有加入。
如今编译系统是和应用代码捆绑在一块儿的,最好可以脱离代码,而且能够动态配置编译模板。
增长对bool,枚举单选,枚举多选,时间等的支持,项目暂时尚未这样的需求。
网易云新用户大礼包:https://www.163yun.com/gift
本文来自网易云社区,经做者段家顺受权发布。