Skip to content

Replace five small dependencies with inline equivalents - #381

Merged
lizadaly merged 1 commit into
mainfrom
vendor-small-deps
Jul 27, 2026
Merged

Replace five small dependencies with inline equivalents#381
lizadaly merged 1 commit into
mainfrom
vendor-small-deps

Conversation

@lizadaly

Copy link
Copy Markdown
Owner

Removes lodash, uuid, yargs, @types/yargs, and es6-template-strings. Each was pulled in for one or two trivial call sites.

  • lodashisEqual in BulletedList, capitalize in the Putney Mountain story. The CJS import meant the whole library was bundled; Next's default optimizePackageImports list covers lodash-es, not lodash.
  • uuid — a single call generating an id for a log entry. Nothing in core/, stories/, or pages/ ever reads the log slice back, so the value was write-only. Now crypto.randomUUID().
  • yargs / es6-template-stringsscripts/create-story.ts used them to read one positional arg and interpolate a single ${story} variable. Also drops a ^17.0.0-candidate.0 prerelease pin and a @types/yargs stuck a major version behind the runtime package.

Kept minimatch (documented in the manual as the matching syntax for <Response> options, so it's a public contract) and js-yaml.

Bundle impact

Measured with an A/B production build off the same tree:

Before After
First Load JS (shared) 103 kB 103 kB
/[story]/[[...chapter]] First Load 117 kB 117 kB
Total emitted JS 877,776 B 858,990 B
Total, gzipped 280,119 B 272,721 B

First Load is unchanged — both lodash call sites sit behind per-story dynamic imports, so it only ever landed in a deferred chunk.

Behavior change

BulletedList previously mapped over group and returned ' (selected)' for each match, which would render the string more than once if a group contained duplicate entries. It now checks membership once, and the loop-invariant array comparison is hoisted out of the inner map.

Verification

npm run test (7 passed), eslint, and tsc --noEmit all clean. npm run new verified to generate all four templates with correct interpolation, plus the missing-argument error path.

https://claude.ai/code/session_01KZk5VDAZmVzJhMMJipKKHD

Each of these was pulled in for one or two trivial call sites:

- lodash: isEqual in BulletedList and capitalize in the Putney Mountain
  story. The CJS import meant the full library was bundled, since Next's
  default optimizePackageImports covers lodash-es, not lodash.
- uuid: one call generating an id for a log entry that nothing reads.
  Replaced with crypto.randomUUID().
- yargs and es6-template-strings: create-story.ts used them to read one
  positional arg and interpolate a single ${story} variable. Also drops a
  prerelease yargs pin and a @types/yargs that was a major version behind.

Bundle impact is modest: total emitted JS drops 18.8 KB (7.2 KB gzipped).
First Load JS is unchanged, as both call sites sit behind per-story
dynamic imports.

BulletedList previously mapped over the group to emit ' (selected)' per
match, which would repeat for duplicate entries; it now checks membership
once and hoists the loop-invariant array comparison.

Claude-Session: https://claude.ai/code/session_01KZk5VDAZmVzJhMMJipKKHD
@vercel

vercel Bot commented Jul 27, 2026

Copy link
Copy Markdown

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated (UTC)
windrift Ready Ready Preview, Comment Jul 27, 2026 8:31pm

@lizadaly
lizadaly merged commit 018b0f0 into main Jul 27, 2026
4 checks passed
@lizadaly
lizadaly deleted the vendor-small-deps branch July 27, 2026 20:40
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant