@timber-js/app 0.1.10 → 0.1.12

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (70) hide show
  1. package/dist/_chunks/request-context-BzES06i1.js.map +1 -1
  2. package/dist/_chunks/ssr-data-BgSwMbN9.js +38 -0
  3. package/dist/_chunks/ssr-data-BgSwMbN9.js.map +1 -0
  4. package/dist/_chunks/{use-cookie-HcvNlW4L.js → use-cookie-D2cZu0jK.js} +3 -37
  5. package/dist/_chunks/use-cookie-D2cZu0jK.js.map +1 -0
  6. package/dist/_chunks/use-query-states-wEXY2JQB.js +109 -0
  7. package/dist/_chunks/use-query-states-wEXY2JQB.js.map +1 -0
  8. package/dist/client/error-boundary.d.ts.map +1 -1
  9. package/dist/client/error-boundary.js +8 -0
  10. package/dist/client/error-boundary.js.map +1 -1
  11. package/dist/client/index.js +3 -84
  12. package/dist/client/index.js.map +1 -1
  13. package/dist/client/ssr-data.d.ts +9 -0
  14. package/dist/client/ssr-data.d.ts.map +1 -1
  15. package/dist/client/use-query-states.d.ts.map +1 -1
  16. package/dist/cookies/index.js +1 -1
  17. package/dist/index.d.ts.map +1 -1
  18. package/dist/index.js +10 -12
  19. package/dist/index.js.map +1 -1
  20. package/dist/plugins/entries.d.ts.map +1 -1
  21. package/dist/plugins/routing.d.ts.map +1 -1
  22. package/dist/plugins/server-bundle.d.ts.map +1 -1
  23. package/dist/plugins/shims.d.ts.map +1 -1
  24. package/dist/routing/status-file-lint.d.ts.map +1 -1
  25. package/dist/search-params/create.d.ts.map +1 -1
  26. package/dist/search-params/index.js +13 -4
  27. package/dist/search-params/index.js.map +1 -1
  28. package/dist/server/fallback-error.d.ts +28 -0
  29. package/dist/server/fallback-error.d.ts.map +1 -0
  30. package/dist/server/html-injectors.d.ts.map +1 -1
  31. package/dist/server/index.js +13 -10
  32. package/dist/server/index.js.map +1 -1
  33. package/dist/server/pipeline.d.ts +12 -0
  34. package/dist/server/pipeline.d.ts.map +1 -1
  35. package/dist/server/request-context.d.ts.map +1 -1
  36. package/dist/server/route-matcher.d.ts.map +1 -1
  37. package/dist/server/rsc-entry/index.d.ts.map +1 -1
  38. package/dist/server/slot-resolver.d.ts +1 -1
  39. package/dist/server/slot-resolver.d.ts.map +1 -1
  40. package/dist/server/ssr-entry.d.ts +7 -0
  41. package/dist/server/ssr-entry.d.ts.map +1 -1
  42. package/dist/server/tree-builder.d.ts +10 -0
  43. package/dist/server/tree-builder.d.ts.map +1 -1
  44. package/package.json +23 -23
  45. package/src/client/browser-entry.ts +1 -1
  46. package/src/client/error-boundary.tsx +22 -0
  47. package/src/client/ssr-data.ts +7 -0
  48. package/src/client/use-query-states.ts +13 -1
  49. package/src/index.ts +16 -16
  50. package/src/plugins/dev-server.ts +3 -1
  51. package/src/plugins/entries.ts +2 -1
  52. package/src/plugins/routing.ts +5 -4
  53. package/src/plugins/server-bundle.ts +15 -6
  54. package/src/plugins/shims.ts +8 -14
  55. package/src/routing/status-file-lint.ts +1 -3
  56. package/src/search-params/create.ts +15 -8
  57. package/src/server/error-formatter.ts +12 -0
  58. package/src/server/fallback-error.ts +159 -0
  59. package/src/server/html-injectors.ts +9 -4
  60. package/src/server/pipeline.ts +24 -0
  61. package/src/server/request-context.ts +0 -1
  62. package/src/server/route-matcher.ts +1 -4
  63. package/src/server/rsc-entry/index.ts +98 -39
  64. package/src/server/slot-resolver.ts +38 -5
  65. package/src/server/ssr-entry.ts +12 -1
  66. package/src/server/tree-builder.ts +39 -11
  67. package/src/shims/server-only-noop.js +1 -0
  68. package/dist/_chunks/registry-BfPM41ri.js +0 -20
  69. package/dist/_chunks/registry-BfPM41ri.js.map +0 -1
  70. package/dist/_chunks/use-cookie-HcvNlW4L.js.map +0 -1
@@ -70,6 +70,18 @@ export interface PipelineConfig {
70
70
  * Undefined in production — zero overhead.
71
71
  */
72
72
  onPipelineError?: (error: Error, phase: string) => void;
73
+ /**
74
+ * Fallback error renderer — called when a catastrophic error escapes the
75
+ * render phase. Produces an HTML Response instead of a bare empty 500.
76
+ *
77
+ * In dev mode, this renders a styled error page with the error message
78
+ * and stack trace. In production, this attempts to render the app's
79
+ * error.tsx / 5xx.tsx / 500.tsx from the root segment.
80
+ *
81
+ * If this function throws, the pipeline falls back to a bare
82
+ * `new Response(null, { status: 500 })`.
83
+ */
84
+ renderFallbackError?: (error: unknown, req: Request, responseHeaders: Headers) => Response | Promise<Response>;
73
85
  }
