关于SQL语句转DSL语句的⼀些实践和思考(⼀)
现在接触的项⽬是公司的路由中台,每天的数据量是亿级别的,同时要记录每⼀次请求的详细数据
开始的时候这些记录数据是存放到elasticsearch与DB2数据库中各⾃保存
当需要查询某个路由信息的详情时从ES中获取,速度⾮常快,当想获取统计报表的时候从DB2中统计,本来是相安⽆事的,ES速度快,DB2是关系型数据库,易于统计分析
但是因为公司要放弃DB2数据库,所以做统计分析的SQL语句也就没⽤了,需要从ES中获取数据并统计分析
这个时候问题就出现了,较为复杂的SQL语句如何转变为DSL语句
如何分组?如何关联?如何⼦查询
关于基本SQL如何转变为DSL语句,⼤家可以参考这个⽹站www.atotoa/,同时还有⼀些开源框架,这⾥我没有使⽤,公司这边纯内⽹开发,不到那种东西就没⽤,java端使⽤的是highlevelclient
⽬前这些转变中已经做到了分组和聚合的对应,但是其中也有⼀些细节需要拿出来说⼀说
⼀:group by和aggs的区别
SQL语句分组查出来的数据仍然是扁平的数据,最终还是能得到⼀个List<T> ,但是DSL通过Aggs聚合得到的数据是有深度的,⼀层套⼀层,如果想获取到SQL那种数据结构,理论上来说聚⼏次就需要⼏层循环⼀层层的取.
在公司项⽬改造中,为了取出数据使⽤了7层循环去取数据
⼆:也许有的sql还不⽌7层,使⽤7层妖塔似乎有点渗⼈,其他⽅法有没有呢
确实可以将聚合拆分,可以每次aggs⼀次,但是在拿到这些数据时,需要对聚合7次获取的数据设计⼀个算法,通过这种⽅式获取到数据有问题,最终放弃了(其实这是⼀个很好的思路,7次聚合带来的压⼒如果分成7个单⼀聚合,ES服务会⾮常安全)
三:聚合7次带来的服务器压⼒
公司每⽇的数据都存⼊⼀个新的index,测试库2000W数据将近60G ⼤⼩,⽽⽣产库每天亿级数据,这么⼤量的数据进⾏7次聚合,最终会直接让服务器崩溃
多次测试发现多次聚合都导致了测试ES崩溃,虽然⽣产服务器更强⼤,但是这样肯定不⾏
四:使⽤query_match代替聚合
如果要进⾏两次聚合,⽐如下⾯的语句
实际上也可以使⽤
将聚合条件转变为query条件,让聚合次数降低,单次查询数量级下降
⽐如在我的⽣产库中有2E跳数据,我使⽤的query字段有1000个值,那么每次聚合的数据就是2E/1000=20W 把⼀次查询ES 2E的数据量变为查询1000次ES每次查20W的数据量
db2数据库sql语句java代码虽然复杂了点,但是完全值得

版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。