☰
一次问数从 38 秒到 4 秒,我把耗时拆成了五段
2026/11/6 6:39:34 网站建设 项目流程

一次问答的链路测量手记 · 从 38 秒到 4 秒

01周一早上那三十秒

周一早上八点四十,运营总监在群里丢了句话,上周租金收缴率怎么掉这么多。

小周打开问数平台,把这句话原样敲进去,按回车。

转圈。转了很久。她看一眼手机,又看回屏幕,然后关掉页面,翻出上个月那份还没删的旧报表。

这个动作我记了很久。报表本身没什么问题,问题在我们费了半年力气做到能用一句话查数,结果败在等三十秒上。

后来我拿这件事做了两个月,把一次问数的耗时从头到尾量了一遍。这篇写这个。

02先记秒数,别猜

第一版做了件很笨的事,给链路每一段打点。

一次问数走五段路。听懂问题,含分词、实体识别、时间归一化,「上周」到底指哪七天的哪一天开始。找表找字段,从两百多张表里筛出可能相关的几张。拼 SQL 是模型干活。执行是数据库干活。收尾出图出文由前端和模板管。

打点跑了三天,抓了两千多次问答。

结果第一眼就把我的判断推翻了。我一直以为慢在模型上,那东西听着就贵。实测里模型那段平均 3.1 秒,数据库那段平均 26 秒。

38 秒的总耗时,七成耗在数据库。模型背了锅。

我后来想过为什么会误判。大模型是黑盒,等它的时候屏幕什么也不动,人容易把等待感全记到它头上。数据库在后台扫几百万行,你看不见,也想不到。

看不见的地方最藏问题,性能上尤其明显。

0326 秒是怎么来的

那段时间我干的事,基本是跟在每条慢查询后面捡东西。

捡出三类。

索引被自己废掉。合同表的起租日期上有索引,模型生成的 SQL 写成to_char(起租日期,'YYYY-MM')= '2026-10',字段被函数包了一层,索引用不上,只能全表扫。这种写法在自然语言转 SQL 里到处都是,因为用户说的就是十月,模型顺手把日期格式化了。

分区裁剪失效。我们按年做了分区,条件被 cast 过,优化器识别不出该走哪个分区,每次扫全部。

join 得太多。问一句这栋楼租金收了多少,模型会老实关联合同、房源、租户、收款四张表。前两张必要,后两张只为了显示名字。

三类叠起来,「上周收缴率」这句看起来很简单的问话,扫了四百多万行。

改法很朴素。日期条件换成开区间,起租日期 >= 月初 and 起租日期 < 下月初,函数挪到常量那边。分区字段单抽一列存年份,别在查询里算。join 按需生成,用户问了租户名才带租户表。

光这三条,26 秒掉到 9 秒。

04宽表,和宽表带来的新麻烦

剩下 9 秒,靠改 SQL 压不下去了,它本来就要扫那么多明细。

我们加了一层日粒度汇总表。收缴率、出租率、单方能耗、在租面积这几类最常被问的指标,每天凌晨算一遍落表,一行是一栋楼一天。

查询进来先判断能不能命中汇总表,能命中就不碰明细。

9 秒变成 2.6 秒。

汇总表有代价,代价在口径。

明细算收缴率和汇总算收缴率,中间差一个「当月应收到期日已过」的过滤条件,写汇总作业的同事漏了。上线第三天,财务发现平台给的收缴率和他们自己算的对不上,差两个点。

账算清楚就明白了,多加一层计算就多一个口径要守。我们后来把每个汇总指标的取数逻辑写进配置文件,和明细口径并排放,改一个必须同时改另一个,评审时一起看。

05缓存,三个 key 少一个就出事

再往下压只能靠缓存。高频问题命中直接返回,这是最省事的一招。P50 从 2.6 秒掉到 400 毫秒。

然后就出事了。

数字过期。缓存 key 当时只用问题原文,没带时间参数。运营早上问这个月出租率,下午再问,拿到早上的旧数。上午刚签了份合同,数字该变,页面没变。

越权。两个人问同一句话,结果该不一样,数据范围不同。key 里没带权限,A 的答案给了 B。

口径切换。中途调整过一次收缴率的分母,缓存里的旧结果还在,新旧两套数混着返回。

三次事故之后,key 定成三段拼起来,归一化后的问题、时间窗口、权限范围。少一段都不行。

有个取舍要说清。带上权限之后命中率掉了差不多一半,它变成了按人区分的缓存。拿命中率换正确性这笔账,我觉得不用犹豫。

06四秒之后,她说还是慢

数字压到 4.2 秒,我挺得意,专门跑去找小周演示。

她试了两次,说,还是有点慢。

我有点不服,四秒还慢。后来让她一边操作一边说感受,才明白问题在哪。

等四秒和等四秒不一样。一种屏幕什么都不动,你不知道它在干嘛。一种上面一行小字在跳,正在查十二万条合同,已经找到三百八十六条,你会觉得它在干活。

差别在进度,秒数只是背景。

后面做的事没什么技术含量。中间状态吐出来。先出结论那一句和总数,明细后补。SQL 执行超过两秒先显示正在查询,预计还需两秒。图表不等明细全量,先画前一百条。

同一套后端,改完这些,小周的原话是,现在感觉挺快的。

07现在的做法

我们没再追更低的数字。P95 稳在六秒上下,偶尔遇到跨年的大范围问题会冲到十几秒,这个我认。

每月看一次 P95 和慢查询 Top20,掉队的拉出来单独看。超过八秒才立项,其余记账不动。

优化到四秒花了我两个月,四秒到三秒可能要再花两个月,那一秒用户感觉不到。工程上容易犯的错,是把能优化的都优化一遍,忘了问一句值不值。

上周我又看见小周在那个页面敲字。这次她敲完没关页面,等着,屏幕上那行小字在跳。

大概三秒,表格出来了。

文中所涉数据来自一次真实的链路打点,跑了三天,两千多次问答。数字做了取整处理。

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询