74
86
  /**
75
87
  * Create the request handler from a pipeline configuration.
@@ -1 +1 @@
1
- {"version":3,"file":"pipeline.d.ts","sourceRoot":"","sources":["../../src/server/pipeline.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;GAWG;AAGH,OAAO,EAAY,KAAK,WAAW,EAAE,MAAM,YAAY,CAAC;AACxD,OAAO,EAAiB,KAAK,YAAY,EAAE,MAAM,wBAAwB,CAAC;AA6B1E,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,oBAAoB,CAAC;AAItD,sEAAsE;AACtE,MAAM,WAAW,UAAU;IACzB,mDAAmD;IACnD,QAAQ,EAAE,WAAW,EAAE,CAAC;IACxB,oEAAoE;IACpE,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,EAAE,CAAC,CAAC;IAC1C,uDAAuD;IACvD,UAAU,CAAC,EAAE,YAAY,CAAC;CAC3B;AAED,6DAA6D;AAC7D,MAAM,MAAM,YAAY,GAAG,CAAC,QAAQ,EAAE,MAAM,KAAK,UAAU,GAAG,IAAI,CAAC;AAEnE,sEAAsE;AACtE,MAAM,MAAM,oBAAoB,GAAG,CACjC,QAAQ,EAAE,MAAM,KACb,OAAO,oBAAoB,EAAE,kBAAkB,GAAG,IAAI,CAAC;AAE5D,iEAAiE;AACjE,MAAM,WAAW,mBAAmB;IAClC,iEAAiE;IACjE,cAAc,EAAE,MAAM,CAAC;CACxB;AAED,6DAA6D;AAC7D,MAAM,MAAM,aAAa,GAAG,CAC1B,GAAG,EAAE,OAAO,EACZ,KAAK,EAAE,UAAU,EACjB,eAAe,EAAE,OAAO,EACxB,oBAAoB,EAAE,OAAO,EAC7B,YAAY,CAAC,EAAE,mBAAmB,KAC/B,QAAQ,GAAG,OAAO,CAAC,QAAQ,CAAC,CAAC;AAElC,+DAA+D;AAC/D,MAAM,MAAM,iBAAiB,GAAG,CAC9B,KAAK,EAAE,UAAU,EACjB,GAAG,EAAE,OAAO,EACZ,eAAe,EAAE,OAAO,KACrB,IAAI,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;AAI1B,MAAM,WAAW,cAAc;IAC7B,iFAAiF;IACjF,KAAK,CAAC,EAAE,WAAW,CAAC;IACpB,gFAAgF;IAChF,WAAW,CAAC,EAAE,MAAM,OAAO,CAAC;QAAE,OAAO,EAAE,WAAW,CAAA;KAAE,CAAC,CAAC;IACtD,qEAAqE;IACrE,UAAU,EAAE,YAAY,CAAC;IACzB,iGAAiG;IACjG,kBAAkB,CAAC,EAAE,oBAAoB,CAAC;IAC1C,kEAAkE;IAClE,MAAM,EAAE,aAAa,CAAC;IACtB,kEAAkE;IAClE,aAAa,CAAC,EAAE,CAAC,GAAG,EAAE,OAAO,EAAE,eAAe,EAAE,OAAO,KAAK,QAAQ,GAAG,OAAO,CAAC,QAAQ,CAAC,CAAC;IACzF,kFAAkF;IAClF,UAAU,CAAC,EAAE,iBAAiB,CAAC;IAC/B,gFAAgF;IAChF,kBAAkB,CAAC,EAAE,OAAO,CAAC;IAC7B,yGAAyG;IACzG,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB;;;;OAIG;IACH,oBAAoB,CAAC,EAAE,OAAO,2BAA2B,EAAE,mBAAmB,EAAE,CAAC;IACjF;;;;;;OAMG;IACH,eAAe,CAAC,EAAE,CAAC,KAAK,EAAE,KAAK,EAAE,KAAK,EAAE,MAAM,KAAK,IAAI,CAAC;CACzD;AAID;;;;;GAKG;AACH,wBAAgB,cAAc,CAAC,MAAM,EAAE,cAAc,GAAG,CAAC,GAAG,EAAE,OAAO,KAAK,OAAO,CAAC,QAAQ,CAAC,CAmR1F"}
1
+ {"version":3,"file":"pipeline.d.ts","sourceRoot":"","sources":["../../src/server/pipeline.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;GAWG;AAGH,OAAO,EAAY,KAAK,WAAW,EAAE,MAAM,YAAY,CAAC;AACxD,OAAO,EAAiB,KAAK,YAAY,EAAE,MAAM,wBAAwB,CAAC;AA6B1E,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,oBAAoB,CAAC;AAItD,sEAAsE;AACtE,MAAM,WAAW,UAAU;IACzB,mDAAmD;IACnD,QAAQ,EAAE,WAAW,EAAE,CAAC;IACxB,oEAAoE;IACpE,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,EAAE,CAAC,CAAC;IAC1C,uDAAuD;IACvD,UAAU,CAAC,EAAE,YAAY,CAAC;CAC3B;AAED,6DAA6D;AAC7D,MAAM,MAAM,YAAY,GAAG,CAAC,QAAQ,EAAE,MAAM,KAAK,UAAU,GAAG,IAAI,CAAC;AAEnE,sEAAsE;AACtE,MAAM,MAAM,oBAAoB,GAAG,CACjC,QAAQ,EAAE,MAAM,KACb,OAAO,oBAAoB,EAAE,kBAAkB,GAAG,IAAI,CAAC;AAE5D,iEAAiE;AACjE,MAAM,WAAW,mBAAmB;IAClC,iEAAiE;IACjE,cAAc,EAAE,MAAM,CAAC;CACxB;AAED,6DAA6D;AAC7D,MAAM,MAAM,aAAa,GAAG,CAC1B,GAAG,EAAE,OAAO,EACZ,KAAK,EAAE,UAAU,EACjB,eAAe,EAAE,OAAO,EACxB,oBAAoB,EAAE,OAAO,EAC7B,YAAY,CAAC,EAAE,mBAAmB,KAC/B,QAAQ,GAAG,OAAO,CAAC,QAAQ,CAAC,CAAC;AAElC,+DAA+D;AAC/D,MAAM,MAAM,iBAAiB,GAAG,CAC9B,KAAK,EAAE,UAAU,EACjB,GAAG,EAAE,OAAO,EACZ,eAAe,EAAE,OAAO,KACrB,IAAI,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;AAI1B,MAAM,WAAW,cAAc;IAC7B,iFAAiF;IACjF,KAAK,CAAC,EAAE,WAAW,CAAC;IACpB,gFAAgF;IAChF,WAAW,CAAC,EAAE,MAAM,OAAO,CAAC;QAAE,OAAO,EAAE,WAAW,CAAA;KAAE,CAAC,CAAC;IACtD,qEAAqE;IACrE,UAAU,EAAE,YAAY,CAAC;IACzB,iGAAiG;IACjG,kBAAkB,CAAC,EAAE,oBAAoB,CAAC;IAC1C,kEAAkE;IAClE,MAAM,EAAE,aAAa,CAAC;IACtB,kEAAkE;IAClE,aAAa,CAAC,EAAE,CAAC,GAAG,EAAE,OAAO,EAAE,eAAe,EAAE,OAAO,KAAK,QAAQ,GAAG,OAAO,CAAC,QAAQ,CAAC,CAAC;IACzF,kFAAkF;IAClF,UAAU,CAAC,EAAE,iBAAiB,CAAC;IAC/B,gFAAgF;IAChF,kBAAkB,CAAC,EAAE,OAAO,CAAC;IAC7B,yGAAyG;IACzG,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB;;;;OAIG;IACH,oBAAoB,CAAC,EAAE,OAAO,2BAA2B,EAAE,mBAAmB,EAAE,CAAC;IACjF;;;;;;OAMG;IACH,eAAe,CAAC,EAAE,CAAC,KAAK,EAAE,KAAK,EAAE,KAAK,EAAE,MAAM,KAAK,IAAI,CAAC;IACxD;;;;;;;;;;OAUG;IACH,mBAAmB,CAAC,EAAE,CACpB,KAAK,EAAE,OAAO,EACd,GAAG,EAAE,OAAO,EACZ,eAAe,EAAE,OAAO,KACrB,QAAQ,GAAG,OAAO,CAAC,QAAQ,CAAC,CAAC;CACnC;AAID;;;;;GAKG;AACH,wBAAgB,cAAc,CAAC,MAAM,EAAE,cAAc,GAAG,CAAC,GAAG,EAAE,OAAO,KAAK,OAAO,CAAC,QAAQ,CAAC,CA2R1F"}
@@ -1 +1 @@
1
- {"version":3,"file":"request-context.d.ts","sourceRoot":"","sources":["../../src/server/request-context.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"request-context.d.ts","sourceRoot":"","sources":["../../src/server/request-context.ts"],"names":[],"mappings":"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"}
@@ -1 +1 @@
1
- {"version":3,"file":"route-matcher.d.ts","sourceRoot":"","sources":["../../src/server/route-matcher.ts"],"names":[],"mappings":"AAAA;;;;;;;;GAQG;AAEH,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,eAAe,CAAC;AAEhD,OAAO,EAEL,KAAK,iBAAiB,EACvB,MAAM,sBAAsB,CAAC;AAM9B,6DAA6D;AAC7D,UAAU,YAAY;IACpB,IAAI,EAAE,MAAM,OAAO,CAAC,OAAO,CAAC,CAAC;IAC7B,QAAQ,EAAE,MAAM,CAAC;CAClB;AAED,gFAAgF;AAChF,MAAM,WAAW,mBAAmB;IAClC,WAAW,EAAE,MAAM,CAAC;IACpB,WAAW,EACP,QAAQ,GACR,SAAS,GACT,WAAW,GACX,oBAAoB,GACpB,OAAO,GACP,MAAM,GACN,cAAc,CAAC;IACnB,OAAO,EAAE,MAAM,CAAC;IAChB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,8DAA8D;IAC9D,kBAAkB,CAAC,EAAE,KAAK,GAAG,MAAM,GAAG,OAAO,GAAG,UAAU,CAAC;IAC3D,8EAA8E;IAC9E,sBAAsB,CAAC,EAAE,MAAM,CAAC;IAEhC,IAAI,CAAC,EAAE,YAAY,CAAC;IACpB,MAAM,CAAC,EAAE,YAAY,CAAC;IACtB,UAAU,CAAC,EAAE,YAAY,CAAC;IAC1B,MAAM,CAAC,EAAE,YAAY,CAAC;IACtB,KAAK,CAAC,EAAE,YAAY,CAAC;IACrB,KAAK,CAAC,EAAE,YAAY,CAAC;IACrB,OAAO,CAAC,EAAE,YAAY,CAAC;IACvB,MAAM,CAAC,EAAE,YAAY,CAAC;IACtB,YAAY,CAAC,EAAE,YAAY,CAAC;IAC5B,WAAW,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,YAAY,CAAC,CAAC;IAC3C,eAAe,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,YAAY,CAAC,CAAC;IAC/C,iBAAiB,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,YAAY,CAAC,CAAC;IACjD,SAAS,CAAC,EAAE,YAAY,CAAC;IACzB,sFAAsF;IACtF,cAAc,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,YAAY,CAAC,CAAC;IAE9C,QAAQ,EAAE,mBAAmB,EAAE,CAAC;IAChC,KAAK,EAAE,MAAM,CAAC,MAAM,EAAE,mBAAmB,CAAC,CAAC;CAC5C;AAED,6DAA6D;AAC7D,MAAM,WAAW,YAAY;IAC3B,IAAI,EAAE,mBAAmB,CAAC;IAC1B,KAAK,CAAC,EAAE,YAAY,CAAC;CACtB;AAID;;;;;GAKG;AACH,wBAAgB,kBAAkB,CAChC,QAAQ,EAAE,YAAY,GACrB,CAAC,QAAQ,EAAE,MAAM,KAAK,UAAU,GAAG,IAAI,CAEzC;AA4MD,2CAA2C;AAC3C,MAAM,WAAW,kBAAkB;IACjC,4DAA4D;IAC5D,IAAI,EAAE,iBAAiB,CAAC;IACxB,4CAA4C;IAC5C,WAAW,EAAE,MAAM,CAAC;IACpB,0DAA0D;IAC1D,IAAI,EAAE,YAAY,CAAC;IACnB,0DAA0D;IAC1D,OAAO,EAAE,mBAAmB,CAAC;CAC9B;AAED;;;;;;;GAOG;AACH,wBAAgB,0BAA0B,CACxC,QAAQ,EAAE,YAAY,GACrB,CAAC,QAAQ,EAAE,MAAM,KAAK,kBAAkB,GAAG,IAAI,CAMjD"}
1
+ {"version":3,"file":"route-matcher.d.ts","sourceRoot":"","sources":["../../src/server/route-matcher.ts"],"names":[],"mappings":"AAAA;;;;;;;;GAQG;AAEH,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,eAAe,CAAC;AAEhD,OAAO,EAA8B,KAAK,iBAAiB,EAAE,MAAM,sBAAsB,CAAC;AAM1F,6DAA6D;AAC7D,UAAU,YAAY;IACpB,IAAI,EAAE,MAAM,OAAO,CAAC,OAAO,CAAC,CAAC;IAC7B,QAAQ,EAAE,MAAM,CAAC;CAClB;AAED,gFAAgF;AAChF,MAAM,WAAW,mBAAmB;IAClC,WAAW,EAAE,MAAM,CAAC;IACpB,WAAW,EACP,QAAQ,GACR,SAAS,GACT,WAAW,GACX,oBAAoB,GACpB,OAAO,GACP,MAAM,GACN,cAAc,CAAC;IACnB,OAAO,EAAE,MAAM,CAAC;IAChB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,8DAA8D;IAC9D,kBAAkB,CAAC,EAAE,KAAK,GAAG,MAAM,GAAG,OAAO,GAAG,UAAU,CAAC;IAC3D,8EAA8E;IAC9E,sBAAsB,CAAC,EAAE,MAAM,CAAC;IAEhC,IAAI,CAAC,EAAE,YAAY,CAAC;IACpB,MAAM,CAAC,EAAE,YAAY,CAAC;IACtB,UAAU,CAAC,EAAE,YAAY,CAAC;IAC1B,MAAM,CAAC,EAAE,YAAY,CAAC;IACtB,KAAK,CAAC,EAAE,YAAY,CAAC;IACrB,KAAK,CAAC,EAAE,YAAY,CAAC;IACrB,OAAO,CAAC,EAAE,YAAY,CAAC;IACvB,MAAM,CAAC,EAAE,YAAY,CAAC;IACtB,YAAY,CAAC,EAAE,YAAY,CAAC;IAC5B,WAAW,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,YAAY,CAAC,CAAC;IAC3C,eAAe,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,YAAY,CAAC,CAAC;IAC/C,iBAAiB,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,YAAY,CAAC,CAAC;IACjD,SAAS,CAAC,EAAE,YAAY,CAAC;IACzB,sFAAsF;IACtF,cAAc,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,YAAY,CAAC,CAAC;IAE9C,QAAQ,EAAE,mBAAmB,EAAE,CAAC;IAChC,KAAK,EAAE,MAAM,CAAC,MAAM,EAAE,mBAAmB,CAAC,CAAC;CAC5C;AAED,6DAA6D;AAC7D,MAAM,WAAW,YAAY;IAC3B,IAAI,EAAE,mBAAmB,CAAC;IAC1B,KAAK,CAAC,EAAE,YAAY,CAAC;CACtB;AAID;;;;;GAKG;AACH,wBAAgB,kBAAkB,CAChC,QAAQ,EAAE,YAAY,GACrB,CAAC,QAAQ,EAAE,MAAM,KAAK,UAAU,GAAG,IAAI,CAEzC;AA4MD,2CAA2C;AAC3C,MAAM,WAAW,kBAAkB;IACjC,4DAA4D;IAC5D,IAAI,EAAE,iBAAiB,CAAC;IACxB,4CAA4C;IAC5C,WAAW,EAAE,MAAM,CAAC;IACpB,0DAA0D;IAC1D,IAAI,EAAE,YAAY,CAAC;IACnB,0DAA0D;IAC1D,OAAO,EAAE,mBAAmB,CAAC;CAC9B;AAED;;;;;;;GAOG;AACH,wBAAgB,0BAA0B,CACxC,QAAQ,EAAE,YAAY,GACrB,CAAC,QAAQ,EAAE,MAAM,KAAK,kBAAkB,GAAG,IAAI,CAMjD"}
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/server/rsc-entry/index.ts"],"names":[],"mappings":"AA2EA;;;;;GAKG;AACH,wBAAgB,0BAA0B,CAAC,OAAO,EAAE,CAAC,KAAK,EAAE,KAAK,EAAE,KAAK,EAAE,MAAM,KAAK,IAAI,GAAG,IAAI,CAE/F;AA0nBD,OAAO,EAAE,uBAAuB,EAAE,MAAM,gCAAgC,CAAC;8BAtgBpD,OAAO,KAAG,OAAO,CAAC,QAAQ,CAAC;AAwgBhD,wBAAiE"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/server/rsc-entry/index.ts"],"names":[],"mappings":"AA2EA;;;;;GAKG;AACH,wBAAgB,0BAA0B,CAAC,OAAO,EAAE,CAAC,KAAK,EAAE,KAAK,EAAE,KAAK,EAAE,MAAM,KAAK,IAAI,GAAG,IAAI,CAE/F;AAqrBD,OAAO,EAAE,uBAAuB,EAAE,MAAM,gCAAgC,CAAC;8BA/jBpD,OAAO,KAAG,OAAO,CAAC,QAAQ,CAAC;AAikBhD,wBAAiE"}
@@ -15,8 +15,8 @@
15
15
  *
16
16
  * See design/02-rendering-pipeline.md §"Parallel Slots"
17
17
  */
18
+ import type { InterceptionContext, RouteMatch } from './pipeline.js';
18
19
  import type { ManifestSegmentNode } from './route-matcher.js';
19
- import type { RouteMatch, InterceptionContext } from './pipeline.js';
20
20
  type CreateElementFn = (...args: unknown[]) => React.ReactElement;
21
21
  /**
22
22
  * Resolve the element for a parallel slot.
@@ -1 +1 @@
1
- {"version":3,"file":"slot-resolver.d.ts","sourceRoot":"","sources":["../../src/server/slot-resolver.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;GAgBG;AAEH,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,oBAAoB,CAAC;AAC9D,OAAO,KAAK,EAAE,UAAU,EAAE,mBAAmB,EAAE,MAAM,eAAe,CAAC;AAMrE,KAAK,eAAe,GAAG,CAAC,GAAG,IAAI,EAAE,OAAO,EAAE,KAAK,KAAK,CAAC,YAAY,CAAC;AAElE;;;;;;;;;;GAUG;AACH,wBAAsB,kBAAkB,CACtC,QAAQ,EAAE,mBAAmB,EAC7B,KAAK,EAAE,UAAU,EACjB,aAAa,EAAE,OAAO,CAAC,MAAM,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,EAAE,CAAC,CAAC,EACzD,CAAC,EAAE,eAAe,EAClB,YAAY,CAAC,EAAE,mBAAmB,GACjC,OAAO,CAAC,KAAK,CAAC,YAAY,GAAG,IAAI,CAAC,CAiIpC"}
1
+ {"version":3,"file":"slot-resolver.d.ts","sourceRoot":"","sources":["../../src/server/slot-resolver.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;GAgBG;AAMH,OAAO,KAAK,EAAE,mBAAmB,EAAE,UAAU,EAAE,MAAM,eAAe,CAAC;AAErE,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,oBAAoB,CAAC;AAE9D,KAAK,eAAe,GAAG,CAAC,GAAG,IAAI,EAAE,OAAO,EAAE,KAAK,KAAK,CAAC,YAAY,CAAC;AAElE;;;;;;;;;;GAUG;AACH,wBAAsB,kBAAkB,CACtC,QAAQ,EAAE,mBAAmB,EAC7B,KAAK,EAAE,UAAU,EACjB,aAAa,EAAE,OAAO,CAAC,MAAM,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,EAAE,CAAC,CAAC,EACzD,CAAC,EAAE,eAAe,EAClB,YAAY,CAAC,EAAE,mBAAmB,GACjC,OAAO,CAAC,KAAK,CAAC,YAAY,GAAG,IAAI,CAAC,CAiKpC"}
@@ -46,6 +46,13 @@ export interface NavContext {
46
46
  /** Request cookies as name→value pairs. Used by useCookie() during SSR
47
47
  * to return correct cookie values before hydration. */
48
48
  cookies?: Map<string, string>;
49
+ /**
50
+ * Mutable flag: set by TimberErrorBoundary during SSR when it catches
51
+ * a DenySignal (via digest). This tells the RSC entry that the denial
52
+ * was contained by a slot error boundary and should NOT be promoted
53
+ * to a page-level deny. See LOCAL-298.
54
+ */
55
+ _denyHandledByBoundary?: boolean;
49
56
  }
50
57
  /**
51
58
  * Handle SSR: decode an RSC stream and render it to hydration-ready HTML.
@@ -1 +1 @@
1
- {"version":3,"file":"ssr-entry.d.ts","sourceRoot":"","sources":["../../src/server/ssr-entry.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;GAYG;AA6BH;;;;;GAKG;AACH,MAAM,WAAW,UAAU;IACzB,6BAA6B;IAC7B,QAAQ,EAAE,MAAM,CAAC;IACjB,mEAAmE;IACnE,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,EAAE,CAAC,CAAC;IAC1C,iCAAiC;IACjC,YAAY,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;IACrC,qCAAqC;IACrC,UAAU,EAAE,MAAM,CAAC;IACnB,6CAA6C;IAC7C,eAAe,EAAE,OAAO,CAAC;IACzB,0DAA0D;IAC1D,QAAQ,EAAE,MAAM,CAAC;IACjB,8EAA8E;IAC9E,sBAAsB,EAAE,MAAM,CAAC;IAC/B,qEAAqE;IACrE,SAAS,CAAC,EAAE,cAAc,CAAC,UAAU,CAAC,CAAC;IACvC;;;0DAGsD;IACtD,gBAAgB,CAAC,EAAE,MAAM,CAAC;IAC1B;;iFAE6E;IAC7E,MAAM,CAAC,EAAE,WAAW,CAAC;IACrB;4DACwD;IACxD,OAAO,CAAC,EAAE,GAAG,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;CAC/B;AAED;;;;;;;;;;;;;;;;;;;;GAoBG;AACH,wBAAsB,SAAS,CAC7B,SAAS,EAAE,cAAc,CAAC,UAAU,CAAC,EACrC,UAAU,EAAE,UAAU,GACrB,OAAO,CAAC,QAAQ,CAAC,CAwEnB;AAED,eAAe,SAAS,CAAC"}
1
+ {"version":3,"file":"ssr-entry.d.ts","sourceRoot":"","sources":["../../src/server/ssr-entry.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;GAYG;AA6BH;;;;;GAKG;AACH,MAAM,WAAW,UAAU;IACzB,6BAA6B;IAC7B,QAAQ,EAAE,MAAM,CAAC;IACjB,mEAAmE;IACnE,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,EAAE,CAAC,CAAC;IAC1C,iCAAiC;IACjC,YAAY,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;IACrC,qCAAqC;IACrC,UAAU,EAAE,MAAM,CAAC;IACnB,6CAA6C;IAC7C,eAAe,EAAE,OAAO,CAAC;IACzB,0DAA0D;IAC1D,QAAQ,EAAE,MAAM,CAAC;IACjB,8EAA8E;IAC9E,sBAAsB,EAAE,MAAM,CAAC;IAC/B,qEAAqE;IACrE,SAAS,CAAC,EAAE,cAAc,CAAC,UAAU,CAAC,CAAC;IACvC;;;0DAGsD;IACtD,gBAAgB,CAAC,EAAE,MAAM,CAAC;IAC1B;;iFAE6E;IAC7E,MAAM,CAAC,EAAE,WAAW,CAAC;IACrB;4DACwD;IACxD,OAAO,CAAC,EAAE,GAAG,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;IAC9B;;;;;OAKG;IACH,sBAAsB,CAAC,EAAE,OAAO,CAAC;CAClC;AAED;;;;;;;;;;;;;;;;;;;;GAoBG;AACH,wBAAsB,SAAS,CAC7B,SAAS,EAAE,cAAc,CAAC,UAAU,CAAC,EACrC,UAAU,EAAE,UAAU,GACrB,OAAO,CAAC,QAAQ,CAAC,CA4EnB;AAED,eAAe,SAAS,CAAC"}
@@ -40,6 +40,16 @@ export interface TreeBuilderConfig {
40
40
  loadModule: ModuleLoader;
41
41
  /** React.createElement or equivalent. */
