Rails + Inertia + React + ShadCN

Follow instructions here:

Note: You can remove these lines from the head since they won't be used:

<%= stylesheet_link_tag :app, "data-turbo-track": "reload" %>
<%= javascript_importmap_tags %>

Test it out by installing any shadcn component, like a button:

npx shadcn@latest add button

and add it to a page:

import { Button } from '@/components/ui/button'

...

<Button variant="outline">Click me</Button>

In addition to those instructions, I also had to make several other fixes to get it working:

Fix the @ issue by updating my vite.config.ts to this:

import react from '@vitejs/plugin-react'
import tailwindcss from '@tailwindcss/vite'
import { defineConfig } from 'vite'
import RubyPlugin from 'vite-plugin-ruby'
import path from 'path'

export default defineConfig({
  plugins: [
    react(),
    tailwindcss(),
    RubyPlugin(),
  ],
  resolve: {
    alias: {
      '@': path.resolve(__dirname, './app/frontend'),
    },
  },
})

CSS styles not showing up

Here are the key changes that were necessary to make Tailwind styles work with shadcn/ui in your Rails + Inertia + Vite setup:

Required Changes

1. Import CSS in the Inertia entrypoint (app/javascript/entrypoints/inertia.ts)

Added the CSS import so Vite processes and injects the Tailwind styles:

import './application.css'

2. Configure Tailwind v4 to scan the correct directories (app/javascript/entrypoints/application.css)

Added @source directives to tell Tailwind where to find your component files:

@source "../../frontend";
@source "../pages";

This ensures Tailwind scans both app/frontend/ (where shadcn components live) and app/javascript/pages/ (where your Inertia pages live) to generate the necessary utility classes.

3. Update TypeScript configuration (tsconfig.app.json)

Changed the include array to cover both directories:

"include": ["app/javascript", "app/frontend"]

This allows TypeScript to resolve imports from the app/frontend directory where shadcn components are installed.

4. Remove duplicate CSS loading (app/views/layouts/application.html.erb)

Removed this line:

<%= vite_stylesheet_tag "application" %>

Since the CSS is now imported in the JavaScript entrypoint, loading it separately was causing conflicts.

Summary

The core issue was that Tailwind v4 wasn't scanning the app/frontend directory where shadcn/ui installs its components, so the utility classes (like bg-primary, hover:bg-primary/90, etc.) weren't being generated. The @source directive fixed this.

Last updated