Skip to content

Getting Started

Create a static React documentation site with Ardo's scaffolded Vite and React Router setup.

Getting Started

The fastest way to evaluate Ardo is to scaffold a real docs site, run it locally, and add one MDX page. The scaffold gives you the full React Router shell, Tailwind v4, Ardo's default UI, and static build settings so you can focus on content first.

Prerequisites

You'll need:

  • Node.js version 22 or higher
  • pnpm (recommended) or npm/yarn

Fast Path

The fastest path is the create-ardo CLI. It scaffolds a complete project — configuration, example content, and a GitHub Pages deployment workflow — so you can focus on writing.

pnpm create ardo@latest my-docs
cd my-docs
pnpm install
pnpm dev

Open http://localhost:5173 and you'll see your site. Add an MDX file to app/routes/, and Ardo includes it in the generated navigation.

Manual Installation

If you want to add Ardo to an existing workspace or understand the scaffold, follow the manual setup. The split is simple: Vite handles build-time configuration, React handles UI configuration.

1. Create a new project

mkdir my-docs
cd my-docs
pnpm init

2. Install dependencies

pnpm add ardo react react-dom react-router isbot
pnpm add -D @react-router/dev @tailwindcss/vite tailwindcss typescript vite @types/react @types/react-dom

3. Create Vite configuration

The ardo() plugin handles build-time configuration. UI configuration (navigation, sidebar, footer) is done via JSX props in root.tsx:

import { defineConfig } from "vite"
import tailwindcss from "@tailwindcss/vite"
import { ardo } from "ardo/vite"

export default defineConfig({
  plugins: [
    tailwindcss(),
    ardo({
      title: "My Documentation",
      description: "My awesome documentation site",
    }),
  ],
})

4. Create React Router configuration

Ardo uses React Router 7 under the hood. For a static documentation site, you want pre-rendering enabled and SSR off:

import type { Config } from "@react-router/dev/config"

export default {
  ssr: false,
  prerender: true,
} satisfies Config

5. Create app files

These are standard React Router entry files plus Ardo's root component. If you've worked with React Router before, the shape should feel familiar.

app/root.tsx:

import { ArdoRoot, ArdoRootLayout } from "ardo/ui"
import config from "virtual:ardo/config"
import sidebar from "virtual:ardo/sidebar"
import "ardo/ui/styles.css"

export function Layout({ children }: { children: React.ReactNode }) {
  return <ArdoRootLayout>{children}</ArdoRootLayout>
}

export default function Root() {
  return <ArdoRoot config={config} sidebar={sidebar} />
}

app/entry.client.tsx:

import { startTransition, StrictMode } from "react"
import { hydrateRoot } from "react-dom/client"
import { HydratedRouter } from "react-router/dom"

startTransition(() => {
  hydrateRoot(
    document,
    <StrictMode>
      <HydratedRouter />
    </StrictMode>
  )
})

app/entry.server.tsx:

import type { EntryContext } from "react-router"
import { ServerRouter } from "react-router"
import { renderToReadableStream } from "react-dom/server"
import { isbot } from "isbot"

export default async function handleRequest(
  request: Request,
  responseStatusCode: number,
  responseHeaders: Headers,
  routerContext: EntryContext
) {
  const userAgent = request.headers.get("user-agent")

  const stream = await renderToReadableStream(
    <ServerRouter context={routerContext} url={request.url} />,
    {
      onError(error: unknown) {
        console.error(error)
        responseStatusCode = 500
      },
    }
  )

  if (userAgent && isbot(userAgent)) {
    await stream.allReady
  }

  responseHeaders.set("Content-Type", "text/html")

  return new Response(stream, {
    status: responseStatusCode,
    headers: responseHeaders,
  })
}

6. Create your first document

Create app/routes/guide/getting-started.mdx:

---
title: Getting Started
---

# Getting Started

Welcome to your documentation site!

That's it. Run pnpm dev and you've got a documentation site.

The create-ardo CLI generates all of these files automatically — use it when you want to skip the boilerplate and get straight to writing.

Development

Start the development server:

pnpm dev

Your site will be running at http://localhost:5173. Changes to MDX and TSX routes flow through Vite's development server.

Production Build

When you're ready to publish:

pnpm build

The output lands in build/client/ — a fully static site ready for any hosting platform. Preview it locally before deploying:

pnpm preview

Project Structure

Here's what an Ardo project looks like. If you've worked with React Router, the layout will feel natural:

my-docs/
├── app/
│   ├── routes/                  # Your MDX/MD content files
│   │   ├── guide/
│   │   │   └── getting-started.mdx
│   │   └── home.tsx             # Home page
│   ├── root.tsx                 # Root layout
│   ├── entry.client.tsx         # Client entry
│   └── entry.server.tsx         # Server entry
├── vite.config.ts               # Vite + Ardo configuration
├── react-router.config.ts       # React Router configuration
├── tsconfig.json
└── package.json

Next Steps

Your site is running. Now make it yours: