A truck fleet's location and diagnostics, streamed in and queried like a fleet dashboard.
We use TSBS's data generator, unchanged, and its 12 query types, ported to SQL every system runs. We don't use TSBS's loaders or query runners: timebench loads the data and times the queries, so the numbers don't compare with published TSBS results.
After each system's maintenance, first run of each query in a fresh process. Systems maintain at different times: Timelake while it ingests, most others in a separate step after it, some not at all; the panel below says which, and how long the step after ingest took.
TunedRun of 2026-10-19
When each system maintains its tables, and how long its step after the last commit took.
The geometric mean over the 12 queries. First run of every reader; lower is better.
First-run time in each of the 4 runs on this storage; dashed: a system read by another engine.
Right after the last commit, before any maintenance: the state readers see while data streams in.
TunedRun of 2026-10-19
The geometric mean over the 12 queries. First run of every reader; lower is better.
First-run time in each of the 4 runs on this storage; dashed: a system read by another engine.
After each system's maintenance, first run of each query in a fresh process. Systems maintain at different times: Timelake while it ingests, most others in a separate step after it, some not at all; the panel below says which, and how long the step after ingest took.
TunedRun of 2026-10-19
When each system maintains its tables, and how long its step after the last commit took.
The geometric mean over the 5 queries. First run of every reader; lower is better.
First-run time in each of the 4 runs on this storage; dashed: a system read by another engine.
Right after the last commit, before any maintenance: the state readers see while data streams in.
TunedRun of 2026-10-19
The geometric mean over the 5 queries. First run of every reader; lower is better.
First-run time in each of the 4 runs on this storage; dashed: a system read by another engine.
How each system took the data in and kept it in shape: load rate, commit times, maintenance, and what it stored.
TunedRun of 2026-10-19
median time per commit while streaming; lower is better
Requests each system makes for one query, right after ingest, and the time it takes; each dot is a request.
Committing is the time spent in all commits together. Storage is all files after maintenance, counting replaced files still waiting for cleanup.
| System | Committing | Commit p50 | Commit p95 | Maintenance | Files | Storage |
|---|---|---|---|---|---|---|
| Timelake | 274 s | 85 ms | 864 ms | 3.5 s | 223 | 369 MB |
| Iceberg (PyIceberg) | 28 min | 943 ms | 1180 ms | 102 s | 1,735 | 1.1 GB |
| Lance | 396 s | 212 ms | 352 ms | 18.9 s | 23 | 452 MB |
| Parquet files | 300 s | 171 ms | 207 ms | 138 s | 7 | 257 MB |
Scroll the table sideways for every column.
Fresh readers during ingest: whether they saw every finished commit, and how fast dashboard queries ran under writes.
TunedRun of 2026-10-19
Every 15 s during ingest, a fresh reader ran the dashboard queries and checked the newest row it could see. Behind: probes that missed a commit that had already finished.
| System | Probes behind | Most behind | Dashboard query, median |
|---|---|---|---|
| Timelake | 0 of 52 | — | 164 ms |
| Iceberg (PyIceberg) | 0 of 27 | — | 1.27 s |
| Lance | 0 of 34 | — | 1.13 s |
| Parquet files | 0 of 24 | — | 2.17 s |
Scroll the table sideways for every column.
Several clients at once after maintenance, each with its own reader, running the dashboard queries in turn.
TunedRun of 2026-10-19
After maintenance, 1, 4, 16 clients at once, each with its own reader open, running the dashboard queries in turn for 30 s. Queries per second over all clients, and the 95th percentile latency.
| System | 1 client | 4 clients | 16 clients |
|---|---|---|---|
| Timelake | 121.4 q/sp95 15 ms | 347.6 q/sp95 23 ms | 423.4 q/sp95 93 ms |
| Iceberg (PyIceberg) | 16.1 q/sp95 106 ms | 36.9 q/sp95 205 ms | 40.7 q/sp95 854 ms |
| Lance | 3.8 q/sp95 398 ms | 7.3 q/sp95 916 ms | 8.8 q/sp95 3.02 s |
| Parquet files | 31.0 q/sp95 39 ms | 128.1 q/sp95 39 ms | 267.6 q/sp95 83 ms |
Scroll the table sideways for every column.
Requests and storage at the store's list prices; machines are not included.
AWS S3TunedRun of 2026-10-19
Ingest is scaled to a month of data arriving at this rate.
| System | Ingest, per month | Storage, per month | Per query |
|---|---|---|---|
| Timelake | $0.80 | $0.0079 | $0.000017 |
| Iceberg (PyIceberg) | $2.30 | $0.024 | $0.000011 |
| Lance | $2.77 | $0.0097 | $0.000047 |
| Parquet files | $1.10 | $0.0055 | $0.000017 |
Scroll the table sideways for every column.
Left out of the rankings above; each query's list says which readers it lost.
Tiger CloudTunedRun of 2026-10-12
Each system is written, maintained, and read the way its own docs suggest, on the same data. An entry in a ranking is a system, or a system and the reader that queried it, such as Lance + DuckDB.
Every system runs in two tunings. Tuned: each system as its docs recommend, precomputation included. Default: each system as installed. Results are tuned unless a section's switch says otherwise.
Timelake's own writer: Iceberg tables of sorted Parquet, compacted as it appends.
Plain Iceberg tables written by PyIceberg appends: what a Firehose stream into S3 Tables writes.
Lance datasets, appended commit by commit.
Parquet files without a table format: a new file per commit, as an S3 sink writes them.
TimescaleDB, a PostgreSQL database for time series, on its server's own disk.
Each system's own reader after maintenance: the geometric mean of first runs over the queries it completed in each run. The weekly run adds a point each week.
4 runs
5 runs
1 run
Hover or tap ⓘ for the machine, the commit and every version.