---
title: "Whitelabel Navigation"
description: "Developer guide to implementing custom navigation components for Ring Platform clones"
locale: "en"
---
# Whitelabel Navigation System

> **Info**
> **Time Estimate**: 30 minutes | **Difficulty**: Intermediate | **Prerequisites**: Understanding of React components and Ring Platform structure

Ring Platform uses a clean whitelabel navigation architecture that automatically selects the correct navigation variant based on project configuration. This guide explains how to create custom navigation components for your Ring clone.

## Architecture Overview

```mermaid
flowchart TD
    A[Layout renders Navigation] --> B[navigation.tsx]
    B --> C[DesktopNavigation]
    C --> D{Read config}
    D -->|default| E[desktop-sidebar.tsx]
    D -->|vikka| F[vikka-desktop-navigation.tsx]
    D -->|greenfood| G[greenfood-navigation.tsx]
    
    style C fill:#10b981
    style D fill:#f59e0b
```

The system separates the **public API** (`DesktopNavigation`) from **variant implementations** (project-specific navigation components). Wrapper components always import the public API, never the variants directly.

## File Structure

```
components/navigation/
├── desktop-navigation.tsx    ← PUBLIC API (import this everywhere)
├── desktop-sidebar.tsx       ← Default Ring Platform variant
├── vikka-desktop-navigation.tsx  ← VIKKA News variant
├── navigation.tsx            ← Orchestrator component
└── bottom-navigation.tsx     ← Mobile navigation

config/
└── navigation.config.ts      ← Client-safe configuration
```

> **Warning**
> **Important**: Never import `desktop-sidebar.tsx` or project-specific navigation directly. Always use `DesktopNavigation` from `desktop-navigation.tsx`.

## Configuration

### Navigation Config File

Create or edit `config/navigation.config.ts`:

{`/**
 * Navigation Configuration for Whitelabel
 * Client-safe configuration for navigation components.
 */

export type NavigationComponentType = 'default' | 'vikka' | 'greenfood'

export const navigationConfig = {
  /**
   * Desktop navigation component to use
   * - 'default': Standard Ring Platform sidebar
   * - 'vikka': VIKKA News portal navigation
   * - 'greenfood': GreenFood marketplace navigation
   */
  desktopComponent: 'default' as NavigationComponentType,
  
  /**
   * Mobile navigation component to use
   */
  mobileComponent: 'default' as NavigationComponentType,
} as const

export function getDesktopNavigationType(): NavigationComponentType {
  return navigationConfig.desktopComponent
}`}

### Instance Config (Optional)

For full whitelabel configuration, create `whitelabel/instance.config.json`:

{`{
  "$schema": "./instance.config.schema.json",
  "name": "My Platform",
  "brand": {
    "colors": {
      "primary": "#3b82f6",
      "background": "#0f172a",
      "foreground": "#f8fafc",
      "accent": "#22c55e"
    }
  },
  "navigation": {
    "desktopComponent": "default",
    "mobileComponent": "default"
  },
  "features": {
    "entities": true,
    "opportunities": true
  }
}`}

## Creating a Custom Navigation Variant

**Create your navigation component:**

Create a new file in `components/navigation/` with your project name:

{`'use client'

import React, { useState, useEffect } from 'react'
import Link from 'next/link'
import { usePathname } from 'next/navigation'
import { useLocale } from 'next-intl'
import { useTheme } from 'next-themes'
import { useSession } from 'next-auth/react'
import { Home, Settings, User } from 'lucide-react'
import type { Locale } from '@/i18n-config'

interface MyProjectDesktopNavigationProps {
  className?: string
}

export default function MyProjectDesktopNavigation({ 
  className 
}: MyProjectDesktopNavigationProps) {
  const pathname = usePathname()
  const locale = useLocale() as Locale
  const { data: session } = useSession()
  const { theme, setTheme } = useTheme()

  const navigationItems = [
    { href: \`/\${locale}\`, label: 'Home', icon: Home },
    { href: \`/\${locale}/settings\`, label: 'Settings', icon: Settings },
    // Add your custom navigation items
  ]

  return (
    
      {/* Your custom navigation UI */}
      
        My Platform
      
      
      
        {navigationItems.map((item) => (
          
            
            {item.label}
          
        ))}
      
    
  )
}`}

**Register your variant in `desktop-navigation.tsx`:**

