Skip to content

Getting Started ​

1. Add the gem ​

ruby
# Gemfile
gem "terrazzo"
bash
bundle install

Bundler selects JSON 2.x for compatibility with current Rails releases. JSON 3 requires the Rails compatibility fix.

2. Install Superglue (if you haven't already) ​

Terrazzo is built on top of Superglue. If your app already uses Superglue, skip to step 3.

bash
rails g superglue:install

Run this before installing Terrazzo's npm dependencies in a new app. The Superglue generator may run your package manager and replace node_modules; installing Terrazzo's frontend packages afterwards keeps the final dependency state consistent.

This sets up the core Superglue infrastructure:

  • React/Redux application entry point (app/javascript/application.jsx)
  • Page-to-page mapping, store, and application visit handler
  • Flash message Redux slice
  • HTML and JSON layouts
  • config/initializers/superglue.rb
  • JS dependencies (react, react-dom, @reduxjs/toolkit, react-redux, @thoughtbot/superglue)

3. Install Vite Rails for the default Vite setup ​

If your app uses Rails esbuild instead, skip this step and pass --bundler=esbuild when you run the Terrazzo installer.

bash
bundle add vite_rails
bundle exec vite install

If the Vite installer reports package-manager errors, resolve those before installing Terrazzo. The Terrazzo installer checks that package.json includes the Vite packages generated by vite_rails, including vite and vite-plugin-ruby.

4. Add the npm package ​

bash
yarn add terrazzo
# or
npm install terrazzo

The terrazzo npm package provides the default React pages/components, utilities (cn, truncate, formatDate/DateTime/Time, csrfToken), hooks (useIsMobile), and the field registry API. The install generator creates app-level barrels that use those package defaults; eject a page, field, component, or UI primitive when you want app-owned source.

5. Install frontend dependencies ​

Terrazzo's default and ejected components use shadcn/ui patterns, so you'll need these packages. The generated admin CSS uses Tailwind CSS 4 syntax (@source, @theme, and @custom-variant), so install Tailwind 4 or newer:

bash
yarn add @radix-ui/react-avatar@1.1.11 @radix-ui/react-dialog@1.1.15 \
  @radix-ui/react-dropdown-menu@2.1.16 @radix-ui/react-label@2.1.8 \
  @radix-ui/react-popover@1.1.15 @radix-ui/react-select@2.2.6 \
  @radix-ui/react-separator@1.1.8 @radix-ui/react-slot@1.2.4 \
  @radix-ui/react-tooltip@1.2.8 class-variance-authority@0.7.1 \
  lucide-react@0.344.0 tailwindcss@4.2.1

The install generator also checks package.json and prints the exact package-manager command if any required frontend packages are missing or pinned below Terrazzo's supported versions.

Terrazzo also generates app/assets/stylesheets/admin.css, which the generated layout links as a Rails stylesheet asset. That file must be compiled by Tailwind before it is served. If your app does not already compile that exact file through a package script or Tailwind 4-compatible tailwindcss-rails, install the Tailwind CLI before running the Terrazzo installer:

bash
yarn add -D @tailwindcss/cli@4.2.1

When @tailwindcss/cli 4 or newer is installed and no Tailwind pipeline is detected, the Terrazzo installer adds this package script for you and includes it in a new build script when the app does not already define one:

json
{
  "scripts": {
    "build": "vite build && tailwindcss -i app/assets/stylesheets/admin.css -o app/assets/builds/admin.css --minify",
    "build:admin:css": "tailwindcss -i app/assets/stylesheets/admin.css -o app/assets/builds/admin.css --minify"
  }
}

The install generator warns when it cannot detect a Tailwind build script for app/assets/stylesheets/admin.css or Tailwind 4-compatible tailwindcss-rails. The @tailwindcss/vite plugin is useful for CSS imported through Vite, but by itself it does not compile Terrazzo's Rails-linked admin.css asset. For package.json script setups without compatible Tailwind tooling, the installer prints the matching install command for your package manager.

6. Run the Terrazzo install generator ​

Make sure your database schema is loaded before installing, because Terrazzo inspects your models' columns and associations to generate dashboards:

bash
bin/rails db:prepare

Run the installer after your app has at least one concrete ApplicationRecord model. Terrazzo generates dashboards and admin routes from those models; if none exist yet, add a model first and run the installer afterwards.

bash
rails g terrazzo:install

By default the generator assumes Vite and requires the vite_rails installer output, including config/vite.json, because the generated admin layout uses Vite Rails asset helpers. If your app uses Rails esbuild instead:

bash
rails g terrazzo:install --bundler=esbuild

The generated page mapping resolves resource pages through shared application components by default. Resource-specific pages generated by Terrazzo are registered in generated_page_mapping.js; manual custom pages belong in custom_page_mapping.js.

This creates an isolated admin namespace alongside your existing app — it won't conflict with any existing Superglue pages or controllers:

Admin Superglue infrastructure (namespaced under admin/):

  • app/javascript/admin/application.jsx — separate Superglue entry point for the admin
  • app/frontend/entrypoints/admin/application.jsx — default Vite entrypoint shim generated only with --bundler=vite; custom Vite sourceCodeDir / entrypointsDir settings are respected
  • config/vite.json — updated with admin JS/view watchAdditionalPaths when those generated files live outside Vite's sourceCodeDir
  • Procfile.dev and bin/dev — for Vite installs, ensures local development starts Rails and bin/vite dev together; custom bin/dev scripts are left untouched with a warning
  • app/javascript/admin/page_to_page_mapping.js — maps admin pages to React components with shared-page fallbacks
  • app/javascript/admin/generated_page_mapping.js — resource-specific page manifest maintained by Terrazzo generators
  • app/javascript/admin/custom_page_mapping.js — manual custom page manifest you own
  • app/javascript/admin/application_visit.js — visit/remote factory
  • app/javascript/admin/slices/flash.js — flash message Redux slice
  • app/javascript/admin.js — esbuild root entrypoint generated only with --bundler=esbuild
  • app/views/layouts/admin/application.html.erb — admin HTML layout
  • app/views/layouts/admin/application.json.props — admin JSON props layout

Admin controllers and routes:

  • app/controllers/admin/application_controller.rb — inherits from Terrazzo::ApplicationController
  • config/routes.rb — adds an admin namespace with a root route

Admin UI components and views:

  • app/assets/stylesheets/admin.css — Tailwind theme that scans Terrazzo package defaults plus local admin views and JavaScript
  • components.json — shadcn CLI aliases for admin components and UI primitives; existing configs are left untouched
  • jsconfig.json — root @/* alias for shadcn-style tooling when no JS/TS config already exists
  • app/views/admin/application/ — shared page stubs and navigation partial
  • app/views/admin/components/ — app component barrel for package defaults and local overrides
  • app/views/admin/components/ui/ — app UI barrel for package defaults and local shadcn-style primitives used by app-owned/ejected files
  • app/views/admin/fields/ — app field barrel for package defaults and local field overrides

Dashboards — automatically generates a dashboard for each ApplicationRecord model it finds.

7. Generate additional dashboards ​

The install generator (step 6) automatically creates dashboards for all existing ApplicationRecord models. To add dashboards for new models later:

bash
rails g terrazzo:dashboard Product
rails g terrazzo:dashboard Customer
rails g terrazzo:dashboard Order

Each generates:

  • app/dashboards/product_dashboard.rb — field definitions
  • app/controllers/admin/products_controller.rb — inherits from your admin ApplicationController

The shared page mapping fallback handles the standard CRUD pages. Generate a resource-specific view only when you need custom props or custom React for that resource.

8. Start the server ​

bash
bin/dev

For Vite installs, Terrazzo adds vite: bin/vite dev to Procfile.dev and replaces the stock Rails-only bin/dev with a Foreman runner. If your app already had a custom bin/dev, the generator leaves it in place and warns you to start Vite alongside Rails.

Visit http://localhost:3000/admin to see your admin panel.

Released under the MIT License.