diff --git a/.changeset/clever-months-swim.md b/.changeset/clever-months-swim.md new file mode 100644 index 00000000000..b2891178dde --- /dev/null +++ b/.changeset/clever-months-swim.md @@ -0,0 +1,5 @@ +--- +"@remix-run/dev": patch +--- + +Support JSX usage in `.jsx` files without manual `React` import in Vite diff --git a/integration/vite-dev-test.ts b/integration/vite-dev-test.ts index 18ec17b2f86..c948106e949 100644 --- a/integration/vite-dev-test.ts +++ b/integration/vite-dev-test.ts @@ -136,10 +136,10 @@ test.describe("Vite dev", () => { ); } `, - "app/routes/non-ts.jsx": js` - export default function Page() { + "app/routes/jsx.jsx": js` + export default function JsxRoute() { return ( -
+

HMR updated: no

); @@ -238,31 +238,32 @@ test.describe("Vite dev", () => { ); }); - test("handle non-typescript jsx file", async ({ page }) => { + test("handles JSX in .jsx file without React import", async ({ page }) => { let pageErrors: unknown[] = []; page.on("pageerror", (error) => pageErrors.push(error)); - await page.goto(`http://localhost:${devPort}/non-ts`, { + await page.goto(`http://localhost:${devPort}/jsx`, { waitUntil: "networkidle", }); expect(pageErrors).toEqual([]); - let hmrStatus = page.locator("#non-ts [data-hmr]"); + let hmrStatus = page.locator("#jsx [data-hmr]"); await expect(hmrStatus).toHaveText("HMR updated: no"); let indexRouteContents = await fs.readFile( - path.join(projectDir, "app/routes/non-ts.jsx"), + path.join(projectDir, "app/routes/jsx.jsx"), "utf8" ); await fs.writeFile( - path.join(projectDir, "app/routes/non-ts.jsx"), + path.join(projectDir, "app/routes/jsx.jsx"), indexRouteContents.replace("HMR updated: no", "HMR updated: yes"), "utf8" ); await page.waitForLoadState("networkidle"); await expect(hmrStatus).toHaveText("HMR updated: yes"); + expect(pageErrors).toEqual([]); - }) + }); }); let bufferize = (stream: Readable): (() => string) => { diff --git a/packages/remix-dev/vite/plugin.ts b/packages/remix-dev/vite/plugin.ts index 9f48433346b..e580c2660d9 100644 --- a/packages/remix-dev/vite/plugin.ts +++ b/packages/remix-dev/vite/plugin.ts @@ -432,9 +432,9 @@ export const remixVitePlugin: RemixVitePlugin = (options = {}) => { "react-dom/client", ], }, - // for server module, JSX transpilation is done by vite's esbuild esbuild: { - jsx: 'automatic', + jsx: "automatic", + jsxDev: viteCommand !== "build", }, resolve: { // https://react.dev/warnings/invalid-hook-call-warning#duplicate-react