Skip to main content

Overview

EpiNeko follows the Next.js 15 App Router structure with a clean separation of concerns. The project uses TypeScript, React 19, and integrates with Supabase for authentication and data persistence.

Technology Stack

Next.js 16

Modern React framework with App Router

React 19

Latest React with Server Components

TypeScript 5

Type-safe development

Tailwind CSS 4

Utility-first styling with DaisyUI

Directory Structure

src/
├── app/                    # Next.js App Router pages
│   ├── layout.tsx         # Root layout with metadata
│   ├── page.tsx           # Homepage
│   ├── globals.css        # Global styles
│   ├── icon.png           # App icon
│   ├── anime/
│   │   └── [id]/          # Dynamic anime detail pages
│   ├── library/           # User's anime library
│   ├── login/             # Authentication pages
│   ├── signup/
│   ├── profile/           # User profile
│   ├── settings/          # User settings
│   ├── error/             # Error page
│   └── api/               # API routes
│       └── check-username/
├── components/            # Reusable React components
│   ├── anime/            # Anime-specific components
│   │   ├── AnimeCard.tsx
│   │   ├── AnimeDetailsModal.tsx
│   │   ├── EpisodeList.tsx
│   │   ├── LibraryButton.tsx
│   │   └── SearchBar.tsx
│   └── layout/           # Layout components
│       ├── MainLayout.tsx
│       ├── Navbar.tsx
│       └── Footer.tsx
├── services/             # External API integrations
│   ├── jikan.ts         # Jikan API (MyAnimeList)
│   └── library.ts       # Library management
├── utils/                # Utility functions
│   └── supabase/        # Supabase client utilities
│       ├── client.ts    # Browser client
│       ├── server.ts    # Server client
│       └── middleware.ts # Auth middleware
└── middleware.ts         # Next.js middleware

Key Directories Explained

The app directory contains all pages and layouts following Next.js 15 App Router conventions:
  • layout.tsx: Root layout with metadata and font configuration
  • page.tsx: Homepage with trending anime
  • anime/[id]/: Dynamic routes for individual anime details
  • api/: Server-side API endpoints
All pages use Server Components by default, with "use client" directive for client-side interactivity.
Organized by feature area:
  • anime/: Components specific to anime display and interaction
  • layout/: Structural components like Navbar and Footer
All components are client-side ("use client") for interactivity.
Service layer for external API calls:
  • jikan.ts: Fetches anime data from Jikan API v4 (MyAnimeList)
  • library.ts: Manages user library with Supabase
Services handle data fetching, caching, and error handling.
Helper functions and configurations:
  • supabase/: Three specialized Supabase clients for different contexts
    • client.ts: Browser-side authentication
    • server.ts: Server-side operations
    • middleware.ts: Session management in middleware

Next.js Configuration

The project uses custom Next.js configuration in next.config.ts:
next.config.ts
import type { NextConfig } from "next";

const nextConfig: NextConfig = {
  images: {
    remotePatterns: [
      {
        protocol: 'https',
        hostname: 'cdn.myanimelist.net',
        port: '',
        pathname: '/**',
      },
    ],
  },
};

export default nextConfig;
Remote image patterns are configured to allow MyAnimeList CDN images for anime posters and covers.

TypeScript Configuration

Key compiler options from tsconfig.json:
{
  "compilerOptions": {
    "target": "ES2017",
    "lib": ["dom", "dom.iterable", "esnext"],
    "strict": true,
    "paths": {
      "@/*": ["./src/*"]
    }
  }
}
The @/* path alias allows clean imports from the src directory.

Middleware

The root middleware.ts handles authentication for protected routes:
src/middleware.ts
import { type NextRequest } from 'next/server'
import { updateSession } from '@/utils/supabase/middleware'

export async function middleware(request: NextRequest) {
  return await updateSession(request)
}

export const config = {
  matcher: [
    '/((?!_next/static|_next/image|favicon.ico|.*\\.(?:svg|png|jpg|jpeg|gif|webp)$).*)',
  ],
}
The matcher excludes static files and images to prevent unnecessary authentication checks on public assets.

Styling Approach

1

Tailwind CSS 4

Utility-first CSS framework for rapid UI development
2

DaisyUI Components

Pre-built component classes for buttons, cards, and more
3

Custom Design System

Dark theme with zinc colors and primary accent

Best Practices

Server Components First

Use Server Components by default for better performance

Client Components for Interactivity

Add "use client" only when needed for state/events

Path Aliases

Always use @/ imports for cleaner code

Type Safety

Leverage TypeScript interfaces for all data structures

Next Steps

Components

Explore React components

Services

Learn about API services

Deployment

Deploy your instance