• 4

  • 451

  • 收藏

30亿日志,检索+分页+后台展示,你是否遇到过更奇葩的需求?

3个月前

沈老师,你好,想请教一个数据库查询日志,前台页面显示的问题。

需求

(1)按照某些特定检索条件查询日志;

(2)通过前台 Web 页面查询并显示相关日志信息;

(3)检索需求包含用户,时间段区间,类型等特定字段;

希望做到

(1)查询速度尽可能快;

(2)支持分页查询;

 

目前方案

日志信息存储在 Oracle 中,根据日期对 Oracle 做了分区处理,每天生成一个分区表,每个分区表中的数据总量大概在 1000W 左右。在相关查询字段例如用户,类型上建立索引,来满足不同维度的查询需求。

潜在问题

跨分区的查询,求记录总数(计算分页时的查询),耗时要 3-4 分钟,请问有什么优化方法么?

== 问题描述完 ==

这个需求还是非常变态的,通常日志会进行过滤 / 结构化 / 汇总,放入数据仓库,建立业务宽表,宽表上的查询,一般不会具体查一行一行的记录。

如果要支持检索,并一行一行在 Web 后台进行展示,至少要解决几个方面的问题

(1)存储问题;

(2)检索问题;

(3)扩展性问题(数据量扩展,检索字段扩展);

一、存储问题

是否可以用关系型数据库存储日志?

如果日志格式固定,检索条件固定,是可以的。

例如:

2019-08-11 23:19:20 uid=123 action=pay type=wechat money=12

可以转化为表:

t_log(date, time, uid, action, type, money)

然后在相关字段上建立索引,以满足后台查询与展示的需求。

数据量太大,怎么解决?

按照题目描述,日数据量大概在 1000W 级别,1 年的数据量大概在 36Y 级别。

如果用 Oracle 存储,1000W 为一个分区表:

一年需要 365 个分区,跨分区的查询性能较低,不太合适。

改为 1 个月一个分区:

单分区 3Y 记录,大部分分区无写操作(插入,修改,删除),只有索引上的读操作,读写性能基本能抗住。一年 12 个分区,性能比 365 个分区好很多。

虽然本例的日志可以结构化(将日志转化表),由于数据量太大,其实关系型数据库不太适用,可以用适合更大数据量的 ES 或者 Hive 来存储。

二、检索问题

日志格式固定,检索条件固定,如果用关系型数据库或者 Hive 存储,可以在相关字段上建立索引,来满足查询需求。

如果用 ES 来存储,其内部用倒排表实现,天然支持检索。

三、扩展性问题

数据量扩展

不管用 Oracle,ES 还是 Hive 来存储,它们的区别只是单实例 / 单集群存储容量不一样,如果数据量无限扩展,本质上的解决方案还是 “水平切分”。

需要注意的是,尽量不要使用自带的 “分区表” 来扩展,而在业务层自己拆分。

画外音:《互联网公司为啥都不用分区表?》。

检索字段扩展

如果日志不是标准化的,检索字段也不是固定的,那就麻烦了,那就变成了也 “搜索引擎” 的问题。

此时使用 ES 是更为合适的,不过结合无限的数据量,最终可能需要自己实现存储于检索引擎(类似于百度,存储容量无限,检索字段不固定)。

画外音:《“搜索” 的原理,架构,实现,实践!》。

总结

结合本例,日志量大,模式固定,建议:

(1)最建议,使用 Hive 存储,使用索引的方式实现日志后台检索需求;

(2)如果扩展性要求稍高,可以使用 ES 实现存储与检索,使用水平扩展来存储更大的数据量;

希望上述思路对星官有帮助,经验有限,也欢迎大家贡献更多更好的方案,思路比结论重要。

免责声明:文章版权归原作者所有,其内容与观点不代表Unitimes立场,亦不构成任何投资意见或建议。

物联网

451

相关文章推荐

未登录头像

暂无评论