42
42
  createElement: CreateElement;
43
+ /**
44
+ * Error boundary component for wrapping segments.
45
+ *
46
+ * This is injected by the caller rather than imported directly to avoid
47
+ * pulling 'use client' code into the server barrel (@timber-js/app/server).
48
+ * In the RSC environment, the RSC plugin transforms this import to a
49
+ * client reference proxy — the caller handles the import so the server
50
+ * barrel stays free of client dependencies.
51
+ */
52
+ errorBoundaryComponent?: unknown;
43
53
  }
44
54
  /**
45
55
  * Framework-injected access gate component.
@@ -1 +1 @@
1
- {"version":3,"file":"tree-builder.d.ts","sourceRoot":"","sources":["../../src/server/tree-builder.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"tree-builder.d.ts","sourceRoot":"","sources":["../../src/server/tree-builder.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,31 +1,35 @@
1
1
  {
2
2
  "name": "@timber-js/app",
3
- "version": "0.1.10",
3
+ "version": "0.1.12",
4
4
  "description": "Vite-native React framework for Cloudflare Workers — correct HTTP semantics, real status codes, pages that work without JavaScript",
5
- "type": "module",
6
- "license": "SEE LICENSE IN LICENSE",
7
- "repository": {
8
- "type": "git",
9
- "url": "git+https://github.com/switz/timber.js.git",
10
- "directory": "packages/timber-app"
11
- },
12
- "homepage": "https://github.com/switz/timber.js",
13
5
  "keywords": [
14
- "react",
15
- "vite",
16
- "rsc",
17
- "react-server-components",
18
6
  "cloudflare-workers",
19
7
  "framework",
8
+ "react",
9
+ "react-server-components",
10
+ "rsc",
20
11
  "ssr",
21
- "streaming"
12
+ "streaming",
13
+ "vite"
22
14
  ],
23
- "engines": {
24
- "node": ">=20.0.0"
15
+ "homepage": "https://github.com/switz/timber.js",
16
+ "license": "SEE LICENSE IN LICENSE",
17
+ "repository": {
18
+ "type": "git",
19
+ "url": "git+https://github.com/switz/timber.js.git",
20
+ "directory": "packages/timber-app"
25
21
  },
26
22
  "bin": {
27
23
  "timber": "./bin/timber.mjs"
28
24
  },
25
+ "files": [
26
+ "dist",
27
+ "src",
28
+ "bin",
29
+ "README.md",
30
+ "LICENSE"
31
+ ],
32
+ "type": "module",
29
33
  "imports": {
30
34
  "#/*": "./src/*"
31
35
  },
@@ -75,13 +79,6 @@
75
79
  "publishConfig": {
76
80
  "access": "public"
77
81
  },
78
- "files": [
79
- "dist",
80
- "src",
81
- "bin",
82
- "README.md",
83
- "LICENSE"
84
- ],
85
82
  "scripts": {
86
83
  "build": "vite build --config vite.lib.config.ts && tsc --emitDeclarationOnly --project tsconfig.json --outDir dist",
87
84
  "typecheck": "tsgo --noEmit",
@@ -121,5 +118,8 @@
121
118
  "zod": {
122
119
  "optional": true
123
120
  }
121
+ },
122
+ "engines": {
123
+ "node": ">=20.0.0"
124
124
  }
125
125
  }
@@ -364,7 +364,7 @@ function bootstrap(runtimeConfig: typeof config): void {
364
364
  // so duplicate URLs in history each have their own scroll position.
365
365
  window.addEventListener('popstate', () => {
366
366
  const state = window.history.state;
367
- const scrollY = (state && typeof state.scrollY === 'number') ? state.scrollY : 0;
367
+ const scrollY = state && typeof state.scrollY === 'number' ? state.scrollY : 0;
368
368
  void router.handlePopState(window.location.pathname + window.location.search, scrollY);
369
369
  });
370
370
 
@@ -19,6 +19,7 @@
19
19
  */
