Skip to main content
Understanding the project structure helps you navigate and customize the starter template.

Directory Overview

nextjs-minimal/
β”œβ”€β”€ app/                         # Next.js App Router pages
β”‚   β”œβ”€β”€ page.tsx                 # Landing page with MBTI explorer
β”‚   β”œβ”€β”€ layout.tsx               # Root layout with providers
β”‚   β”œβ”€β”€ test/page.tsx            # Personality test (iframe embed)
β”‚   β”œβ”€β”€ results/page.tsx         # Results dashboard with analysis
β”‚   β”œβ”€β”€ coach/page.tsx           # AI coaching with dynamic context
β”‚   β”œβ”€β”€ admin/                   # Admin panel (modular components)
β”‚   β”‚   β”œβ”€β”€ page.tsx             # Main admin page
β”‚   β”‚   β”œβ”€β”€ BalanceCard.tsx      # Account balance display
β”‚   β”‚   β”œβ”€β”€ SessionsCard.tsx     # Sessions list
β”‚   β”‚   └── ...                  # Other admin components
β”‚   β”œβ”€β”€ auth/
β”‚   β”‚   β”œβ”€β”€ AuthContext.tsx      # Auth provider (Firebase + local)
β”‚   β”‚   └── signin/page.tsx      # Sign-in page
β”‚   └── api/
β”‚       β”œβ”€β”€ ttai/client.ts       # Server-side ToughTongue API client
β”‚       β”œβ”€β”€ sessions/            # Session CRUD + analyze endpoints
β”‚       β”‚   β”œβ”€β”€ route.ts         # GET /api/sessions
β”‚       β”‚   β”œβ”€β”€ [sessionId]/route.ts
β”‚       β”‚   └── analyze/route.ts
β”‚       └── balance/route.ts     # GET /api/balance
β”‚
β”œβ”€β”€ components/
β”‚   β”œβ”€β”€ TTAIIframe.tsx           # ToughTongue iframe wrapper
β”‚   β”œβ”€β”€ Header.tsx               # Navigation header
β”‚   β”œβ”€β”€ PageHeader.tsx           # Page title component
β”‚   β”œβ”€β”€ EmptyState.tsx           # Empty state placeholder
β”‚   β”œβ”€β”€ StatusCards.tsx          # Status display cards
β”‚   β”œβ”€β”€ auth/                    # Auth-related components
β”‚   β”‚   β”œβ”€β”€ AuthCard.tsx         # Auth form card
β”‚   β”‚   β”œβ”€β”€ AuthGuard.tsx        # Route protection
β”‚   β”‚   └── index.ts             # Exports
β”‚   └── ui/                      # shadcn/ui components
β”‚       β”œβ”€β”€ button.tsx
β”‚       β”œβ”€β”€ card.tsx
β”‚       β”œβ”€β”€ dialog.tsx
β”‚       └── ...
β”‚
β”œβ”€β”€ lib/
β”‚   β”œβ”€β”€ config.ts                # Centralized environment config
β”‚   β”œβ”€β”€ constants.ts             # Routes + MBTI type data (16 types)
β”‚   β”œβ”€β”€ store.ts                 # Zustand store with localStorage
β”‚   β”œβ”€β”€ firebase.ts              # Firebase initialization
β”‚   β”œβ”€β”€ auth.ts                  # Admin auth utilities
β”‚   β”œβ”€β”€ utils.ts                 # Utility functions (cn, etc.)
β”‚   └── ttai/                    # ToughTongue client module
β”‚       β”œβ”€β”€ index.ts             # Public exports
β”‚       β”œβ”€β”€ constants.ts         # Scenario IDs
β”‚       β”œβ”€β”€ types.ts             # Type definitions
β”‚       └── client.ts            # URL builders + event handlers
β”‚
β”œβ”€β”€ public/                      # Static assets
β”‚   └── icons/                   # App icons
β”‚
β”œβ”€β”€ .env.example                 # Environment template
β”œβ”€β”€ tailwind.config.ts           # Tailwind configuration
β”œβ”€β”€ tsconfig.json                # TypeScript config
└── package.json

Key Directories

/app - Pages and API Routes

The app/ directory uses Next.js App Router conventions:
  • page.tsx files define route pages
  • layout.tsx files define shared layouts
  • api/ contains server-side API route handlers

/components - Reusable Components

Components are organized by scope:
  • Root level: App-wide components (Header, TTAIIframe)
  • auth/: Authentication-related components
  • ui/: shadcn/ui primitive components

/lib - Utilities and Configuration

Core application logic:
  • config.ts: Centralized environment variables
  • constants.ts: App-wide constants and MBTI data
  • store.ts: Zustand state management
  • ttai/: ToughTongue AI integration module

Key Files Explained

lib/config.ts

Centralizes all environment configuration:
export const AppConfig = {
  app: {
    name: "Discover Your Personality",
    shortName: "Personality",
    description: "AI-powered personality assessment",
  },
  ttai: {
    apiKey: process.env.TOUGH_TONGUE_API_KEY,
    baseUrl: "https://app.toughtongueai.com",
    apiBaseUrl: "https://api.toughtongueai.com/api/public",
  },
  firebase: {
    // Firebase config from env vars
  },
  isDev: process.env.NEXT_PUBLIC_IS_DEV === "true",
};

lib/constants.ts

Contains routes and static data:
export const ROUTES = {
  HOME: "/",
  TEST: "/test",
  RESULTS: "/results",
  COACH: "/coach",
  ADMIN: "/admin",
} as const;

export const MBTI_TYPES = [
  { type: "INTJ", name: "The Architect", ... },
  // ... all 16 types
];

lib/store.ts

Zustand store with localStorage persistence:
export const useAppStore = create<AppState>()(
  persist(
    (set, get) => ({
      user: null,
      assessmentSessions: [],
      coachSessions: [],
      sessionDetails: {},
      // ... actions
    }),
    { name: "ttai-app-store" }
  )
);

lib/ttai/

ToughTongue integration module - see ToughTongue Integration.

Adding New Features

Adding a New Page

  1. Create directory in app/:
app/my-feature/page.tsx
  1. Add route to lib/constants.ts:
export const ROUTES = {
  // ...existing routes
  MY_FEATURE: "/my-feature",
} as const;
  1. Add navigation link in components/Header.tsx

Adding a New Component

  • Shared component: Add to components/
  • Feature-specific: Keep in the feature’s directory
  • UI primitive: Add to components/ui/ using shadcn/ui patterns

Adding a New API Route

Create route handler in app/api/:
// app/api/my-endpoint/route.ts
import { NextResponse } from "next/server";

export async function GET() {
  // Your logic
  return NextResponse.json({ data: "..." });
}

Next Steps

ToughTongue Integration

Learn the integration patterns

State & Auth

State management and authentication