ARTICLE DETAIL

建站实战干货

来自一线的建站与推广经验沉淀,每一条都经过真实交付验证。

Cal.diy 预订流程性能测试指南:基于 Grafana k6 的四阶段压测实战

2026/9/11 15:02:46 拓冰建站 浏览量
Cal.diy 预订流程性能测试指南:基于 Grafana k6 的四阶段压测实战 Cal.diy 预订流程性能测试指南基于 Grafana k6 的四阶段压测实战【免费下载链接】cal.diyScheduling infrastructure for absolutely everyone.项目地址: https://gitcode.com/GitHub_Trending/ca/cal.diy本指南以 Cal.diy 仓库中的 性能测试套件文档 为核心系统讲解如何利用 Grafana k6 对 Cal.diy 最关键的预订Booking流程开展 smoke、load、stress、spike 四类压测。读完本文你将掌握测试目录的组织方式、命令行与 Docker 两种运行手段、阈值与负载参数的源码级配置以及在此基础上扩展新压测用例的完整方法。性能测试套件概览守护核心预订链路Cal.diy 是一个开源的日程预订基础设施其预订流程Booking Flow——从用户访问某个可预订页面到提交预订——是最核心、最影响用户体验的链路。为此仓库在 packages/testing/performance 目录下内置了一套基于Grafana k6的专用性能测试套件专门用于测量预订流程在不同负载条件下的表现覆盖从低负载功能验证到每分钟数万请求的高并发场景。测试目录结构packages/testing/performance/ ├── smoke/ # 冒烟测试最小负载验证功能是否正常 ├── load/ # 负载测试模拟预期的正常负载每分钟数千请求 ├── stress/ # 压力测试模拟重负载寻找系统瓶颈点每分钟数万请求 ├── spike/ # 尖峰测试模拟突发流量短时间内激增至每分钟数万请求 ├── utils/ # 共享工具与辅助函数 │ ├── config.js # 全局配置阈值、测试用户、环境变量读取 │ └── helpers.js # 核心场景封装预订页面访问 └── README.md # 官方使用文档本指南的原始依据每个负载档位目录下都对应一份booking.js它们复用utils/中的共享配置与辅助函数仅通过options虚拟用户数、时长、阶段与阈值区分压测强度。这种场景复用、参数分层的组织方式使得新增或调整压测档位非常轻量。前置条件运行这套测试需要满足两个基本条件安装 k6在你的机器上安装 Grafana k6官方支持通过包管理器、二进制或 Docker 镜像安装。准备被测实例本地运行中的 Cal.diy默认指向http://localhost:3000或者一个已部署的 Cal.diy 实例。此外若使用 Docker 脚本方式运行还需要本机安装并启动 Docker。运行测试从单条命令到完整压测设置 BASE_URL所有测试默认针对http://localhost:3000运行。若要压测其他环境通过BASE_URL环境变量指定BASE_URLhttps://your-cal-instance.com k6 run tests/performance/smoke/booking.js注意文档中的命令路径如tests/performance/smoke/booking.js对应的是测试位于仓库根目录tests/下的原始布局。在当前仓库中性能测试实际位于 packages/testing/performance因此直接运行时应使用仓库内实际路径例如k6 run packages/testing/performance/smoke/booking.jsBASE_URL的读取与防护逻辑在 config.js 中实现细节见下文共享配置一节。直接运行各档位测试# 运行预订流程冒烟测试最小负载验证功能 k6 run packages/testing/performance/smoke/booking.js # 运行预订流程负载测试每分钟数千请求 k6 run packages/testing/performance/load/booking.js # 运行预订流程压力测试每分钟数万请求 k6 run packages/testing/performance/stress/booking.js # 运行预订流程尖峰测试突发流量激增至每分钟数万请求 k6 run packages/testing/performance/spike/booking.jsk6 运行结束后会自动输出完整的指标报告包括请求吞吐率、错误率、延迟分位数等若任一阈值被突破k6 会以非零退出码结束便于接入 CI。使用 Docker 脚本运行推荐方式除了直接调用 k6套件还提供了 run-k6-local.sh 脚本它会自动检测操作系统Linux / macOS并配置合适的 Docker 参数免去手动拼接docker run命令的麻烦。前置条件Docker 已安装并启动Cal.diy 在本地运行默认http://localhost:3000。交互式菜单用法从仓库根目录执行./packages/testing/scripts/run-k6-local.sh脚本会显示交互式菜单Select a test: 1) smoke 2) load 3) stress 4) spike 5) all 0) exit命令行直传参数也可以跳过菜单直接通过 CLI 参数指定档位# 运行冒烟测试 ./packages/testing/scripts/run-k6-local.sh smoke # 依次运行 smoke/load/stress/spike 全部档位 ./packages/testing/scripts/run-k6-local.sh all脚本实现要点源码级阅读 run-k6-local.sh 源码可以理解脚本的几项关键行为操作系统适配通过uname -s判断平台。在 Linux 下追加--add-hosthost.docker.internal:host-gateway让容器内能通过host.docker.internal访问宿主机上运行的 Cal.diymacOS 无需额外参数其他系统直接报错退出。镜像可定制默认使用grafana/k6镜像可通过K6_IMAGE环境变量覆盖。目录挂载将本地测试目录挂载到容器内/scripts工作目录挂载源可用MOUNT_LOCAL覆盖默认按脚本所在位置推算。当前仓库中测试根目录为 packages/testing因此运行脚本时建议显式指定MOUNT_LOCALpackages/testing ./packages/testing/scripts/run-k6-local.sh load环境变量透传脚本始终注入BASE_URLDocker 模式下默认http://host.docker.internal:3000并仅在变量存在时透传TOKEN、TEST_USER_FREE、TEST_PASSWORD_FREE、TEST_USER_PRO、TEST_PASSWORD_PRO。健壮性检查若测试目录不存在脚本会在启动容器前报错退出。自定义运行参数BASE_URLhttp://localhost:3000 \ TOKENyour_token_here \ ./packages/testing/scripts/run-k6-local.sh load脚本支持的环境变量BASE_URLTOKENTEST_USER_FREETEST_PASSWORD_FREETEST_USER_PROTEST_PASSWORD_PRO共享配置thresholds、测试用户与工具函数config.js 是整个套件的配置中枢所有档位的测试脚本都从这里导入常量。BASE_URL 与生产域名保护export const BASE_URL __ENV.BASE_URL || http://localhost:3000; if (BASE_URL.includes(cal.com)) { throw new Error(BLOCKED: Do not run against production domain); }这里有两层设计意图默认指向本地http://localhost:3000同时硬性拦截包含cal.com的域名一旦误配到生产域名测试在启动阶段就会抛错终止从机制上杜绝了误压生产环境的可能。模拟思考时间export const SLEEP_DURATION { SHORT: 1, MEDIUM: 3, LONG: 5, };SLEEP_DURATION定义了短1s、中3s、长5s三档思考时间用户阅读页面的停顿用于让请求节奏更接近真实用户行为。阈值体系export const THRESHOLDS { HTTP_ERRORS: [rate0.01], RESPONSE_TIME: { SMOKE: { p95: [p(95)500], p99: [p(99)1000] }, LOAD: { p95: [p(95)1000], p99: [p(99)2000] }, STRESS: { p95: [p(95)2000], p99: [p(99)4000] }, SPIKE: { p95: [p(95)3000], p99: [p(99)6000] }, }, };核心阈值分为两类档位HTTP 错误率p95 延迟p99 延迟阈值严格程度smoke 1% 500ms 1000ms最严格用于捕捉性能回归load 1% 1000ms 2000ms中等针对正常运营条件stress 1% 2000ms 4000ms较宽松针对重负载spike 1% 3000ms 6000ms最宽松针对突发流量rate0.01表示请求失败率http_req_failed须低于 1%延迟阈值随负载强度逐级放宽反映负载越高、容忍度越大的测试哲学。测试账号池export const TEST_USERS new SharedArray(users, () [ { username: __ENV.TEST_USER_FREE || free, password: __ENV.TEST_PASSWORD_FREE || free }, { username: __ENV.TEST_USER_PRO || pro, password: __ENV.TEST_PASSWORD_PRO || pro }, ]); export function getRandomUser() { return TEST_USERS[Math.floor(Math.random() * TEST_USERS.length)]; }测试账号池同时包含免费版默认free/free与 Pro 版默认pro/pro两组账号通过SharedArray在所有虚拟用户VU间共享并用getRandomUser()随机抽取模拟不同套餐用户的混合流量。防缓存与随机等待export function randomQueryParam() { return nocache${Date.now()}; } export function randomSleep(min SLEEP_DURATION.SHORT, max SLEEP_DURATION.MEDIUM) { if (min max) { throw new Error(min cannot be greater than max); } const sleepTime Math.random() * (max - min) min; sleep(sleepTime); }randomQueryParam()为每个请求追加基于时间戳的nocache参数绕过浏览器/CDN 缓存保证压测打到真实渲染链路randomSleep()在给定区间内随机休眠且内置min max的参数校验。核心场景实现预订页面访问helpers.js 中封装了本套件唯一的用户旅程场景viewBookingPageexport function viewBookingPage(username, eventSlug) { return group(View Booking Page, () { const url ${BASE_URL}/${username}/${eventSlug}?${randomQueryParam()}; const response http.get(url, { tags: { name: Booking Page }, timeout: 30s, }); check(response, { Booking page loaded: (r) r.status 200, Has booking form: (r) r.body.includes(data-testidday) || r.body.includes(booking), Response time acceptable: (r) r.timings.duration 5000, }); randomSleep(); return response; }); }逐行解读其设计URL 构造${BASE_URL}/${username}/${eventSlug}对应 Cal.diy 的公开预订页路由如/pro/30min并拼接randomQueryParam()防止缓存。请求参数timeout: 30s给出宽松的请求超时tags: { name: Booking Page }将指标聚合到统一的标签名下便于跨档位对比。三重断言status 200验证页面可访问data-testidday验证预订表单日期选择器确实渲染data-testidday这个测试锚点可以在 DatePicker.tsx 中找到对应实现timings.duration 5000给出单请求的兜底延迟红线。节奏控制请求后调用randomSleep()模拟真实用户浏览页面的停顿避免 VU 变成无停顿的压测机器人。分组统计group(View Booking Page, ...)使 k6 报告按此分组展示指标语义清晰。四种压测档位options 逐档剖析四份booking.js都复用viewBookingPage(pro, 30min)作为主场景即压测 Pro 用户30min事件类型的预订页差异完全体现在options中。smoke固定 VU 固定时长smoke/booking.js 采用最简单直接的配置export const options { vus: 10, duration: 2m, thresholds: { http_req_failed: THRESHOLDS.HTTP_ERRORS, http_req_duration: THRESHOLDS.RESPONSE_TIME.SMOKE.p95, }, };10 个虚拟用户恒定运行 2 分钟配合最严格的 p95 500ms 阈值用作每次改动后的快速回归验证。load阶梯式爬坡到 2,000 VUload/booking.js 使用stages定义五段负载曲线阶段时长VU 目标说明12m500爬坡到 500 VU23m1000继续爬坡到 1,000 VU35m2000爬坡到 2,000 VU410m2000维持 2,000 VU 运行 10 分钟53m0缓慢归零主循环sleep(0.1)保持较高请求密度总测试约 23 分钟用于评估正常运营高峰每分钟数千请求下的稳定性。stress逼近并寻找瓶颈点stress/booking.js 的负载曲线更长、更狠阶段时长VU 目标说明12m1000爬坡到 1,000 VU23m2000爬坡到 2,000 VU35m3000爬坡到 3,000 VU410m3000维持 3,000 VU55m4000继续爬坡到 4,000 VU610m4000维持 4,000 VU数万请求/分钟73m0缓慢归零主循环压缩到sleep(0.05)以每分钟数万请求的强度冲击系统寻找吞吐与延迟的拐点。总时长约 38 分钟建议在专门的压测环境执行。spike模拟突发流量尖峰spike/booking.js 模拟流量突变场景阶段时长VU 目标说明11m500基线负载22m50002 分钟内快速激增到 5,000 VU35m5000维持峰值 5,000 VU42m500回落至基线51m0归零总时长约 11 分钟。这类场景适合验证营销活动上线、热点事件等瞬时流量洪峰下系统的弹性与自动扩容表现阈值也是最宽松的p95 3000ms。环境变量参考变量作用默认值BASE_URL被测应用的基础 URLhttp://localhost:3000Docker 脚本模式为http://host.docker.internal:3000TEST_USER_FREE免费版测试账号用户名freeTEST_PASSWORD_FREE免费版测试账号密码freeTEST_USER_PROPro 版测试账号用户名proTEST_PASSWORD_PROPro 版测试账号密码proTOKEN透传给 k6 的令牌脚本模式无K6_IMAGEDocker 模式使用的 k6 镜像脚本模式grafana/k6MOUNT_LOCALDocker 模式挂载的本地测试目录脚本模式脚本位置推算出的默认目录新增测试的最佳实践README 给出了新增用例的标准流程结合源码可以进一步细化创建测试文件在smoke/、load/、stress/或spike/目录下新建 JS 文件如packages/testing/performance/load/booking-create.js。导入共享能力从 utils/helpers.js 导入既有场景封装或参考其模式用group/check编写新场景从 utils/config.js 导入BASE_URL、THRESHOLDS、randomSleep、getRandomUser等能力保证新用例与既有档位共享相同的阈值与账号管理逻辑。定义 options声明 VUs /stages、运行时长与thresholds——务必从THRESHOLDS中按档位选取对应的 p95/p99 阈值而非硬编码数值以便全局统一调整。实现主函数在default函数中编排场景调用并用sleep/randomSleep控制请求节奏。验证运行先用小 VU 数冒烟验证脚本本身无错误再按档位完整执行最后根据结果决定是否纳入 CI 回归。结语把压测沉淀为常态化质量手段Cal.diy 的这套性能测试套件在工程实践上有几个值得借鉴的设计场景与参数分离helpers.js只描述用户旅程options只描述负载与阈值、按档位梯度放宽阈值从 smoke 的 500ms 到 spike 的 3000ms量化了不同负载下可接受的体验水位、以及生产域防护从根上杜绝误压。将 smoke 档位接入每次 CI 回归、将 load/stress/spike 按发布节奏定期执行就能持续量化预订流程的容量水位在流量洪峰到来之前提前发现瓶颈。延伸阅读测试目录的官方说明见 packages/testing/performance/README.md共享配置与场景封装见 config.js 与 helpers.jsDocker 运行脚本见 run-k6-local.sh预订表单的测试锚点实现见 DatePicker.tsx。【免费下载链接】cal.diyScheduling infrastructure for absolutely everyone.项目地址: https://gitcode.com/GitHub_Trending/ca/cal.diy创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考