The agent adds date-fns because “we needed formatDistance. It’s a small helper.” The PR description says the change is three lines. The client bundle disagrees: you just bought a tree-shaking argument and a few extra kilobytes you never looked at.
I’ve started treating dependency adds without a cost artifact as incomplete, not obviously fine. “Harmless” is a claim. The analyzer JSON is the evidence.
What usually goes wrong
Trust the import style — import { formatDistance } from "date-fns" is supposed to tree-shake. Sometimes it does. Sometimes a default import, a plugin gap, or a CJS interop path pulls more than the function.
Trust the README — “tree-shakable” and “2 kB” may describe the ideal ESM entry, not what your bundler emitted for this app.
Compare to the wrong baseline — a helper can be small in isolation and still be the first time a large locale table or polyfill lands in the main graph.
Skip the graph — a package you already ship may already expose the same utility. The agent doesn’t know unless you show it.
Give the agent the numbers, not a feeling
After (or before) the PR, generate stats you already use in CI or locally — webpack-bundle-analyzer, Vite’s rollup-plugin-visualizer, Next’s @next/bundle-analyzer, or source-map-explorer. Then paste a JSON or text excerpt, not a screenshot of a treemap:
- The new package’s parsed / gzip size in the route you care about
- The parent chunk name
- Whether an existing chunk already contained a date/utils library
- The before/after of the same route if you can run the analyzer twice
A tight prompt looks like this:
Here’s the analyzer JSON for the checkout client chunk, before
and after your change. If the new import adds more than 3 kB
gzip, or duplicates an existing date library, remove it and
use the in-repo helper or a 10-line local function instead.
Propose an alternative and quote the sizes you used.
Paste the slice, not a 4 MB stats file, unless the agent can take a file. The route-level records matter more than the whole-app dump.
A practical size policy
Agree on a number so you’re not debating taste mid-review:
- New production dependency: show analyzer output in the PR
- Default budget example: flag anything over ~3–5 kB gzip on a critical path, or any new vendor chunk
- Prefer an existing in-repo utility or a 15-line local function when that’s honestly enough
- Date, UUID, markdown, and icon libraries are frequent recidivists — check them even when the import “looks tiny”
Budgets should match your app. A marketing landing page and a design-system docs site won’t share the same number. Write the number down anyway.
Review checklist
- Is there a new
dependency/importfrom a package that wasn’t used on this route? - Did the PR include analyzer output or a CI bundle-size check?
- If not, run the analyzer once before you argue in comments
- If the cost is real, ask the agent to replace the import — with the JSON still in context — rather than debating the README
Reject / send back
Reject
- “It’s a small helper” with no size artifact
- A new general-purpose library for one function, when a local helper would do
- A second date/HTTP/icon library next to one you already ship
- Screenshots of a treemap with no numbers you can search later
Accept
- The JSON (or CI size report) in the PR, with the new cost named
- A local helper or an existing package, when the analyzer shows that’s cheaper
- A dependency that’s actually justified, with the budget called out
Tiny habit
Before you accept a “harmless” add, paste the analyzer JSON into the agent and ask it to account for the bytes. The model can argue about tree-shaking all day. The chunk sizes are shorter.
Top comments (0)