{`import React from 'react'
import dynamic from 'next/dynamic'
import { navigationConfig, type NavigationComponentType } from '@/config/navigation.config'

// Lazy load navigation variants
const DefaultSidebar = dynamic(
  () => import('@/components/navigation/desktop-sidebar'),
  { ssr: false }
)

const VikkaSidebar = dynamic(
  () => import('@/components/navigation/vikka-desktop-navigation'),
  { ssr: false }
)

// Add your new variant
const MyProjectSidebar = dynamic(
  () => import('@/components/navigation/myproject-desktop-navigation'),
  { ssr: false }
)

// Component registry
const variants: Record<NavigationComponentType, React.ComponentType<{ className?: string }>> = {
  default: DefaultSidebar,
  vikka: VikkaSidebar,
  myproject: MyProjectSidebar, // Register here
}

export default function DesktopNavigation({ className }: { className?: string }) {
  const Variant = variants[navigationConfig.desktopComponent] || DefaultSidebar
  return 
}`}

**Update the type definition:**

Add your variant to the type in `config/navigation.config.ts`:

{`export type NavigationComponentType = 'default' | 'vikka' | 'greenfood' | 'myproject'`}

**Activate your variant:**

Set your project's navigation in the config:

{`export const navigationConfig = {
  desktopComponent: 'myproject' as NavigationComponentType,
  mobileComponent: 'default' as NavigationComponentType,
} as const`}

## Using Navigation in Wrapper Components

All page wrapper components should import `DesktopNavigation`:

{`'use client'

import React from 'react'
import DesktopNavigation from '@/components/navigation/desktop-navigation'
import RightSidebar from '@/components/layout/right-sidebar'

interface MyPageWrapperProps {
  children: React.ReactNode
}

export default function MyPageWrapper({ children }: MyPageWrapperProps) {
  return (
    
      {/* Desktop Layout */}
      
        
        {children}
        
          {/* Sidebar content */}
        
      

      {/* Mobile Layout */}
      
        {children}
      
    
  )
}`}

## Mobile Navigation

Mobile navigation is handled separately by `bottom-navigation.tsx`. The same whitelabel pattern can be applied:

{`export const navigationConfig = {
  desktopComponent: 'vikka' as NavigationComponentType,
  mobileComponent: 'default' as NavigationComponentType,  // Can also be customized
}`}

> **Info**
> The mobile `BottomNavigation` component includes a fullscreen menu modal with conditional Admin section (visible only for admin/superadmin roles).

## Best Practices

### ✅ Do

- Always import from `@/components/navigation/desktop-navigation`
- Keep navigation config in `config/navigation.config.ts`
- Use `dynamic()` imports for navigation variants (code splitting)
- Include all localization support in your variant
- Support light/dark themes

### ❌ Don't

- Never import `desktop-sidebar.tsx` directly in wrappers
- Don't hardcode locale paths - use `useLocale()` hook
- Don't skip theme support - Ring supports dark mode
- Don't forget mobile navigation consideration

## Migrating Existing Code

If your codebase has direct `desktop-sidebar` imports:

{`# Find all files with direct imports
grep -r "import.*desktop-sidebar" --include="*.tsx" .

# Replace import (use sed or your IDE)
# FROM: import DesktopSidebar from '@/components/navigation/desktop-sidebar'
# TO:   import DesktopNavigation from '@/components/navigation/desktop-navigation'

# Also update component usage
# FROM: 
# TO:   `}

## Example: VIKKA News Navigation

VIKKA (`ring-vikka-ua`) uses a custom navigation optimized for news portals:

```mermaid
mindmap
  root((VIKKA Nav))
    Branding
      Logo & Tagline
      Social Links
      Footer Info
    Categories
      News Categories
      Live TV
      Shows
    User Features
      Auth Widget
      Theme Toggle
      Language Switcher
    Business
      Advertising
      Jobs
      Production
```

---

## Next Steps

> **Success**
> Your navigation system is now whitelabel-ready! Explore more customization options:

- [Complete Customization Guide](/en/docs/customization/customization-guide) - Full branding and feature customization
- [Code Structure](/en/docs/development/code-structure) - Understanding Ring's architecture
- [Best Practices](/en/docs/development/best-practices) - Coding standards

---

> **Note**
> **Legiox Commander Tip**: The whitelabel navigation system was designed to keep the codebase clean and project customizations separate. When in doubt, remember: *components import the public API, never the variants directly*.
