@vitejs/plugin-rsc 0.4.25 → 0.4.27

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.
package/README.md CHANGED
@@ -168,6 +168,11 @@ export default async function handler(request: Request): Promise<Response> {
168
168
  },
169
169
  })
170
170
  }
171
+
172
+ // add `import.meta.hot.accept` to handle server module change efficiently
173
+ if (import.meta.hot) {
174
+ import.meta.hot.accept()
175
+ }
171
176
  ```
172
177
 
173
178
  - [`entry.ssr.tsx`](./examples/starter/src/framework/entry.ssr.tsx)
@@ -355,6 +360,8 @@ import.meta.hot.on('rsc:update', async () => {
355
360
 
356
361
  ### `@vitejs/plugin-rsc`
357
362
 
363
+ - Type: `rsc: (options?: RscPluginOptions) => Plugin[]`;
364
+
358
365
  ```js
359
366
  import rsc from '@vitejs/plugin-rsc'
360
367
  import { defineConfig } from 'vite'
@@ -390,8 +397,15 @@ export default defineConfig({
390
397
  // for example, to obtain a key through environment variable during runtime.
391
398
  // cf. https://nextjs.org/docs/app/guides/data-security#overwriting-encryption-keys-advanced
392
399
  defineEncryptionKey: 'process.env.MY_ENCRYPTION_KEY',
400
+
401
+ // see `RscPluginOptions` for full options ...
393
402
  }),
394
403
  ],
404
+ // the same options can be also specified via top-level `rsc` property.
405
+ // this allows other plugin to set options via `config` hook.
406
+ rsc: {
407
+ // ...
408
+ },
395
409
  })
