Build with a clear
starting point.
The React + Tailwind developer guide. Learn the structure, customize the details and connect your own services.
Run locally
Use Node 22.12 or later; Node 24 is recommended. Open a terminal in this edition's folder.
npm ci npm run dev -- --port 5186
Open localhost:5186. Demo
credentials: jamie@example.com / navrenza123.
Included: dashboards, customers, projects, orders, inventory, solution starters, admin demos, reports, forms, components, profiles, mailbox, calendar, media, authentication examples and layout previews. Use Find a page in the sidebar to browse the catalog.
Understand the source
src/pages/: native Tailwind pages.src/moduleRoutes.tsx: lazy feature routes.-
src/modules/: standalone feature catalog, custom styles, images and JSON fixtures. -
src/ModuleProviders.tsx: workspace and theme adapters. src/components/: reusable presentation.src/data/workspace.json: editable sample data.src/data/model.ts: shared data contract.-
src/services/api.ts: mock/real transport selection. -
src/state.tsx: session, workspace and preference state.
Customize appearance
Edit palette values in src/theme-tokens.css and
semantic Tailwind utilities in src/styles.css. Tailwind
utilities use semantic colors such as bg-surface,
text-ink and border-line. Settings
controls dark mode, eleven color palettes, compact navigation,
header styles, sticky-header control and RTL. Preferences persist in
this browser. Layout pages contain interactive previews. Feature
styles are scoped under .edition-page by
src/module-skin.css; they retain custom selectors and
some legacy class names, without importing Bootstrap CSS or
JavaScript.
Fake backend and your API
Mock mode loads local JSON asynchronously through a request/response
transport. Changes are persisted under
navrenza:tailwind:workspace:v1. Editing the JSON seed
does not overwrite existing browser records; remove that storage key
in browser developer tools to reload the seed.
Copy .env.example to .env.local. Replace
mock mode with:
VITE_API_MODE=real VITE_API_URL=https://your-api.example.com/api
Restart Vite after changing environment variables. Your server must provide:
-
GET /workspace: a BusinessData response matchingsrc/data/model.ts. -
POST /workspace/actions: accepts anActionfromsrc/data/model.ts(customer, project, order and product mutations) and returns updated BusinessData.
The real-API switch covers workspace records. Admin, reporting and
library examples use separate local services under
src/modules/features/; replace these services to
connect additional server endpoints. Their browser data uses
navrenza:tailwind:modules:* keys. Alternate
login/register/reset pages demonstrate UI states only.
Requests include cookies via credentials:include. Configure your server's CORS and cookie policy. Replace demo login with server authentication and enforce authorization/CSRF protection there. The demo route guard is not a security boundary. No production backend is shipped.
Test and deploy
npm run build npm run test:e2e
Browser tests use installed Google Chrome. Upload the contents of
dist/ to static hosting. Hash routes work without
server-side route rewriting. Run through HTTP; opening React's
index.html via file:// is unsupported. Keep environment secrets on
your server; VITE_ variables are public.
Routes & navigation
The application uses hash routing. Public screens and the main shell
live in src/App.tsx. Feature routes are lazy-loaded in
src/moduleRoutes.tsx.
-
Create your screen in
src/pages/or in the appropriate feature directory. -
Add its lazy import and a route in
src/moduleRoutes.tsx, inside the existing application shell. -
Add its label and path to the appropriate group in
src/modules/app/navigation.ts. Main workspace shortcuts are defined insrc/App.tsx; horizontal navigation also usessrc/components/pageGroups.ts. - Test a direct hash URL, active navigation state, compact sidebar and mobile navigation.
const Reports = lazy(() => import('./pages/Reports'));
// Inside the route collection:
<Route path="reports" element={<Reports />} />
Use Link or NavLink from react-router-dom
for application routes. Use a normal anchor for standalone
documentation files.
Components & workflow boundaries
Native presentation components live in src/components/.
Shared feature controls such as cards, tables and dialogs live in
src/modules/components/. Check existing feature pages
before creating a new control.
-
Workspace: customer, project, order and inventory
operations share the model in
src/data/model.tsand reducer insrc/data/reducer.ts. -
Admin examples: team, support, files and billing
have separate local services under
src/modules/features/admin/. Connecting the workspace API does not connect these automatically. - Forms: demonstrate input and validation behavior. Connect submission handlers to your own endpoints.
- Files and billing: browser file storage and sample invoices are demonstrations; no upload server or payment processor is included.
Use semantic colors such as bg-surface,
text-muted and border-line so new
components follow the selected theme. Feature catalog styles are
scoped to .edition-page; keep that wrapper when reusing
those components.
Branding & default settings
Update the shared logo in
src/modules/components/BrandLogo.tsx and keep
meaningful alt text. The main shell is src/App.tsx; the
product introduction is
src/modules/features/business/ProductLandingPage.tsx.
Default appearance is defined by defaultSettings in
src/state.tsx. Saved preferences under
navrenza:tailwind:settings take priority over defaults.
Use Settings to reset them when checking a changed default.
The /welcome page is optional. For a customer
application, remove its route and navigation links if you do not
need a template introduction. Keep the dashboard as your primary
entry point.
How the fake backend works
-
src/data/seed.tsprepares sample data fromsrc/data/workspace.json. -
src/services/api.tsselects the fake or real transport based onVITE_API_MODE. -
src/services/fakeBackend.tshandles asynchronous Request/Response objects in the browser. This is an in-browser simulation, not a running HTTP server. - The workspace state loads records and dispatches typed actions. Successful writes update this browser's saved demo data.
# .env.local — default demo mode
VITE_API_MODE=mock
# Replace the mode above when your own API is ready:
# VITE_API_MODE=real
# VITE_API_URL=https://your-api.example.com/api
Keep only one active VITE_API_MODE assignment. Restart the dev server after changing this file. Production builds bake environment values into the output, so rebuild before uploading.
Troubleshooting
My JSON changes are not visible
Saved records take precedence over the seed. For this demo only,
remove navrenza:tailwind:workspace:v1 from browser
storage and reload. This discards local demo edits. Other feature
modules use their own keys.
The app opens the login screen
The demo uses a session-scoped login. Sign in with
jamie@example.com / navrenza123. Replace demo
authentication when integrating your server.
API requests fail after switching to real mode
Check VITE_API_URL, restart Vite, and inspect the browser Network tab. Verify the workspace response matches BusinessData and that your server allows the requesting origin and credentials.
Styles or assets are missing after deployment
Upload the complete contents of dist, including assets. Serve React over HTTP. If hosting beneath a subdirectory, configure Vite's base in vite.config.ts before rebuilding.
A new page is missing from navigation
Registering a route does not create a menu item. Update the matching navigation group and test both vertical and horizontal layouts.
Before handing over your application
- Replace demo identities, data and authentication.
- Connect the services your application actually uses.
- Run npm run build and the relevant browser tests.
- Check mobile, dark mode, RTL, empty states and error handling.
- Remove unused demo routes and update the documentation for your application.