20
20
 
21
21
  import { Component, createElement, type ReactNode } from 'react';
22
+ import { getSsrData } from './ssr-data.js';
22
23
 
23
24
  // ─── Page Unload Detection ───────────────────────────────────────────────────
24
25
  // Track whether the page is being unloaded (user refreshed or navigated away).
@@ -97,6 +98,27 @@ export class TimberErrorBoundary extends Component<
97
98
  if (_isUnloading) {
98
99
  return { hasError: false, error: null };
99
100
  }
101
+
102
+ // Report DenySignal handling to prevent page-level promotion.
103
+ // When a slot's error boundary catches a DenySignal, the RSC onError
104
+ // callback has already tracked it globally. Setting this flag tells
105
+ // the RSC entry not to promote the denial to page-level (which would
106
+ // replace the entire SSR response). See LOCAL-298.
107
+ const digest = (error as { digest?: string }).digest;
108
+ if (typeof digest === 'string') {
109
+ try {
110
+ const parsed = JSON.parse(digest);
111
+ if (parsed?.type === 'deny') {
112
+ const ssrData = getSsrData();
113
+ if (ssrData?._navContext) {
114
+ ssrData._navContext._denyHandledByBoundary = true;
115
+ }
116
+ }
117
+ } catch {
118
+ // Not a JSON digest — ignore
119
+ }
120
+ }
121
+
100
122
  return { hasError: true, error };
101
123
  }
102
124
 
@@ -30,6 +30,13 @@ export interface SsrData {
30
30
  cookies: Map<string, string>;
31
31
  /** The request's route params (e.g. { id: '123' }) */
32
32
  params: Record<string, string | string[]>;
33
+ /**
34
+ * Mutable reference to NavContext for error boundary → RSC communication.
35
+ * When TimberErrorBoundary catches a DenySignal, it sets
36
+ * `_navContext._denyHandledByBoundary = true` to prevent the RSC entry
37
+ * from promoting the denial to page-level. See LOCAL-298.
38
+ */
39
+ _navContext?: { _denyHandledByBoundary?: boolean };
33
40
  }
34
41
 
35
42
  // ─── ALS-Backed Provider ─────────────────────────────────────────