396
410
  ```
397
411
 
@@ -477,6 +491,57 @@ export function Page() {
477
491
 
478
492
  See https://github.com/vitejs/vite-plugin-react/pull/524 for how to install the package for React [canary](https://react.dev/community/versioning-policy#canary-channel) and [experimental](https://react.dev/community/versioning-policy#all-release-channels) usages.
479
493
 
494
+ ## Using `@vitejs/plugin-rsc` as a framework package's `dependencies`
495
+
496
+ By default, `@vitejs/plugin-rsc` is expected to be used as `peerDependencies` similar to `react` and `react-dom`. When `@vitejs/plugin-rsc` is not available at the project root (e.g., in `node_modules/@vitejs/plugin-rsc`), you will see warnings like:
497
+
498
+ ```sh
499
+ Failed to resolve dependency: @vitejs/plugin-rsc/vendor/react-server-dom/client.browser, present in client 'optimizeDeps.include'
500
+ ```
501
+
502
+ This can be fixed by updating `optimizeDeps.include` to reference `@vitejs/plugin-rsc` through your framework package. For example, you can add the following plugin:
503
+
504
+ ```js
505
+ // package name is "my-rsc-framework"
506
+ export default function myRscFrameworkPlugin() {
507
+ return {
508
+ name: 'my-rsc-framework:config',
509
+ configEnvironment(_name, config) {
510
+ if (config.optimizeDeps?.include) {
511
+ config.optimizeDeps.include = config.optimizeDeps.include.map(
512
+ (entry) => {
513
+ if (entry.startsWith('@vitejs/plugin-rsc')) {
514
+ entry = `my-rsc-framework > ${entry}`
515
+ }
516
+ return entry
517
+ },
518
+ )
519
+ }
520
+ },
521
+ }
522
+ }
523
+ ```
524
+
525
+ ## Typescript
526
+
527
+ Types for global API are defined in `@vitejs/plugin-rsc/types`. For example, you can add it to `tsconfig.json` to have types for `import.meta.viteRsc` APIs:
528
+
529
+ ```json
530
+ {
531
+ "compilerOptions": {
532
+ "types": ["vite/client", "@vitejs/plugin-rsc/types"]
533
+ }
534
+ }
535
+ ```
536
+
537
+ ```ts
538
+ import.meta.viteRsc.loadModule
539
+ // ^^^^^^^^^^
540
+ // <T>(environmentName: string, entryName: string) => Promise<T>
541
+ ```
542
+
543
+ See also [Vite documentation](https://vite.dev/guide/api-hmr.html#intellisense-for-typescript) for `vite/client` types.
544
+
480
545
  ## Credits
481
546
 
482
547
  This project builds on fundamental techniques and insights from pioneering Vite RSC implementations.
package/dist/index.d.ts CHANGED
@@ -1,4 +1,4 @@
1
- import { RscPluginOptions, vitePluginRsc } from "./plugin-YtSjJn3Y.js";
1
+ import { RscPluginOptions, vitePluginRsc } from "./plugin-Be24jgQb.js";
2
2
  import MagicString from "magic-string";
3
3
  import { Program } from "estree";
4
4
 
package/dist/index.js CHANGED
@@ -1,6 +1,6 @@
1
1
  import "./dist-DiJnRA1C.js";
2
2
  import "./plugin-CZbI4rhS.js";
3
- import { transformHoistInlineDirective, vitePluginRsc } from "./plugin--LiSJGtB.js";
3
+ import { transformHoistInlineDirective, vitePluginRsc } from "./plugin-CtdHIozK.js";
4
4
  import "./encryption-utils-BDwwcMVT.js";
5
5
  import "./rpc-tGuLT8PD.js";
6
6
  import "./shared-BWHxNw3Q.js";
@@ -88,7 +88,7 @@ type RscPluginOptions = {
88
88
  /**
89
89
  * use `Plugin.buildApp` hook (introduced on Vite 7) instead of `builder.buildApp` configuration
90
90
  * for better composability with other plugins.
91
- * @default false
91
+ * @default true since Vite 7
92
92
  */
93
93
  useBuildAppHook?: boolean;
94
94
  /**
@@ -106,10 +106,13 @@ type RscPluginOptions = {
106
106
  *
107
107
  * This function allows you to group multiple client components into
108
108
  * custom chunks instead of having each module in its own chunk.
109
+ * By default, client chunks are grouped by `meta.serverChunk`.
109
110
  */
110
111
  clientChunks?: (meta: {
111
112
  /** client reference module id */
112
113
  id: string;
114
+ /** normalized client reference module id */
115
+ normalizedId: string;
113
116
  /** server chunk which includes a corresponding client reference proxy module */
114
117
  serverChunk: string;
115
118
  }) => string | undefined;
@@ -148,4 +151,4 @@ declare function transformRscCssExport(options: {
148
151
  output: MagicString;
149
152
  } | undefined>;
150
153
  //#endregion
151
- export { AssetDeps, AssetsManifest, ResolvedAssetDeps, ResolvedAssetsManifest, RscPluginOptions, transformRscCssExport, vitePluginRsc, vitePluginRscMinimal };
154
+ export { AssetDeps, AssetsManifest, ResolvedAssetDeps, ResolvedAssetsManifest, type RscPluginManager, RscPluginOptions, transformRscCssExport, vitePluginRsc, vitePluginRscMinimal };
@@ -519,6 +519,21 @@ function hashString(v) {
519
519
 
520
520
  //#endregion
521
521
  //#region src/plugins/scan.ts
522
+ function scanBuildStripPlugin({ manager }) {
523
+ return {
524
+ name: "rsc:scan-strip",
525
+ apply: "build",
526
+ enforce: "post",
527
+ async transform(code, _id, _options) {
528
+ if (!manager.isScanBuild) return;
529
+ const output = await transformScanBuildStrip(code);
530
+ return {
531
+ code: output,
532
+ map: { mappings: "" }
533
+ };
534
+ }
535
+ };
536
+ }
522
537
  const importGlobRE = /\bimport\.meta\.glob(?:<\w+>)?\s*\(/g;
523
538
  async function transformScanBuildStrip(code) {
524
539
  const [imports] = esModuleLexer.parse(code);
@@ -734,6 +749,7 @@ function vitePluginRsc(rscPluginOptions = {}) {
734
749
  {
735
750
  name: "rsc",
736
751
  async config(config, env) {
752
+ if (config.rsc) Object.assign(rscPluginOptions, vite.mergeConfig(config.rsc, rscPluginOptions));
737
753
  const result = await crawlFrameworkPkgs({
738
754
  root: process.cwd(),
739
755
  isBuild: env.command === "build",
@@ -752,7 +768,7 @@ function vitePluginRsc(rscPluginOptions = {}) {
752
768
  ...result.ssr.noExternal.sort()
753
769
  ];
754
770
  return {
755
- appType: "custom",
771
+ appType: config.appType ?? "custom",
756
772
  define: { "import.meta.env.__vite_rsc_build__": JSON.stringify(env.command === "build") },
757
773
  environments: {
758
774
  client: {
@@ -810,11 +826,18 @@ function vitePluginRsc(rscPluginOptions = {}) {
810
826
  builder: {
811
827
  sharedPlugins: true,
812
828
  sharedConfigBuild: true,
813
- buildApp: rscPluginOptions.useBuildAppHook ? void 0 : buildApp
829
+ async buildApp(builder) {
830
+ if (!rscPluginOptions.useBuildAppHook) await buildApp(builder);
831
+ }
814
832
  }
815
833
  };
816
834
  },
817
- buildApp: rscPluginOptions.useBuildAppHook ? buildApp : void 0,
835
+ configResolved() {
836
+ if (Number(vite.version.split(".")[0]) >= 7) rscPluginOptions.useBuildAppHook ??= true;
837
+ },
838
+ buildApp: { async handler(builder) {
839
+ if (rscPluginOptions.useBuildAppHook) await buildApp(builder);
840
+ } },
818
841
  configureServer(server) {
819
842
  globalThis.__viteRscDevServer = server;
820
843
  const oldSend = server.environments.client.hot.send;
@@ -845,6 +868,7 @@ function vitePluginRsc(rscPluginOptions = {}) {
845
868
  const resolved = await environment.pluginContainer.resolveId(source);
846
869
  assert(resolved, `[vite-rsc] failed to resolve server handler '${source}'`);
847
870
  const mod = await environment.runner.import(resolved.id);
871
+ req.url = req.originalUrl ?? req.url;
848
872
  await createRequestListener(mod.default)(req, res);
849
873
  } catch (e) {
850
874
  next(e);
@@ -873,6 +897,7 @@ function vitePluginRsc(rscPluginOptions = {}) {
873
897
  return () => {
874
898
  server.middlewares.use(async (req, res, next) => {
875
899
  try {
900
+ req.url = req.originalUrl ?? req.url;
876
901
  await handler(req, res);
877
902
  } catch (e) {
878
903
  next(e);
@@ -1164,34 +1189,25 @@ import.meta.hot.on("rsc:update", () => {
1164
1189
  `;
