tailwindcss icon indicating copy to clipboard operation
tailwindcss copied to clipboard

Tailwind 4 does not work with react-router v7 framework mode

Open AlemTuzlak opened this issue 1 year ago • 4 comments

What version of Tailwind CSS are you using?

For example: v4.0.0-beta.3

What build tool (or framework if it abstracts the build tool) are you using?

For example: react-router v7

What version of Node.js are you using?

For example: v22.0.0

What browser are you using?

For example: Chrome

What operating system are you using?

For example: Windows

Reproduction URL

You can find the reproduction on the PR below: https://github.com/forge42dev/base-stack/pull/14

Steps to reproduce:

  • clone the repro and checkout the PR
  • run npm run build
  • it fails

Describe your issue

The build script for tailwind doesn't work with react-router framework mode, I'm guessing it's also the case with Remix.run as the root issue seems the same. What I've noticed is that if you replace the following in package.json:

  "build": "react-router build"

with

  "build": "vite build"

the build goes through, I'm guessing there is something in the react-router build pipeline that breaks the tailwind compilation, the error i get is: [@tailwindcss/vite:generate:build] Missing opening {.

AlemTuzlak avatar Nov 29 '24 08:11 AlemTuzlak

I too am currently running into this error.

Node Version: v21.6.2 Pnpm Version: v8.15.6

{
  "name": "dabzsite",
  "private": true,
  "type": "module",
  "scripts": {
    "build": "react-router build",
    "dev": "react-router dev",
    "start": "react-router-serve ./build/server/index.js",
    "typecheck": "react-router typegen && tsc --build --noEmit"
  },
  "dependencies": {
    "@react-router/node": "^7.0.1",
    "@react-router/serve": "^7.0.1",
    "@szhsin/react-menu": "^4.2.3",
    "@tailwindcss/vite": "4.0.0-beta.3",
    "@types/luaparse": "^0.2.12",
    "framer-motion": "^11.12.0",
    "gray-matter": "^4.0.3",
    "isbot": "^5.1.17",
    "luaparse": "^0.3.1",
    "react": "^18.3.1",
    "react-dom": "^18.3.1",
    "react-icons": "^5.3.0",
    "react-markdown": "^9.0.1",
    "react-router": "^7.0.1",
    "react-syntax-highlighter": "^15.6.1"
  },
  "devDependencies": {
    "@react-router/dev": "^7.0.1",
    "@types/node": "^20",
    "@types/react": "^18.3.12",
    "@types/react-dom": "^18.3.1",
    "@types/react-syntax-highlighter": "^15.5.13",
    "tailwindcss": "4.0.0-beta.3",
    "typescript": "^5.6.3",
    "vite": "^5.4.11",
    "vite-tsconfig-paths": "^5.1.2"
  }
}

[@tailwindcss/vite:generate:build] Missing opening { file: DabzSite/app/app.css?transform-only

that said file only has the @import "tailwindcss"; in it.

ItzDabbzz avatar Nov 30 '24 05:11 ItzDabbzz

Similar here, I just updated both dependencies: tailwindcss and the vite plugin and I am getting the same issue: "^4.0.0-beta.4. I wonder if this relates to how I import the CSS file in the root.tsx. I am just doing import index.css

code: 'PLUGIN_ERROR',
plugin: '@tailwindcss/vite:generate:build',
hook: 'transform',

mobregozo avatar Nov 30 '24 10:11 mobregozo

I would like to note, if you build your css file using tailwind's cli tool, and use the outputted css file, react router builds just fine.

ItzDabbzz avatar Nov 30 '24 10:11 ItzDabbzz

After a bit of digging around I've noticed that it fails only with the server part of the bundling, the client build for production works fine. It's a bit impossible to debug locally because the code is minified. From what I can see it happens in the transform hook of @tailwincss/vite:generate:build with the tailwind file that ends with ?transform-only

Also what I've noticed after looking at the source Code because the strack trace locally complains about P.generate, I'd guess it originates from here: https://github.com/tailwindlabs/tailwindcss/blob/next/packages/%40tailwindcss-vite/src/index.ts#L281

AlemTuzlak avatar Nov 30 '24 13:11 AlemTuzlak

We've done a bit of digging into this today and, whelp, this is confusing to say the least!

We tracked this down to the Vite createResolver() API we use to resolve CSS files inside @import. So what's happening is that our Vite extension sees the following module:

/* tailwind.css?transform-only */
@import "tailwindcss";

@theme {
  /* Your theme styles go here */
}

Which looks like great CSS to me! Then this goes into tailwindcss core where we attempt to resolve the @import. But, for some reason, the Vite resolver function returns a JavaScript module in your repro?!.

Screenshot 2024-12-02 at 17 32 35

You can see in the screenshots the options we pass into the createResolver() API yet we get an .mjs extension back?

It's unclear yet what's going on in the react-router codebase for this to be the case.

We have one potentially gruel workaround for this already where we introspect the result of Vite's createResolver() API and if it's not a .css file, fall-back to using our internal version of the CSS file resolver. But. Ugh.

philipp-spiess avatar Dec 02 '24 16:12 philipp-spiess

@philipp-spiess thank you for looking into this, I've pretty please asked the react router core team to take a look at this issue to see if maybe they could pinpoint the issue as well so we can all get along and enjoy our styling experience!

AlemTuzlak avatar Dec 02 '24 17:12 AlemTuzlak

With the thanks of the glorious @rossipedia we've managed to get it sorted it seems, after his investigation it seems as though it wasn't just a react-router thing but rather a vite build --ssr thing. I've created a PR with the potential fix that you guys can investigate a bit deeper and see if that works out. Really hope this helps out @philipp-spiess

AlemTuzlak avatar Dec 02 '24 20:12 AlemTuzlak

Alright the fix has been merged and it'll be in the next beta release. Appreciate it @AlemTuzlak (and @rossipedia) 👍

thecrypticace avatar Dec 02 '24 22:12 thecrypticace

I have tried this with the new version of Tailwindcss 4.0.0-beta.5 plus vite 6.0.2 and works as expected! great work!!!!

mobregozo avatar Dec 05 '24 10:12 mobregozo

@thecrypticace This again doesn't work in 4.0.17

package.json

"tailwindcss": "^4.0.17",
 "@tailwindcss/vite": "^4.0.17",

vite config

export default defineConfig({
  plugins: [
    tailwindcss(),
    remixCloudflareDevProxy(),
    reactRouter(),
    serverAdapter({
      adapter,
      getLoadContext,
      entry: "server/index.ts",
    }),
    tsconfigPaths(),
  ],
});

more details here - https://github.com/yusukebe/hono-react-router-adapter/issues/66

vickyRathee avatar Mar 26 '25 13:03 vickyRathee

"devDependencies": {
    "@react-router/dev": "^7.7.1",
    "@tailwindcss/vite": "^4.1.4",
    "@types/bun": "latest",
    "@types/node": "^20",
    "@types/react": "^19.1.2",
    "@types/react-dom": "^19.1.2",
    "tailwindcss": "^4.1.13",
    "typescript": "^5.8.3",
    "vite": "^6.3.3",
    "vite-tsconfig-paths": "^5.1.4"
  }

Tailwind CSS still not working when I do, "npm run dev". I checked all the configs, everything is as mentioned in the documentation. Can someone please help me. I have been trying to make it work for a while now. I'm Using Vite.

Also please note: Tailwindcss works fine when I use it with TanStack Router via Vite.

spicebits avatar Sep 11 '25 11:09 spicebits

Consider checking you have followed all the Vite integration steps. Otherwise, consider providing a git repo that reproduces the issue and we can take a look for you.

wongjn avatar Sep 11 '25 13:09 wongjn