Skip to content

cmd: add per-runner concurrency benchmark harness and baseline#2573

Draft
bendrucker wants to merge 1 commit into
masterfrom
concurrency-bench-harness
Draft

cmd: add per-runner concurrency benchmark harness and baseline#2573
bendrucker wants to merge 1 commit into
masterfrom
concurrency-bench-harness

Conversation

@bendrucker

@bendrucker bendrucker commented Jun 21, 2026

Copy link
Copy Markdown
Member

First PR in a benchmark-driven pass at tflint's concurrency. The repo has no
benchmarks, and the changes that follow (bounding the per-runner check fan-out, cutting
redundant per-runner work) only make sense measured against a baseline, so this
establishes one. No behavior change.

It extracts the inline per-runner fan-out in inspectModule into checkRunners, the
seam the benchmarks measure and that a later PR will bound. Three benchmarks cover the
path: BenchmarkCheckRunners runs the fan-out in isolation with a synthetic check,
BenchmarkInspectFanout runs it end-to-end over a generated N-module fixture with each
check hitting the real evaluator through a plugin.GRPCServer plus a simulated remote
delay, and BenchmarkBuildRunners isolates runner construction. Sizes sweep
1/10/100/1000.

The path is I/O-bound, so wall-clock is noisy and the signals that matter are the custom
metrics: peak-concurrency, check-calls/op, and runners. make bench runs the
suite; bench.yml posts a benchstat table to the job summary, non-blocking and
HEAD-only until the base branch also carries the benchmarks.

Two things the baseline already shows. The fan-out is unbounded: peak concurrency tracks
runner count, ~900 in flight at 1000 module calls on 10 cores. And runner construction
is serial and superlinear, 7s and ~14 GiB allocated at 1000 modules, which may matter
more than the fan-out itself.

One correction to the plan that motivated this: the shared-root evaluation race it set
out to fix (#2094) doesn't exist on master. Evaluator.scope() allocates a fresh scope
per call, so the CallStack/ResolvedLocalValues caches are never shared across
goroutines, and integrationtest/race/eval_locals_on_root_ctx passes under -race. If
#2094 still reproduces, it's a logic bug in CallStack ordering.

Extract the per-runner check fan-out into checkRunners and add a benchmark suite covering the fan-out in isolation, serial runner construction, and the end-to-end fan-out over a generated fixture. The benchmarks report deterministic custom metrics (peak-concurrency, check-calls/op, runners) since the path is I/O-bound. Adds a make bench target and a non-blocking benchstat CI workflow that renders a HEAD-vs-base table into the job summary.

No behavior change. This establishes the master baseline that the rest of the concurrency re-architecture stack is measured against.

Claude-Session: https://claude.ai/code/session_01SFtKL5iaFWPVDqdcyvPiCJ
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Development

Successfully merging this pull request may close these issues.

1 participant