事件量不是长出来的,是当初一个一个设计出来的。
一、账单超过了服务器总和
周岚第一年用得很省。她选了一家按事件计价的第三方服务,每月事件不多,账单只是服务器开销的零头。
第二年她做了一次改版,加了阅读进度、折叠面板和滚动深度,仪表盘上的曲线丰富了很多。三个月后账单来了,数字超过了服务器、数据库和对象存储三项之和。她翻事件字典才发现,「滚动 10%」被单独记成了一个事件,而一个用户读一篇文章会触发十几次。
以下情境为教学假设,人物、引语和数字不代表经核实的真实案例。
事件量是设计出来的,不是长出来的。 每一个 scroll_depth 都是当初某次「顺手加一下」的结果;加的时候没人算过它乘上人均次数是多少。
采样要按用途分层,不能一刀切。 把付费事件也采样,等于把结论也采样;把诊断事件全量存,等于为几个百分点的精度付全款。
保留期是成本的主要杠杆。 存储按月累积,保留九十天和保留三年差十二倍;多数诊断数据过了季度就没人再看。
省下来的钱要能换成一次功能开发。 成本优化的目标不是账单好看,是把钱挪到能带来收入的地方;省不出一整块,就等于没省。
二、一年到底有多少条事件
先把量算清楚,再谈采样。基线是 24 个日活、人均 18 个事件。
| 项 | 算法 | 结果 |
|---|---|---|
| 活跃人日 | 24 DAU × 30 天 | 720 |
| 人均事件 | 事件字典实际有量的 18 个 | 18 |
| 日事件 | 720 × 18 ÷ 30 | 432 |
| 月事件 | 432 × 30 | 12,960 |
| 年事件 | 12,960 × 12 | 155,520 |
| 单条大小 | 6 个属性加时间戳与 ID | 600 字节 |
| 月存储 | 12,960 × 600 B ÷ 1,048,576 | 7.4 MiB |
| 年存储 | 155,520 × 600 B ÷ 1,048,576 | 89 MiB |
18 个事件是「有量」的数量。 事件字典写了 24 个,其中 6 个是预留或极少触发;按 24 算会把模型高估三成。
人均 18 次是设计值,不是观测值。 它等于「一次会话里真正有价值的动作数」;超过 25 次通常意味着有诊断事件在按秒记录。
存储量小不代表账单小。 89 MiB 一年,任何对象存储都放得下;按事件计价的成本在「条数」上,不在「字节」上。
月与年要先算年。 月账单会随活动波动,年量才能看出趋势;采购与选型都按年量谈。
模型要写进事件字典。 每加一个事件,就在字典里补一列「预计人均次数」;乘出来超过月量 10% 的,必须先过采样方案。
三、三类事件,三种待遇
不是所有事件都值得全量保留。按用途分三类,采样规则就清楚了。
| 类别 | 占比 | 是否采样 | 理由 |
|---|---|---|---|
| 结果类 | 18% | 不采样 | 注册、激活、付费是结论,缺一条就少一个事实 |
| 驱动类 | 40% | 不采样 | 用于漏斗与归因,样本偏差会直接改变判断 |
| 诊断类 | 42% | 采样 10% | 用于定位问题,看的是分布不是个体 |
结果类是不可逆的。 付费事件少记一条,当月收入就对不上;这类事件宁可重复,也不能丢。
驱动类决定分步转化。 漏斗每一步的分子分母都要精确;采样会让 53.9% 变成 51% 或 57%,而这个差距足以让你改错方向。
诊断类只需要分布。 滚动深度、面板展开、搜索无结果,这些问题看的是「多数人停在哪」,544 条样本足够画出形状。
占比要按条数算,不是按事件种类算。 24 个事件里诊断类可能只有 6 个,但它们的触发频率高,条数占 42%。
分类写进字典的同一行。 事件名、属性、类别、是否采样放在一张表里;新增事件时,类别是必填项。
四、复算:采样与保留各省多少
把三类规则套进月量,再叠加保留期,成本结构就出来了。
诊断类月量 = 12,960 × 0.42 = 5,443 条
按 10% 采样保留 = 5,443 × 0.10 = 544 条
每月减少 = 5,443 − 544 = 4,899 条(4,899 ÷ 12,960 = 37.8%)
采样后月量 = 12,960 − 4,899 = 8,061 条
采样后年量 = 8,061 × 12 = 96,732 条
原始年量 155,520 × 600 B = 89 MiB;索引副本 ×2 = 178 MiB
采样后年量 96,732 × 600 B = 55.4 MiB;索引副本 ×2 = 110.7 MiB
明细保留 90 天 = 8,061 × 3 = 24,183 条 ≈ 13.8 MiB
自建存储与计算 ≈ 5 美元/月
一年少存 = 155,520 − 96,732 = 58,788 条
37.8% 的削减几乎全部来自诊断类。 结果类与驱动类一条没动,结论的精度没有损失;被砍掉的只是「用户滚到第几屏」这类定位信息。
544 条样本的误差约 ±4 个百分点。 按比例估计的常规算法,544 条在 95% 置信水平下的误差约 4.2 个百分点;判断「多数人停在前两屏」够用,判断「转化率是 53.9% 还是 54.1%」不够。
索引副本才是存储的大头,保留期决定它会不会逐年累加。 原始口径 89 MiB 建一份索引就变 178 MiB;采样后 55.4 MiB 变 110.7 MiB,省下 67 MiB,比例与条数一致。明细只留九十天,峰值就是 8,061 × 3 = 24,183 条,约 13.8 MiB;超过九十天的需求走聚合表,不查原始事件。
自建约 5 美元/月,省的是「条数」不是「字节」。 自建之后按条计价的账单消失,剩下的是磁盘与计算;一年少存的 58,788 条如果一条都没被查过,它们从一开始就不该被全量保留。
什么时候不该采样,比采样率更值得写清楚。 样本本身小于 100 时,任何采样都是在制造噪声;漏斗末步只有 120 条,采 10% 剩 12 条,连「本周比上周多还是少」都答不了。
| 场景 | 样本量 | 结论 |
|---|---|---|
| 漏斗末步(付费) | 120 | 不采样,120 条已经是全量 |
| 漏斗末步采样 10% | 12 | 不可用,12 条撑不起任何比例 |
| 诊断类分布 | 544 | 可用,看形状与中位数 |
判断标准是「要回答什么问题」,采样率还要写进报表脚注。 问「大多数人停在哪」可以用样本,问「这个月有多少人付费」必须用全量;看板上的诊断类数字如果不标注 10%,三个月后没人记得它是抽样值。
五、行动清单与复算验收
先量,再砍,最后才谈工具。以下八条按顺序执行。
- 给事件字典补两列:类别、预计人均次数。
- 用 24 个日活乘 18 个事件,算出自己的月量与年量。
- 把现有事件分成结果、驱动、诊断三类,核对占比是否为 18/40/42。
- 找出触发频率最高的三个诊断事件,先给它们定采样率。
- 确认结果类与驱动类一条都不采样,写进字典。
- 给明细表设九十天保留,超期只留聚合。
- 在报表脚注标明哪些数字来自采样、采样率多少。
- 每季度核对一次账单与事件量,涨幅超过 30% 就查新增事件。
验收标准:你能说出每一条事件为什么被保留、为什么可以被采样;说不出来,说明它只是被记录,没有被设计。
使用边界与实操验收
采样不豁免数据最小化义务。 能不采集的字段就不采集,采样解决的是成本,不是合规;告知与授权仍要按适用法规执行。
采样后的绝对值不能直接比较。 诊断类采 10% 时,报表上的条数是样本数;要还原总量得乘 10,但还原值只用于量级判断,不用于精确结论。
保留期不等于备份。 九十天保留是查询窗口,备份是另一套策略;两者混在一起,恢复演练时就会发现缺数据。
自建成本不含人力。 5 美元/月是磁盘与计算,不含部署、升级与排障的时间;一个人的项目要把这部分算进去再决定是否自建。
验收看两件事。 账单是否随事件量同比例增长,以及出问题时能否在十分钟内定位到具体事件;两者有一项不达标,采样或保留策略就还没调对。
关键参考与核验范围
核验日期:2026-10-26。以下链接用于核对采样方式、保留期与存储策略的一般做法,本文未逐条引用其内容。
- OpenTelemetry 采样 :用于核对头部采样与尾部采样的区别及适用场景。
- OpenTelemetry SDK 环境变量 :用于核对采样率参数的配置口径。
- ClickHouse TTL :用于核对按时间自动过期、降采样与冷热分层的一般做法。
- Snowflake Time Travel :用于核对数据保留窗口与历史版本保留的配置边界。
引用口径。 本文只借用「按用途分层采样、按时间设保留」这一一般做法;155,520 条、42%、10% 与 110.7 MiB 全部是教学假设,与上述材料无关。
核验范围。 核验的是事件量模型、三类采样规则与九十天保留这套结构是否仍可操作,不是比对某个分析服务的计价方式。
如何自行复核。 用自己最近三十天的事件条数除以 30,得到日均;再乘 12 得到年量,与账单上的计费条数对比;差额超过 10%,说明还有一类事件没被分类。
系列导航
继续阅读
探索更多技术文章
浏览归档,发现更多关于系统设计、工具链和工程实践的内容。