Commit 683f2ee
Closes #1490.
## Background
Importing only `oz.file()` from `@orpc/zod` was pulling ~21 kB of
`@orpc/server` runtime into client bundles via the chain:
```
@orpc/zod → @orpc/openapi → @orpc/server
```
Because `@orpc/zod` re-exports `JSONSchemaFormat` etc. from
`@orpc/openapi`, and `@orpc/openapi/dist/index.mjs` has top-level
`import { ORPCError, createRouterClient } from '@orpc/server'`. Those
top-level cross-package imports are preserved by the consumer's bundler
unless the package is annotated as side-effect free, because the bundler
cannot otherwise prove the import has no observable effect.
## Fix
Add `"sideEffects": false` to the all oRPC's packages
I audited the source for global mutations / prototype patches /
side-effecting class registrations at import time and found none — the
published modules are pure, so the annotation is safe.
## Reproducer
Stand-alone Vite app that mirrors the issue body:
```ts
// client.ts
import { oc } from '@orpc/contract'
import { z } from 'zod/v3'
import { oz } from '@orpc/zod'
export const myRouter = oc.router({
downloadFile: oc
.route({ method: 'GET', path: '/download/{id}' })
.input(z.object({ id: z.string() }))
.output(oz.file()),
})
```
Bundled with `vite build --minify esbuild --target es2022` and
`external: ['zod', 'zod/v3']`:
| Variant | Bundle | Gzipped | `@orpc/server` symbols leaked |
|---|---|---|---|
| Before this PR | **37.9 kB** | 9.54 kB | `ORPCError`, `Procedure`,
`createRouterClient`, `isProcedure`, `resolveContractProcedures` |
| After this PR | **14.8 kB** | 4.76 kB | none from `@orpc/server` (the
remaining `ORPCError` is from `@orpc/contract`, which is legitimately
needed because `oc.router()` returns objects that use it) |
**Net savings: 23.1 kB minified (61% reduction) / 4.78 kB gzipped
(50%).**
## Why this rather than the subpath split suggested in #1490
The reporter (correctly) suggested splitting `ZodToJsonSchemaConverter`
into a separate `@orpc/zod/json-schema` subpath and removing it from the
main entry. That would also fix the bug, but it is a **breaking change**
for everyone currently importing the converter from `@orpc/zod` (incl.
all in-repo playgrounds that use `@orpc/zod/zod4`'s sister export,
README example, etc.) and the subpath split is bundler-independent only
insofar as users don't accidentally re-export the heavy entry
transitively.
`sideEffects: false` is **non-breaking**, lands in 6 lines, and — as the
numbers show — actually achieves the bundle reduction the reporter
expected. If the cross-package tree-shaking turns out insufficient for
some consumer's bundler, the subpath split is still available as a
follow-up.
The reporter's original claim that `sideEffects: false` alone wouldn't
fix this assumed it was set on `@orpc/zod` only; the chain only
tree-shakes when **every** package along the cross-package import path
is marked, which is what this PR does.
## Local gates
- `pnpm --filter='./packages/*' run -r build` ✓ all packages build, dist
outputs unchanged in shape (sideEffects flag does not alter the
rolled-up bundle, only the `package.json` of the published artifact)
- `pnpm test` ✓ 4720 pass / 48 skipped / 5 todo across 280 test files
(untouched by this change)
- `pnpm run type:check` ✓ clean across all packages
- `pnpm lint` ✓ clean (auto-formatter sorted the new key after
`keywords` per `jsonc/sort-keys`)
I was happy to find this fits in 6 lines — happy to fold in the subpath
split as a follow-up if any reviewer measures their bundler still needs
it.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
<!-- This is an auto-generated comment: release notes by coderabbit.ai
-->
## Summary by CodeRabbit
* **Chores**
* Updated package metadata across many packages to mark them as
side-effect free for improved bundling behavior.
* **New Features**
* Exposed a package entry point for one package, updating its public
exports.
<!-- end of auto-generated comment: release notes by coderabbit.ai -->
---------
Co-authored-by: voidborne-d <258577966+voidborne-d@users.noreply.github.com>
Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Co-authored-by: Dinh Le <dinwwwh@gmail.com>
1 parent ba3c437 commit 683f2ee
35 files changed
Lines changed: 35 additions & 0 deletions
File tree
- packages
- ai-sdk
- arktype
- client
- contract
- durable-iterator
- hey-api
- interop
- json-schema
- nest
- openapi-client
- openapi
- otel
- pino
- publisher-durable-object
- publisher
- ratelimit
- react-query
- react-swr
- react
- server
- solid-query
- standard-server-aws-lambda
- standard-server-fastify
- standard-server-fetch
- standard-server-node
- standard-server-peer
- standard-server
- svelte-query
- tanstack-query
- trpc
- valibot
- vue-colada
- vue-query
- zod
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
13 | 13 | | |
14 | 14 | | |
15 | 15 | | |
| 16 | + | |
16 | 17 | | |
17 | 18 | | |
18 | 19 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
12 | 12 | | |
13 | 13 | | |
14 | 14 | | |
| 15 | + | |
15 | 16 | | |
16 | 17 | | |
17 | 18 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
12 | 12 | | |
13 | 13 | | |
14 | 14 | | |
| 15 | + | |
15 | 16 | | |
16 | 17 | | |
17 | 18 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
12 | 12 | | |
13 | 13 | | |
14 | 14 | | |
| 15 | + | |
15 | 16 | | |
16 | 17 | | |
17 | 18 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
12 | 12 | | |
13 | 13 | | |
14 | 14 | | |
| 15 | + | |
15 | 16 | | |
16 | 17 | | |
17 | 18 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
13 | 13 | | |
14 | 14 | | |
15 | 15 | | |
| 16 | + | |
16 | 17 | | |
17 | 18 | | |
18 | 19 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
12 | 12 | | |
13 | 13 | | |
14 | 14 | | |
| 15 | + | |
15 | 16 | | |
16 | 17 | | |
17 | 18 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
12 | 12 | | |
13 | 13 | | |
14 | 14 | | |
| 15 | + | |
15 | 16 | | |
16 | 17 | | |
17 | 18 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
12 | 12 | | |
13 | 13 | | |
14 | 14 | | |
| 15 | + | |
15 | 16 | | |
16 | 17 | | |
17 | 18 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
12 | 12 | | |
13 | 13 | | |
14 | 14 | | |
| 15 | + | |
15 | 16 | | |
16 | 17 | | |
17 | 18 | | |
| |||
0 commit comments