1165
1190
  return code;
1166
1191
  }),
1167
- {
1168
- name: "rsc:inject-async-local-storage",
1169
- transform: { handler(code) {
1170
- if ((this.environment.name === "ssr" || this.environment.name === "rsc") && code.includes("typeof AsyncLocalStorage") && code.includes("new AsyncLocalStorage()") && !code.includes("__viteRscAyncHooks")) return (this.environment.mode === "build" && !isRolldownVite ? `const __viteRscAyncHooks = require("node:async_hooks");` : `import * as __viteRscAyncHooks from "node:async_hooks";`) + `globalThis.AsyncLocalStorage = __viteRscAyncHooks.AsyncLocalStorage;` + code;
1171
- } }
1172
- },
1173
1192
  ...vitePluginRscMinimal(rscPluginOptions, manager),
1174
1193
  ...vitePluginFindSourceMapURL(),
1175
1194
  ...vitePluginRscCss(rscPluginOptions, manager),
1176
- ...rscPluginOptions.validateImports !== false ? [validateImportPlugin()] : [],
1195
+ {
1196
+ ...validateImportPlugin(),
1197
+ apply: () => rscPluginOptions.validateImports !== false
1198
+ },
1177
1199
  scanBuildStripPlugin({ manager }),
1178
- ...cjsModuleRunnerPlugin()
1200
+ ...cjsModuleRunnerPlugin(),
1201
+ ...globalAsyncLocalStoragePlugin()
1179
1202
  ];
1180
1203
  }
