Postgres has to guess how to run a join query before it runs it, and the number of ways grows fast: the write-up counts 4,608 possible plans for a three-table query and roughly 8.9 quadrillion for a nine-table one. Picking well is famously hard — the standard paper asking “How good are query optimizers, really?” was written in 2015 and updated a decade later with the same answer.

Rohan Bansal’s observation is that checking a plan is much easier than finding one. You run it and time it. That asymmetry turns query planning into something a language model can be trained on with a single, unambiguous score: faster is better. He then trained a small open-weights model to emit explicit hints that override Postgres’s own choices, and measured the result.

How the experiment works

  • Training data was the Cardinality Estimation Benchmark — about 13,600 generated queries on the standard IMDb dataset. Bansal checked its join-graph topologies against the 113 Join Order Benchmark evaluation queries and reports no overlap, so no filtering was required. Both benchmarks use the same database; this is not a test of transfer to an unseen database.
  • The model went through supervised fine-tuning first, including learning from roughly 500 trajectories of a frontier agent at the same task, then agentic reinforcement learning: initially four rollouts per query, increased to eight for the successful training runs. Candidate plans were executed against Postgres, with execution time used to compute the reward that updated the weights.
  • Timing noise was the main engineering problem. A candidate identical to the default plan, measured three times, could show a phantom 14–26% speedup about 20% of the time — so he used a custom scoring variant that treats anything within 5% of the default as zero and shrinks real gains, plus repeated interleaved measurements and clipping to keep one extreme plan from dominating.
  • Compute was split across two machines: a rented 2x H100 node running the model and training, and four Postgres containers on his own desktop, joined over Tailscale. After finding that 92% of a rollout’s time was model inference, he switched to leasing a Postgres worker only during measurement, which allowed 20 concurrent rollouts instead of 4.

Results

  • The supervised-fine-tuned checkpoint entering reinforcement learning produced valid candidates for 71 of 113 queries, with a reported 1.16x geometric-mean speedup. That was not the untrained baseline, which produced valid candidates for only 14 queries.
  • After 1,200 reinforcement-learning updates: 101 of 113 valid plans, 1.41x geometric-mean speedup, 38 wins against 2 regressions.
  • Taking the best of up to 15 candidates per query pushed it to a 1.81x geometric-mean speedup with 68 wins and no regressions, and a 44.7% reduction in total query latency.
  • What the model learned is legible: mostly rewriting join order, forcing parallel execution, and fixing a single scan. It developed preferences — nested loops over hash joins, index scans over bitmap and sequential — and liked switching off sorts and setting random_page_cost to 1.1.

Why the small model is the point

The headline number is the least interesting part. The argument is about the recipe: a company with its own data, a niche domain, and a measurable objective can build a small RL environment, spend a modest sum, and get a 4B model that beats a general-purpose planner at one specific task. The total bill here was $1,200 — about $800 for 95 hours of the rented GPU node, $400 in API fees for the frontier demonstration trajectories, plus electricity.

He is careful not to overclaim in the other direction. The distillation step is itself evidence that frontier models are not going anywhere, and the write-up is framed as a proof of a pattern rather than a product.

What the thread adds

The discussion on Hacker News sharpens the distinction between finding reusable hints offline and replacing a live planner.

  • perrygeo states the missing cost: “they must improve the combined time - planning + query - based on live database statistics.” The source explicitly targets repeated analytic queries, not one-off planning: upfront search and measurement would need to be amortized over later executions. The 1.81x result is faster execution of selected plans, not a measured end-to-end planning-and-execution speedup.
  • zacmps questions the comparison baseline: “If random_page_cost wasn’t set correctly for the default cases postgres’s query planner can generate terrible plans”. sgarland adds: “Unless they’ve been elided, there were no indices other than the PK on any table, and no additional statistics.” These are objections to investigate, not demonstrated explanations of the gains. The write-up reports the model’s preference for random_page_cost=1.1; it does not establish how much advantage remains against a separately tuned baseline.
  • Sesse__ corrects the statistical premise in the reply to dvt: “Postgres keeps histograms (including N most common values) for all columns; it does not blindly assume uniform distributions.” PostgreSQL’s documentation confirms that the planner uses most-common values and histograms. Merely proposing to use actual distributions is not a new capability; estimating the intermediate results of joins remains the harder problem described in Bansal’s source.
  • refibrillator warns about transfer: “Many of us appreciate how database workloads can drift over time and with scale.” The source’s IMDb slice is 8.5 GB on disk and queries are warmed. It also describes raising shared_buffers from 128 MB to 2 GB before locking in the configuration, so the initial low-buffer calibration should not be mistaken for the final setup.
  • fsmv asks: “But how will you know that the query plan actually does what your query asked for?” topaz0 clarifies: “The SQL doesn’t change. It’s still up to postgres to guarantee that the results match the query.” polyphilz, the author, reports: “pg_hint_plan has a debug log so you can verify Postgres actually used the hint or not!” Checking hint acceptance is useful, but is not a guarantee of future performance.
  • whazor suggests a deployment boundary: “you can commit the hints to git and run tests for verification. The model would be used during coding.” That is a proposal for a reviewable artifact, not evidence of a production deployment. williamdclt supplies the constraint: “The same query with different params can (and should) result in different query plans.” Reusing hints needs parameter-sensitive tests and revalidation as the data changes.

The question the write-up does not answer

How much net benefit remains after paying for search, comparing against a tuned planner, and maintaining the hints as parameters and data distributions change? The source supports an offline optimization experiment on one database, with the best measured candidate selected from up to 15 per query. It does not establish a general replacement for Postgres planning. An earlier version of this summary also attributed a train/test objection to jwpapi that is not supported by the complete current snapshot; that attribution has been removed.

HN handles are pseudonymous and HN publishes no per-comment scores. API order is a ranking proxy, not a measure of agreement or expertise. These selections are ordered for usefulness and are a slice of the discussion, not consensus.