从入门到放弃之「ClickHouse」

1. 写在最前面

最近在整理 api 成功率的问题。但是总结下来以下三点是我分析路上的绊脚石。

  • 上报链路还不够稳定,所以最终实时计算产生的指标是会有所丢失的。
  • 数据存储使用的是 ClickHouse ,而我对这个数据库的「高端」用法一无所知。
  • 需要在有限的时间里,完成对大概 200 多个客户的成功率的分析。

注:此处的「高端」指从数据库小白的角度

1.1 思路

  • 「链路数据上报丢失的问题」

    • 丢失具体随机性,一方面可以跟责任方沟通是否可以优化上报链路的可用性,另一方可以将丢失的点从成功率的计算中过滤出去。
  • 「200 多个客户的成功率分析」

    • 采用抓大放小的原则,优先对请求量在一定数量级的客户进行分析。
    • 对于请求量较小的客户,可以先协商是否可以延期交付

注:「当老板交代你完成一件事情的时候,你第一反应不应该是拒绝,而应该是我先出一份整体的完成思路,请老板帮忙评估一下是否符合交付目标」(ps:论把一件事件完成的符合老板的 N 种想法

2. ClickHouse

2.1 基本概念

ClickHouse 是一个开源的分布式数据库管理系统,用于在线分析处理 (OLAP),它是由俄罗斯搜索引擎公司 Yandex 开发的,并于 2016 年开源发布。

ClickHouse 支持高性能数据压缩和并行查询处理,可以在大规模数据集上快速执行复杂的分析查询,它的主要特点包括:

  • 高性能:可以以每秒百万级别的查询速度处理大型数据集,适用于需要快速响应分析查询的应用场景。
  • 可扩容:支持横向扩容,可以通过添加更多的节点来处理更大的数据集和更高的查询负载。
  • 列式存储: 使用列式存储结构,将同一列的数据连续存储在磁盘上,这种存储结构使得它在进行聚合和过滤操作的时非常高效。
  • 数据压缩:支持多种数据压缩算法,可以大幅减少数据的存储空间,同时不影响查询性能。
  • SQL 支持:支持标准的 SQL 查询语言,可以通过简单的 SQL 语句进行分析查询。

2.2 高端用法

2.2.1 条件判断

java 复制代码
SELECT if(cond, then, else)

如果条件 cond 的计算结果为非零值,则返回表达式 then 的结果,并跳过表达式 else 的结果。如果 cond 为零或 NULL,则将跳过 then 表达式的结果,并返回 else 表达式的结构。

成功率计算使用举例:

scss 复制代码
 sum(if(error_code in(200), response_cnt, 0))/sum(response_cnt) 

2.2.2 HAVING

允许过滤由 GROUP BY 生成的聚合结果。它类似于 WHERE,但是不同的事 WHERE 是在聚合之前执行的,而 HAVING 之后执行。

注:限制,HAVING 如果不执行聚合则无法使用。

过滤请求量低的使用举例:

scss 复制代码
HAVING sum(req_cnt) > 2

2.2.3 CASE WHEN

  • ClickHouse中的CASE WHEN用法与SQL标准中的用法基本相同,用于实现条件分支逻辑

  • CASE WHEN的基本语法如下:

    sql 复制代码
    CASE [expression]
        WHEN condition_1 THEN result_1
        WHEN condition_2 THEN result_2
        ...
        WHEN condition_n THEN result_n
        [ELSE else_result]
    END

阈值调参使用举例:

sql 复制代码
 case when req_succ_cnt/req_total_cnt < 0.9 
     then ts 
     else null 
 end

2.2.4

语法:

sql 复制代码
aggregate_function (column_name)
  OVER ([[PARTITION BY grouping_column] [ORDER BY sorting_column] 
        [ROWS or RANGE expression_to_bound_rows_withing_the_group]] | [window_name])
FROM table_name
WINDOW window_name as ([[PARTITION BY grouping_column] [ORDER BY sorting_column])
  • PARTITION BY - defines how to break a resultset into groups.
  • ORDER BY - defines how to order rows inside the group during calculation aggregate_function.
  • ROWS or RANGE - defines bounds of a frame, aggregate_function is calculated within a frame.
  • WINDOW - allows to reuse a window definition with multiple expressions.

五分钟维度聚合窗口阈值分析举例:

sql 复制代码
sum(req_total_cnt) over (partition by id order by ts range between 240 preceding and current row) as req_total_cnt

这个比较复杂,详细的分析语法如下:

以上语句是一个 ClickHouse 查询语句,用于计算在每个 ID 分组下,从当前行往前推 240 个范围内的请求总数。

具体解释如下:

  • sum(req_total_cnt):这是一个聚合函数,计算前面定义的req_total_cnt列中的值的总和。
  • over:这是一个窗口函数,它允许在聚合函数的基础上执行额外的操作。它指定在给定窗口范围内执行聚合函数。
  • partition by id:这是一个窗口分区子句,它定义了按照id列进行分组,即针对每个不同的id值执行聚合计算。
  • order by ts:这是一个窗口排序子句,它根据ts列的值对数据进行排序。窗口函数将按照此顺序计算。
  • range between 240 preceding and current row:这是一个窗口范围子句,它指定了窗口的范围,「240 preceding」表示从当前行往前推240行,「current row」表示当前行。

3. 碎碎念

ClickHouse 「高端」的语法其实还有很多,但无奈这波流感的威力实在是太强了,感觉中招之后,就很难受,不写了,我要继续吃颗退烧药了。

  • i was looking for a person who would encourage me support me inspire me keep me focused make me happy and give me unconditional love then i really that all along that person was myself
  • 诞生降世的意义,就是为了采集这个世界中美丽的事物啊!
  • 他很辛苦,所以要给他高温补贴,高工资,防中暑物资,不拖欠工资,而不是来教育我们不要抱怨生活。

4. 参考资料

相关推荐
憨憨小江38 分钟前
SpringBoot接收参数
chrome·spring boot·后端
isolusion1 小时前
Springboot配置嵌入式服务器
服务器·spring boot·后端
玉红7771 小时前
Erlang语言的数据结构
开发语言·后端·golang
后端转全栈_小伵2 小时前
从 Coding (Jenkinsfile) 到 Docker:全流程自动化部署 Spring Boot 实战指南(简化篇)
java·spring boot·后端·docker·自动化·集成学习
m0_748251722 小时前
Spring Boot——统一功能处理
java·spring boot·后端
dream21st3 小时前
从零开始采用命令行创建uniapp vue3 ts springboot项目
spring boot·后端·uni-app
小蒜学长3 小时前
基于Spring Boot的宠物领养系统的设计与实现(代码+数据库+LW)
java·前端·数据库·spring boot·后端·旅游·宠物
GraduationDesign4 小时前
基于SpringBoot的在线文档管理系统的设计与实现
java·spring boot·后端
xiaosannihaiyl245 小时前
Scala语言的函数实现
开发语言·后端·golang
山山而川粤10 小时前
母婴用品系统|Java|SSM|JSP|
java·开发语言·后端·学习·mysql