1181
- function scanBuildStripPlugin({ manager }) {
1182
- return {
1183
- name: "rsc:scan-strip",
1184
- apply: "build",
1185
- enforce: "post",
1186
- async transform(code, _id, _options) {
1187
- if (!manager.isScanBuild) return;
1188
- const output = await transformScanBuildStrip(code);
1189
- return {
1190
- code: output,
1191
- map: { mappings: "" }
1192
- };
1193
- }
1194
- };
1204
+ function globalAsyncLocalStoragePlugin() {
1205
+ return [{
1206
+ name: "rsc:inject-async-local-storage",
1207
+ transform: { handler(code) {
1208
+ if ((this.environment.name === "ssr" || this.environment.name === "rsc") && code.includes("typeof AsyncLocalStorage") && code.includes("new AsyncLocalStorage()") && !code.includes("__viteRscAsyncHooks")) return (this.environment.mode === "build" && !isRolldownVite ? `const __viteRscAsyncHooks = require("node:async_hooks");` : `import * as __viteRscAsyncHooks from "node:async_hooks";`) + `globalThis.AsyncLocalStorage = __viteRscAsyncHooks.AsyncLocalStorage;` + code;
1209
+ } }
1210
+ }];
1195
1211
  }
1196
1212
  function vitePluginUseClient(useClientPluginOptions, manager) {
1197
1213
  const packageSources = /* @__PURE__ */ new Map();
@@ -1293,8 +1309,9 @@ function vitePluginUseClient(useClientPluginOptions, manager) {
1293
1309
  for (const meta of Object.values(manager.clientReferenceMetaMap)) {
1294
1310
  let name = useClientPluginOptions.clientChunks?.({
1295
1311
  id: meta.importId,
1312
+ normalizedId: manager.toRelativeId(meta.importId),
1296
1313
  serverChunk: meta.serverChunk
1297
- }) ?? manager.toRelativeId(meta.importId);
1314
+ }) ?? meta.serverChunk;
1298
1315
  name = cleanUrl(name.replaceAll("..", "__"));
1299
1316
  const group = manager.clientReferenceGroups[name] ??= [];
1300
1317
  group.push(meta);
package/dist/plugin.d.ts CHANGED
@@ -1,2 +1,2 @@
1
- import { AssetDeps, AssetsManifest, ResolvedAssetDeps, ResolvedAssetsManifest, RscPluginOptions, transformRscCssExport, vitePluginRsc, vitePluginRscMinimal } from "./plugin-YtSjJn3Y.js";
2
- export { AssetDeps, AssetsManifest, ResolvedAssetDeps, ResolvedAssetsManifest, RscPluginOptions, vitePluginRsc as default, transformRscCssExport, vitePluginRscMinimal };
1
+ import { AssetDeps, AssetsManifest, ResolvedAssetDeps, ResolvedAssetsManifest, RscPluginManager, RscPluginOptions, transformRscCssExport, vitePluginRsc, vitePluginRscMinimal } from "./plugin-Be24jgQb.js";
2
+ export { AssetDeps, AssetsManifest, ResolvedAssetDeps, ResolvedAssetsManifest, RscPluginManager, RscPluginOptions, vitePluginRsc as default, transformRscCssExport, vitePluginRscMinimal };
package/dist/plugin.js CHANGED
@@ -1,6 +1,6 @@
1
1
  import "./dist-DiJnRA1C.js";
2
2
  import "./plugin-CZbI4rhS.js";
3
- import { transformRscCssExport, vitePluginRsc, vitePluginRscMinimal } from "./plugin--LiSJGtB.js";
3
+ import { transformRscCssExport, vitePluginRsc, vitePluginRscMinimal } from "./plugin-CtdHIozK.js";
4
4
  import "./encryption-utils-BDwwcMVT.js";
5
5
  import "./rpc-tGuLT8PD.js";
6
6
  import "./shared-BWHxNw3Q.js";
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@vitejs/plugin-rsc",
3
- "version": "0.4.25",
3
+ "version": "0.4.27",
4
4
  "description": "React Server Components (RSC) support for Vite.",
5
5
  "keywords": [
6
6
  "vite",
@@ -52,8 +52,8 @@
52
52
  "@tsconfig/strictest": "^2.0.5",
53
53
  "@types/estree": "^1.0.8",
54
54
  "@types/node": "^22.18.0",
55
- "@types/react": "^19.1.11",
56
- "@types/react-dom": "^19.1.8",
55
+ "@types/react": "^19.1.12",
56
+ "@types/react-dom": "^19.1.9",
57
57
  "@vitejs/plugin-react": "workspace:*",
58
58
  "react": "^19.1.1",
59
59
  "react-dom": "^19.1.1",
package/types/index.d.ts CHANGED
@@ -16,4 +16,11 @@ declare global {
16
16
  }
17
17
  }
18
18
 
19
+ declare module 'vite' {
20
+ interface UserConfig {
21
+ /** Options for `@vitejs/plugin-rsc` */
22
+ rsc?: import('@vitejs/plugin-rsc').RscPluginOptions
23
+ }
24
+ }
25
+
19
26
  export {}