@@ -101,7 +101,19 @@ export function useQueryStates<T extends Record<string, unknown>>(
101
101
  nuqsOptions.urlKeys = resolvedUrlKeys;
102
102
  }
103
103
 
104
- const [values, setValues] = nuqsUseQueryStates(bridged, nuqsOptions);
104
+ let values: Record<string, unknown>;
105
+ let setValues: Function;
106
+ try {
107
+ [values, setValues] = nuqsUseQueryStates(bridged, nuqsOptions);
108
+ } catch (err) {
109
+ if (err instanceof Error && /Invalid hook call|cannot be called|Cannot read properties of null/i.test(err.message)) {
110
+ throw new Error(
111
+ 'useQueryStates is a client component hook and cannot be called outside a React component. ' +
112
+ 'Use definition.parse(searchParams) in server components instead.'
113
+ );
114
+ }
115
+ throw err;
116
+ }
105
117
 
106
118
  // Wrap the nuqs setter to match timber's SetParams<T> signature.
107
119
  // nuqs's setter accepts Partial<Nullable<Values>> | UpdaterFn | null.
package/src/index.ts CHANGED
@@ -190,9 +190,7 @@ export function resolveAppDir(root: string, configAppDir?: string): string {
190
190
  if (configAppDir) {
191
191
  const explicit = join(root, configAppDir);
192
192
  if (!existsSync(explicit)) {
193
- throw new Error(
194
- `[timber] Configured appDir "${configAppDir}" does not exist at ${explicit}`
195
- );
193
+ throw new Error(`[timber] Configured appDir "${configAppDir}" does not exist at ${explicit}`);
196
194
  }
197
195
  return explicit;
198
196
  }
@@ -361,19 +359,21 @@ export function timber(config?: TimberUserConfig): PluginOption[] {
361
359
  const consumerRequire = createRequire(join(process.cwd(), 'package.json'));
362
360
  const rscPluginPath = consumerRequire.resolve('@vitejs/plugin-rsc');
363
361
  ctx.timer.start('rsc-plugin-import');
364
- const rscPluginsPromise = import(pathToFileURL(rscPluginPath).href).then(({ default: vitePluginRsc }) => {
365
- ctx.timer.end('rsc-plugin-import');
366
- return vitePluginRsc({
367
- serverHandler: false,
368
- customClientEntry: true,
369
- entries: {
370
- rsc: 'virtual:timber-rsc-entry',
371
- ssr: 'virtual:timber-ssr-entry',
372
- client: 'virtual:timber-browser-entry',
373
- },
374
- clientChunks: assignClientChunk,
375
- });
376
- });
362
+ const rscPluginsPromise = import(pathToFileURL(rscPluginPath).href).then(
363
+ ({ default: vitePluginRsc }) => {
364
+ ctx.timer.end('rsc-plugin-import');
365
+ return vitePluginRsc({
366
+ serverHandler: false,
367
+ customClientEntry: true,
368
+ entries: {
369
+ rsc: 'virtual:timber-rsc-entry',
370
+ ssr: 'virtual:timber-ssr-entry',
371
+ client: 'virtual:timber-browser-entry',
372
+ },
373
+ clientChunks: assignClientChunk,
374
+ });
375
+ }
376
+ );
377
377
 
378
378
  return [
379
379
  rootSync,
@@ -146,7 +146,9 @@ function createTimberMiddleware(server: ViteDevServer, projectRoot: string) {
146
146
  // environment's module runner for HMR-aware loading.
147
147
  let handler: (req: Request) => Promise<Response>;
148
148
  try {
149
- const rscEnv = server.environments.rsc as DevEnvironment & { runner?: { import: (id: string) => Promise<any> } };
149
+ const rscEnv = server.environments.rsc as DevEnvironment & {
150
+ runner?: { import: (id: string) => Promise<any> };
151
+ };
150
152
  // Duck-type check instead of isRunnableDevEnvironment() — the vite
151
153
  // import-based check fails across pnpm link boundaries where the
152
154
  // linked package resolves a different vite module instance.
@@ -92,7 +92,8 @@ function stripRootPrefix(id: string, root: string): string {
92
92
  */
93
93
  function generateConfigModule(ctx: PluginContext): string {
94
94
  // Resolve cookie secrets: `secret` shorthand expands to `secrets: [secret]`
95
- const cookieSecrets = ctx.config.cookies?.secrets ??
95
+ const cookieSecrets =
96
+ ctx.config.cookies?.secrets ??
96
97
  (ctx.config.cookies?.secret ? [ctx.config.cookies.secret] : undefined);
97
98
 
98
99
  const runtimeConfig = {
@@ -14,7 +14,10 @@ import { join } from 'node:path';
14
14
  import { scanRoutes } from '#/routing/scanner.js';
15
15
  import { generateRouteMap } from '#/routing/codegen.js';
16
16
  import { collectInterceptionRewrites } from '#/routing/interception.js';
17
- import { lintStatusFileDirectives, formatStatusFileLintWarnings } from '#/routing/status-file-lint.js';
17
+ import {
18
+ lintStatusFileDirectives,
19
+ formatStatusFileLintWarnings,
20
+ } from '#/routing/status-file-lint.js';
18
21
  import type { RouteTree, SegmentNode, RouteFile } from '#/routing/types.js';
19
22
  import type { PluginContext } from '#/index.js';
20
23
 
@@ -352,9 +355,7 @@ function generateManifestModule(tree: RouteTree): string {
352
355
  `${nextIndent} ${JSON.stringify(name)}: { load: ${v}, filePath: ${JSON.stringify(file.filePath)} }`
353
356
  );
354
357
  }
355
- parts.push(
356
- `${nextIndent}metadataRoutes: {\n${metaEntries.join(',\n')}\n${nextIndent}},`
357
- );
358
+ parts.push(`${nextIndent}metadataRoutes: {\n${metaEntries.join(',\n')}\n${nextIndent}},`);
358
359
  }
359
360
 
360
361
  // Children
@@ -26,11 +26,20 @@ export function timberServerBundle(): Plugin[] {
26
26
  // which throws in the SSR environment.
27
27
  if (command === 'serve') {
28
28
  // In dev, Vite externalizes node_modules and loads them via Node's
29
- // native require(). Deps that import `server-only` (like `bright`)
30
- // hit the real CJS package which throws at runtime. We force these
31
- // poison-pill packages to be non-external so they go through Vite's
32
- // module pipeline, where the timber-shims plugin intercepts them
33
- // and serves no-op virtual modules for server environments.
29
+ // native require(). This causes two problems:
30
+ //
31
+ // 1. Poison-pill packages: deps that import `server-only` (like `bright`)
32
+ // hit the real CJS package which throws in the SSR environment.
33
+ //
34
+ // 2. Dual React instances: deps with React hooks (nuqs, etc.) are
35
+ // externalized and loaded via Node.js, getting their own copy of
36
+ // React. Meanwhile, SSR's renderToReadableStream uses Vite's
37
+ // dep-optimized React. Two React instances = dispatcher mismatch,
38
+ // causing "Invalid hook call" / "Cannot read properties of null
39
+ // (reading 'useId')" errors. See LOCAL-297.
40
+ //
41
+ // We force these packages to be non-external so they go through
42
+ // Vite's module pipeline, which deduplicates React correctly.
34
43
  return {
35
44
  environments: {
36
45
  rsc: {
@@ -40,7 +49,7 @@ export function timberServerBundle(): Plugin[] {
40
49
  },
41
50
  ssr: {
42
51
  resolve: {
43
- noExternal: ['server-only', 'client-only'],
52
+ noExternal: ['server-only', 'client-only', 'nuqs'],
44
53
  },
45
54
  },
46
55
  },
@@ -173,21 +173,15 @@ export function timberShims(_ctx: PluginContext): Plugin {
173
173
  return 'export {};';
174
174
  }
175
175
 
176
- // Stub for @timber-js/app/server in client environment.
177
- // Exports throw-on-call stubs so named imports resolve but
178
- // calling them gives a clear error instead of crashing the bundle.
176
+ // Error module for @timber-js/app/server in client environment.
177
+ // Server modules must never be bundled into the browser — if this
178
+ // module is reached, there is a broken import chain that needs fixing.
179
179
  if (id === '\0timber:server-empty') {
180
- return `
181
- const stub = (name) => () => { throw new Error(name + "() is a server-only function and cannot be called in client code."); };
182
- export const headers = stub("headers");
183
- export const cookies = stub("cookies");
184
- export const notFound = stub("notFound");
185
- export const redirect = stub("redirect");
186
- export const permanentRedirect = stub("permanentRedirect");
187
- export const deny = stub("deny");
188
- export const searchParams = stub("searchParams");
189
- export const RedirectType = { push: "push", replace: "replace" };
190
- `;
180
+ return `throw new Error(
181
+ "[timber] @timber-js/app/server was imported from client code. " +
182
+ "Server modules (headers, cookies, redirect, deny, etc.) cannot be used in client components. " +
183
+ "If you need these APIs, move the import to a server component or middleware."
184
+ );`;
191
185
  }
192
186
  },
193
187
  };
@@ -106,9 +106,7 @@ export function formatStatusFileLintWarnings(warnings: StatusFileLintWarning[]):
106
106
  lines.push(
107
107
  " Status files and error.tsx are rendered inside TimberErrorBoundary (a 'use client' component)."
108
108
  );
109
- lines.push(
110
- " Add 'use client' as the first line of each file to avoid a runtime error."
111
- );
109
+ lines.push(" Add 'use client' as the first line of each file to avoid a runtime error.");
112
110
 
113
111
  return lines.join('\n');
114
112
  }
@@ -8,6 +8,8 @@
8
8
  * Design doc: design/09-typescript.md §"Typed searchParams — search-params.ts"
9
9
  */
10
10
 
11
+ import { useQueryStates as clientUseQueryStates } from '#/client/use-query-states.js';
12
+
11
13
  // ---------------------------------------------------------------------------
12
14
  // Types
13
15
  // ---------------------------------------------------------------------------
@@ -288,14 +290,19 @@ function buildDefinition<T extends Record<string, unknown>>(
288
290
  }
289
291
 
290
292
  // ---- useQueryStates ----
291
- // This is a placeholder that will be replaced by the client runtime.
292
- // At import time in a server context, calling this throws.
293
- // The actual implementation wraps nuqs and lives in @timber-js/app/client.
294
- function useQueryStates(_options?: QueryStatesOptions): [T, SetParams<T>] {
295
- throw new Error(
296
- 'useQueryStates() can only be called in a client component. ' +
297
- 'Import from @timber-js/app/client instead.'
298
- );
293
+ // Delegates to the 'use client' implementation from use-query-states.ts.
294
+ //
295
+ // In the RSC environment: use-query-states.ts is transformed by the RSC
296
+ // plugin into a client reference proxy. Calling it throws — correct,
297
+ // because hooks can't run during server component rendering.
298
+ // In SSR: use-query-states.ts is the real nuqs-backed function. Hooks
299
+ // work during SSR's renderToReadableStream, so this works correctly.
300
+ // On the client: same as SSR — the real function is available.
301
+ function useQueryStates(options?: QueryStatesOptions): [T, SetParams<T>] {
302
+ return clientUseQueryStates(codecMap, options, Object.freeze({ ...urlKeys })) as [
303
+ T,
304
+ SetParams<T>,
305
+ ];
299
306
  }
300
307
 
301
308
  const definition: SearchParamsDefinition<T> = {
@@ -147,6 +147,18 @@ function extractErrorHint(message: string): string | null {
147
147
  return 'A component resolved to undefined/null — check default exports and import paths';
148
148
  }
149
149
 
150
+ // "Invalid hook call" — hooks called outside React's render context.
151
+ // In RSC, this typically means a 'use client' component was executed as a
152
+ // server component instead of being serialized as a client reference.
153
+ if (message.includes('Invalid hook call')) {
154
+ return (
155
+ 'A hook was called outside of a React component render. ' +
156
+ "If this is a 'use client' component, ensure the directive is at the very top of the file " +
157
+ '(before any imports) and that @vitejs/plugin-rsc is loaded correctly. ' +
158
+ "Barrel re-exports from non-'use client' files do not propagate the directive."
159
+ );
160
+ }
161
+
150
162
  return null;
151
163
  }
152
164