Signed-off-by: mbrucedogs <mbrucedogs@gmail.com>
2627
docs/PRD-backup.md
Normal file
2795
docs/PRD.md
@ -17,7 +17,7 @@ These files are intended for:
|
||||
| `PRD.md` | **Complete Product Requirements Document** — platform-agnostic business logic, technical specifications, data flows, service APIs, component architecture, error handling, and performance optimizations. **Self-guiding for AI implementation.** |
|
||||
| `types.ts` | Reference TypeScript interfaces used for modeling app objects. **Not imported into app runtime code.** |
|
||||
| `firebase_schema.json` | Example Firebase Realtime Database structure for understanding data relationships and CRUD operations. |
|
||||
| `design/` | **UI/UX Design Assets** — mockups and visual references for different platforms and features. |
|
||||
| `platforms/web/design/` | **Web UI/UX Design Assets** — mockups and visual references for web platform features. |
|
||||
|
||||
---
|
||||
|
||||
@ -38,7 +38,7 @@ Simply say **"Read this PRD"** in any new chat. The PRD contains:
|
||||
|
||||
### **For New Implementations:**
|
||||
1. **Read the PRD completely** - it contains comprehensive specifications
|
||||
2. **Review design assets** in `design/` folder for visual reference
|
||||
2. **Review design assets** in `platforms/web/design/` folder for visual reference
|
||||
3. **Answer implementation questions** from Section 29
|
||||
4. **Follow the implementation checklist** for complete build process
|
||||
5. **Preserve business logic** while adapting UI to chosen framework
|
||||
@ -48,24 +48,24 @@ Simply say **"Read this PRD"** in any new chat. The PRD contains:
|
||||
## 📋 Key Features of the Updated PRD
|
||||
|
||||
### **Platform-Agnostic Design:**
|
||||
- **Core requirements** separated from implementation details
|
||||
- **Framework-specific sections** clearly marked
|
||||
- **Migration guidance** for different platforms
|
||||
- **Toolset rationale** for informed technology choices
|
||||
- **Core business logic** completely separated from implementation details
|
||||
- **Firebase architecture** and data models for any platform
|
||||
- **Cross-platform references** to platform-specific PRDs
|
||||
- **Universal business rules** that apply to all implementations
|
||||
|
||||
### **Complete Technical Specifications:**
|
||||
- **Data flow diagrams** for all operations
|
||||
- **State management architecture** with exact structure
|
||||
- **Service layer APIs** with function signatures
|
||||
- **Component architecture** with interfaces and behavior
|
||||
- **Error handling matrix** for all scenarios
|
||||
- **Performance specifications** with optimization patterns
|
||||
- **Firebase data structure** and relationships
|
||||
- **Business logic patterns** and validation rules
|
||||
- **Real-time synchronization** requirements
|
||||
- **User role permissions** and access control
|
||||
- **Error handling scenarios** and recovery patterns
|
||||
- **Performance requirements** and optimization guidelines
|
||||
|
||||
### **Implementation Guide:**
|
||||
- **7 key questions** to determine platform/framework
|
||||
- **5-phase implementation checklist**
|
||||
- **Must preserve vs. can replace** guidelines
|
||||
- **Critical success factors** for accurate builds
|
||||
- **Platform selection questions** to determine technology stack
|
||||
- **5-phase implementation checklist** for complete builds
|
||||
- **Business logic preservation** guidelines
|
||||
- **Critical success factors** for accurate implementations
|
||||
|
||||
### **Design Assets:**
|
||||
- **Visual mockups** for all major features and screens
|
||||
@ -110,8 +110,8 @@ Simply say **"Read this PRD"** in any new chat. The PRD contains:
|
||||
|
||||
## 🎨 Design Assets Reference
|
||||
|
||||
### **Current Design Assets:**
|
||||
Located in `design/web/` folder with comprehensive mockups for all features:
|
||||
### **Current Web Design Assets:**
|
||||
Located in `platforms/web/design/` folder with comprehensive mockups for all features:
|
||||
|
||||
#### **Core Navigation & Layout:**
|
||||
- `00-web-layout.JPG` - Overall web layout structure
|
||||
@ -159,12 +159,17 @@ Located in `design/web/` folder with comprehensive mockups for all features:
|
||||
|
||||
### **Future Platform Design Structure:**
|
||||
```
|
||||
design/
|
||||
├── web/ # Current web mockups
|
||||
├── ios/ # Future iOS designs
|
||||
├── android/ # Future Android designs
|
||||
├── tablet/ # Future tablet designs
|
||||
└── desktop/ # Future desktop designs
|
||||
docs/platforms/
|
||||
├── web/
|
||||
│ └── design/ # Current web mockups
|
||||
├── ios/
|
||||
│ └── design/ # Future iOS designs
|
||||
├── android/
|
||||
│ └── design/ # Future Android designs
|
||||
├── tablet/
|
||||
│ └── design/ # Future tablet designs
|
||||
└── desktop/
|
||||
└── design/ # Future desktop designs
|
||||
```
|
||||
|
||||
### **Using Design Assets:**
|
||||
|
||||
759
docs/platforms/web/PRD-web.md
Normal file
@ -0,0 +1,759 @@
|
||||
# Web Platform Implementation Guide
|
||||
|
||||
> **Platform:** Web (React + Ionic + TypeScript)
|
||||
> **Core Business Logic:** See `../../PRD.md` for platform-agnostic requirements
|
||||
|
||||
This document contains **web-specific implementation details** for the Karaoke App. All business logic, data models, and core requirements are defined in the main PRD.
|
||||
|
||||
---
|
||||
|
||||
## Quick Reference
|
||||
|
||||
| Section | Purpose |
|
||||
|---------|---------|
|
||||
| [UI/UX Behavior](#uiux-behavior) | Web-specific UI patterns and interactions |
|
||||
| [Component Architecture](#component-architecture) | React/Ionic component structure |
|
||||
| [State Management](#state-management) | Redux Toolkit implementation |
|
||||
| [Development Setup](#development-setup) | Web project configuration |
|
||||
| [Design Assets](#design-assets) | Web-specific visual references |
|
||||
| [Toolset Choices](#toolset-choices) | Web technology rationale |
|
||||
|
||||
---
|
||||
|
||||
## UI/UX Behavior
|
||||
|
||||
### **Web-Specific Requirements:**
|
||||
|
||||
#### **Responsive Design:**
|
||||
- **Mobile-first approach** with touch-friendly interface
|
||||
- **Progressive Web App (PWA)** capabilities for app-like experience
|
||||
- **Responsive breakpoints** for tablet and desktop views
|
||||
- **Touch gestures** for queue reordering and navigation
|
||||
|
||||
#### **Ionic React Components:**
|
||||
- **IonApp** as root container with proper theming
|
||||
- **IonRouterOutlet** for navigation between pages
|
||||
- **IonList** and **IonItem** for song and queue displays
|
||||
- **IonButton** with proper touch targets (44px minimum)
|
||||
- **IonSearchbar** for song search with debounced input
|
||||
- **IonModal** for singer selection and settings
|
||||
- **IonToast** for user feedback and notifications
|
||||
|
||||
#### **Navigation Patterns:**
|
||||
- **Tab-based navigation** for main sections (Queue, Search, History, etc.)
|
||||
- **Stack navigation** for detail views (song info, artist pages)
|
||||
- **Modal overlays** for quick actions (singer selection, settings)
|
||||
- **Deep linking** support for direct page access
|
||||
|
||||
#### **Real-time Updates:**
|
||||
- **Live queue updates** with visual indicators for changes
|
||||
- **Playback state synchronization** across all connected devices
|
||||
- **User presence indicators** showing who's currently active
|
||||
- **Optimistic UI updates** with rollback on errors
|
||||
|
||||
---
|
||||
|
||||
## Codebase Organization & File Structure
|
||||
|
||||
### **Web Project Structure:**
|
||||
```
|
||||
src/
|
||||
├── components/ # Reusable UI components
|
||||
│ ├── Auth/ # Authentication components
|
||||
│ ├── common/ # Shared components (SongItem, ActionButton, etc.)
|
||||
│ ├── Layout/ # Layout and navigation components
|
||||
│ └── Navigation/ # Navigation components
|
||||
├── features/ # Feature-specific components
|
||||
│ ├── Artists/ # Artist browsing feature
|
||||
│ ├── Favorites/ # Favorites management
|
||||
│ ├── History/ # Play history
|
||||
│ ├── NewSongs/ # New songs feature
|
||||
│ ├── Queue/ # Queue management
|
||||
│ ├── Search/ # Song search
|
||||
│ ├── Settings/ # Settings and admin features
|
||||
│ ├── Singers/ # Singer management
|
||||
│ ├── SongLists/ # Song lists feature
|
||||
│ └── TopPlayed/ # Top played songs
|
||||
├── firebase/ # Firebase configuration and services
|
||||
│ ├── config.ts # Firebase configuration
|
||||
│ ├── services.ts # Firebase service layer
|
||||
│ └── useFirebase.ts # Firebase hooks
|
||||
├── hooks/ # Custom React hooks
|
||||
│ ├── useQueue.ts # Queue management hooks
|
||||
│ ├── useSearch.ts # Search functionality hooks
|
||||
│ ├── useFavorites.ts # Favorites management hooks
|
||||
│ └── ... # Other feature hooks
|
||||
├── redux/ # State management
|
||||
│ ├── store.ts # Redux store configuration
|
||||
│ ├── slices/ # Redux slices
|
||||
│ ├── selectors.ts # Memoized selectors
|
||||
│ └── hooks.ts # Redux hooks
|
||||
├── types/ # TypeScript type definitions
|
||||
└── utils/ # Utility functions
|
||||
```
|
||||
|
||||
### **File Organization Rules:**
|
||||
| Folder | Purpose | Key Files | Import Pattern |
|
||||
|--------|---------|-----------|----------------|
|
||||
| `/components` | Reusable UI components | `SongItem.tsx`, `ActionButton.tsx` | `import { SongItem } from '../components/common'` |
|
||||
| `/features` | Feature-specific pages | `Queue.tsx`, `Search.tsx` | `import { Queue } from '../features/Queue'` |
|
||||
| `/firebase` | Firebase integration | `services.ts`, `config.ts` | `import { queueService } from '../firebase/services'` |
|
||||
| `/hooks` | Custom business logic | `useQueue.ts`, `useSearch.ts` | `import { useQueue } from '../hooks/useQueue'` |
|
||||
| `/redux` | State management | `controllerSlice.ts`, `authSlice.ts`, `selectors.ts` | `import { useAppDispatch, selectQueue } from '../redux'` |
|
||||
| `/types` | TypeScript definitions | `index.ts` (extends docs/types.ts) | `import type { Song, QueueItem } from '../types'` |
|
||||
|
||||
### **Import Patterns:**
|
||||
|
||||
#### **1. Redux Imports:**
|
||||
```typescript
|
||||
// Always import from the main redux index
|
||||
import { useAppDispatch, useAppSelector } from '../redux';
|
||||
import { selectQueue, selectSongs } from '../redux';
|
||||
import { setController, updateQueue } from '../redux';
|
||||
|
||||
// ❌ Don't import directly from slice files
|
||||
// ❌ import { selectQueue } from '../redux/controllerSlice';
|
||||
// ✅ Always use the main redux index
|
||||
// ✅ import { selectQueue } from '../redux';
|
||||
```
|
||||
|
||||
#### **2. Firebase Service Imports:**
|
||||
```typescript
|
||||
// Import services from the main services file
|
||||
import { queueService, searchService } from '../firebase/services';
|
||||
|
||||
// ❌ Don't import directly from individual service files
|
||||
// ❌ import { addToQueue } from '../firebase/queueService';
|
||||
// ✅ Always use the main services file
|
||||
// ✅ import { queueService } from '../firebase/services';
|
||||
```
|
||||
|
||||
#### **3. Type Imports:**
|
||||
```typescript
|
||||
// Always use type imports for TypeScript interfaces
|
||||
import type { Song, QueueItem, Singer } from '../types';
|
||||
|
||||
// ❌ Don't import types from individual files
|
||||
// ❌ import { Song } from '../types/Song';
|
||||
// ✅ Always use the main types index
|
||||
// ✅ import type { Song } from '../types';
|
||||
```
|
||||
|
||||
#### **4. Hook Imports:**
|
||||
```typescript
|
||||
// Import hooks from their specific files
|
||||
import { useQueue } from '../hooks/useQueue';
|
||||
import { useSearch } from '../hooks/useSearch';
|
||||
import { useFavorites } from '../hooks/useFavorites';
|
||||
|
||||
// ❌ Don't import from a general hooks index
|
||||
// ❌ import { useQueue } from '../hooks';
|
||||
// ✅ Import from specific hook files
|
||||
// ✅ import { useQueue } from '../hooks/useQueue';
|
||||
```
|
||||
|
||||
#### **5. Component Imports:**
|
||||
```typescript
|
||||
// Import components from their specific folders
|
||||
import { SongItem } from '../components/common/SongItem';
|
||||
import { ActionButton } from '../components/common/ActionButton';
|
||||
import { Layout } from '../components/Layout/Layout';
|
||||
|
||||
// ❌ Don't import from general component indices
|
||||
// ❌ import { SongItem } from '../components';
|
||||
// ✅ Import from specific component files
|
||||
// ✅ import { SongItem } from '../components/common/SongItem';
|
||||
```
|
||||
|
||||
### **Architecture Flow:**
|
||||
```
|
||||
UI Components → Custom Hooks → Redux State → Firebase Services → Firebase Database
|
||||
```
|
||||
|
||||
### **Separation of Concerns:**
|
||||
- **Components:** Only handle UI presentation and user interactions
|
||||
- **Hooks:** Contain business logic and data management
|
||||
- **Redux:** Manage global application state
|
||||
- **Services:** Handle Firebase operations and data persistence
|
||||
- **Types:** Define data structures and interfaces
|
||||
|
||||
## Component Architecture
|
||||
|
||||
### **React Component Structure:**
|
||||
|
||||
#### **Page Components:**
|
||||
```typescript
|
||||
// src/features/Queue/Queue.tsx
|
||||
interface QueueProps {
|
||||
// Props interface
|
||||
}
|
||||
|
||||
const Queue: React.FC<QueueProps> = () => {
|
||||
// Component implementation
|
||||
}
|
||||
```
|
||||
|
||||
#### **Common Components:**
|
||||
```typescript
|
||||
// src/components/common/SongItem.tsx
|
||||
interface SongItemProps {
|
||||
song: Song;
|
||||
onAddToQueue: (song: Song) => void;
|
||||
onAddToFavorites: (song: Song) => void;
|
||||
showAddButton?: boolean;
|
||||
showFavoriteButton?: boolean;
|
||||
}
|
||||
```
|
||||
|
||||
#### **Layout Components:**
|
||||
```typescript
|
||||
// src/components/Layout/Layout.tsx
|
||||
interface LayoutProps {
|
||||
children: React.ReactNode;
|
||||
title?: string;
|
||||
showBackButton?: boolean;
|
||||
}
|
||||
```
|
||||
|
||||
### **Ionic Integration:**
|
||||
- **IonPage** wrapper for all page components
|
||||
- **IonHeader** with dynamic titles and action buttons
|
||||
- **IonContent** with proper scrolling behavior
|
||||
- **IonFooter** for player controls and queue management
|
||||
- **IonLoading** for async operations and data fetching
|
||||
|
||||
---
|
||||
|
||||
## State Management
|
||||
|
||||
### **Redux Architecture Pattern:**
|
||||
The web implementation uses Redux Toolkit for predictable state management with excellent TypeScript support.
|
||||
|
||||
#### **Store Structure:**
|
||||
```typescript
|
||||
// src/redux/store.ts
|
||||
export const store = configureStore({
|
||||
reducer: {
|
||||
auth: authSlice,
|
||||
player: playerSlice,
|
||||
queue: queueSlice,
|
||||
controller: controllerSlice,
|
||||
},
|
||||
middleware: (getDefaultMiddleware) =>
|
||||
getDefaultMiddleware({
|
||||
serializableCheck: {
|
||||
ignoredActions: ['persist/PERSIST'],
|
||||
},
|
||||
}),
|
||||
});
|
||||
```
|
||||
|
||||
#### **Slice Patterns:**
|
||||
```typescript
|
||||
// src/redux/controllerSlice.ts
|
||||
const controllerSlice = createSlice({
|
||||
name: 'controller',
|
||||
initialState,
|
||||
reducers: {
|
||||
setController: (state, action) => {
|
||||
state.data = action.payload;
|
||||
},
|
||||
updateQueue: (state, action) => {
|
||||
state.data.player.queue = action.payload;
|
||||
},
|
||||
},
|
||||
});
|
||||
```
|
||||
|
||||
#### **Selectors:**
|
||||
```typescript
|
||||
// src/redux/selectors.ts
|
||||
export const selectQueue = (state: RootState) => state.controller.data?.player?.queue || {};
|
||||
export const selectQueueLength = createSelector(
|
||||
[selectQueue],
|
||||
(queue) => Object.keys(queue).length
|
||||
);
|
||||
```
|
||||
|
||||
### **Redux Toolkit Implementation:**
|
||||
|
||||
#### **Store Structure:**
|
||||
```typescript
|
||||
// src/redux/store.ts
|
||||
export const store = configureStore({
|
||||
reducer: {
|
||||
auth: authSlice,
|
||||
player: playerSlice,
|
||||
queue: queueSlice,
|
||||
controller: controllerSlice,
|
||||
},
|
||||
middleware: (getDefaultMiddleware) =>
|
||||
getDefaultMiddleware({
|
||||
serializableCheck: {
|
||||
ignoredActions: ['persist/PERSIST'],
|
||||
},
|
||||
}),
|
||||
});
|
||||
```
|
||||
|
||||
#### **Slice Patterns:**
|
||||
```typescript
|
||||
// src/redux/queueSlice.ts
|
||||
const queueSlice = createSlice({
|
||||
name: 'queue',
|
||||
initialState,
|
||||
reducers: {
|
||||
addToQueue: (state, action) => {
|
||||
// Implementation
|
||||
},
|
||||
removeFromQueue: (state, action) => {
|
||||
// Implementation
|
||||
},
|
||||
},
|
||||
});
|
||||
```
|
||||
|
||||
#### **Selectors:**
|
||||
```typescript
|
||||
// src/redux/selectors.ts
|
||||
export const selectQueue = (state: RootState) => state.queue.items;
|
||||
export const selectQueueLength = createSelector(
|
||||
[selectQueue],
|
||||
(queue) => queue.length
|
||||
);
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Development Setup
|
||||
|
||||
### **Project Configuration:**
|
||||
|
||||
#### **Package.json Dependencies:**
|
||||
```json
|
||||
{
|
||||
"dependencies": {
|
||||
"@ionic/react": "^7.0.0",
|
||||
"@reduxjs/toolkit": "^1.9.0",
|
||||
"react": "^18.2.0",
|
||||
"react-dom": "^18.2.0",
|
||||
"react-redux": "^8.0.0",
|
||||
"firebase": "^9.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@types/react": "^18.0.0",
|
||||
"@types/react-dom": "^18.0.0",
|
||||
"typescript": "^4.9.0",
|
||||
"vite": "^4.0.0"
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
#### **Vite Configuration:**
|
||||
```typescript
|
||||
// vite.config.ts
|
||||
export default defineConfig({
|
||||
plugins: [react()],
|
||||
resolve: {
|
||||
alias: {
|
||||
'@': path.resolve(__dirname, './src'),
|
||||
},
|
||||
},
|
||||
build: {
|
||||
outDir: 'dist',
|
||||
sourcemap: true,
|
||||
},
|
||||
});
|
||||
```
|
||||
|
||||
#### **TypeScript Configuration:**
|
||||
```json
|
||||
// tsconfig.json
|
||||
{
|
||||
"compilerOptions": {
|
||||
"target": "ES2020",
|
||||
"lib": ["ES2020", "DOM", "DOM.Iterable"],
|
||||
"module": "ESNext",
|
||||
"skipLibCheck": true,
|
||||
"moduleResolution": "bundler",
|
||||
"allowImportingTsExtensions": true,
|
||||
"resolveJsonModule": true,
|
||||
"isolatedModules": true,
|
||||
"noEmit": true,
|
||||
"jsx": "react-jsx",
|
||||
"strict": true,
|
||||
"noUnusedLocals": true,
|
||||
"noUnusedParameters": true,
|
||||
"noFallthroughCasesInSwitch": true
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### **Environment Setup:**
|
||||
```bash
|
||||
# .env.local
|
||||
VITE_FIREBASE_API_KEY=your_api_key
|
||||
VITE_FIREBASE_AUTH_DOMAIN=your_project.firebaseapp.com
|
||||
VITE_FIREBASE_PROJECT_ID=your_project_id
|
||||
VITE_FIREBASE_STORAGE_BUCKET=your_project.appspot.com
|
||||
VITE_FIREBASE_MESSAGING_SENDER_ID=your_sender_id
|
||||
VITE_FIREBASE_APP_ID=your_app_id
|
||||
VITE_FIREBASE_DATABASE_URL=https://your_project-default-rtdb.firebaseio.com
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Design Assets
|
||||
|
||||
### **Web-Specific Mockups:**
|
||||
Located in `design/` with 30+ mockups covering all features:
|
||||
|
||||
#### **Core Navigation & Layout:**
|
||||
- `00-web-layout.JPG` - Overall web layout structure
|
||||
- `01-Login.png` - Login screen design
|
||||
- `02-menu.jpeg`, `02a-menu.jpeg`, `02b-menu.png`, `02c-menu.jpeg` - Navigation menu variations
|
||||
|
||||
#### **Queue Management:**
|
||||
- `02-queue.png` - Main queue view
|
||||
- `02-queue-delete.png` - Queue with delete functionality
|
||||
- `02-queue-drag.png` - Queue reordering with drag and drop
|
||||
- `02-queue-sorting.png` - Queue sorting interface
|
||||
|
||||
#### **Search & Discovery:**
|
||||
- `04-search.png` - Main search interface
|
||||
- `04-search typing .png` - Search with typing interaction
|
||||
- `04-search-song info.png` - Search results with song information
|
||||
|
||||
#### **User Management:**
|
||||
- `05-singers.png` - Singer list view
|
||||
- `05-singers add.png` - Singer management interface
|
||||
|
||||
#### **Content Browsing:**
|
||||
- `06-artists .png` - Artist browse interface
|
||||
- `06-artists (not admin).png` - Non-admin artist view
|
||||
- `06-artists search.png` - Artist search functionality
|
||||
- `06-artists songs.png` - Artist songs list
|
||||
|
||||
#### **User Features:**
|
||||
- `07-favorites.png` - Favorites management
|
||||
- `08-history.png` - Play history view
|
||||
- `09-songs list.png` - Main song lists view
|
||||
- `09-song lists - songs.png` - Song lists with song details
|
||||
- `09- song lists songs expand.png` - Song lists with expandable sections
|
||||
|
||||
#### **Admin Features:**
|
||||
- `10-Settings.png` - Settings interface
|
||||
- `11-top 100.png` - Top played songs
|
||||
- `12-favorites .png` - Favorites view
|
||||
- `12-favorite lists.png` - Favorite lists management
|
||||
|
||||
#### **Menu States:**
|
||||
- `03-menu.png` - General menu layout
|
||||
- `03-menu current page and non-admin.png` - Navigation with current page indicators
|
||||
- `03-menu playing (admin).png` - Admin view during playback
|
||||
|
||||
### **Design System:**
|
||||
- **Ionic Design System** for consistent UI components
|
||||
- **Custom CSS variables** for theming and branding
|
||||
- **Responsive grid system** for layout consistency
|
||||
- **Touch-friendly spacing** and sizing guidelines
|
||||
|
||||
---
|
||||
|
||||
## Toolset Choices
|
||||
|
||||
### **Current Web Implementation Toolset:**
|
||||
|
||||
#### **Core Framework: React 18 + TypeScript**
|
||||
- **Why:** Chosen for its component-based architecture, strong ecosystem, and excellent TypeScript support
|
||||
- **Migration Note:** Can be replaced with any other component-based framework (e.g., Vue, Svelte)
|
||||
|
||||
#### **State Management: Redux Toolkit**
|
||||
- **Why:** Provides predictable state management with excellent TypeScript support and dev tools
|
||||
- **Migration Note:** Can be replaced with Context API, Zustand, or other state management solutions
|
||||
|
||||
#### **UI Framework: Ionic React**
|
||||
- **Why:** Provides mobile-first UI components with excellent touch support and PWA capabilities
|
||||
- **Migration Note:** Can be replaced with Material-UI, Chakra UI, or custom components
|
||||
|
||||
#### **Build Tool: Vite**
|
||||
- **Why:** Fast development server and optimized builds with excellent TypeScript support
|
||||
- **Migration Note:** Can be replaced with Webpack, Parcel, or other build tools
|
||||
|
||||
#### **Backend: Firebase Realtime Database**
|
||||
- **Why:** Real-time synchronization, simple setup, and excellent React integration
|
||||
- **Migration Note:** Can be replaced with any real-time database (Supabase, AWS AppSync, etc.)
|
||||
|
||||
### **Development Tools:**
|
||||
- **TypeScript:** Type safety and better developer experience
|
||||
- **ESLint:** Code quality and consistency
|
||||
- **Prettier:** Code formatting
|
||||
- **React DevTools:** Component debugging
|
||||
- **Redux DevTools:** State management debugging
|
||||
|
||||
---
|
||||
|
||||
## Web-Specific Implementation Details
|
||||
|
||||
### **Authentication & Session Management:**
|
||||
- **Admin Access:** Triggered by URL parameter (`?admin=true`), removed after login
|
||||
- **Session Persistence:** Lost on browser reload (no persistent storage)
|
||||
- **Admin Mode:** Pre-fills singer name as "Admin" for convenience
|
||||
- **URL Handling:** Admin parameter automatically removed from URL after authentication
|
||||
|
||||
### **Search Implementation:**
|
||||
- **Pagination:** Uses Ionic InfiniteScrollList component for efficient loading
|
||||
- **Debouncing:** Search input debounced to prevent excessive API calls
|
||||
- **Real-time Results:** Instant search results as user types
|
||||
- **Context Actions:** Add to queue, favorite, and other actions available per song
|
||||
|
||||
### **Queue Management:**
|
||||
- **UI Controls:** Reordering and deletion exposed via UI controls only visible to admins
|
||||
- **Drag & Drop:** Uses Ionic drag handles and swipe actions for reordering
|
||||
- **Visual Feedback:** Clear indicators for admin-only actions
|
||||
- **State Synchronization:** Real-time updates across all connected clients
|
||||
|
||||
### **Favorites Implementation:**
|
||||
- **Infinite Scroll:** Uses Ionic InfiniteScrollList for pagination
|
||||
- **Real-time Sync:** Shared favorites list synchronized across all clients
|
||||
- **Duplicate Prevention:** Prevents duplicates using song path field
|
||||
- **User Actions:** Anyone can add/remove favorites
|
||||
|
||||
### **New Songs Implementation:**
|
||||
- **Infinite Scroll:** Uses Ionic InfiniteScrollList for pagination
|
||||
- **Real-time Updates:** Shows recently added songs from newSongs node
|
||||
- **Automatic Loading:** Progressive loading as user scrolls
|
||||
|
||||
### **Artists Implementation:**
|
||||
- **Modal Views:** Uses Ionic modals for artist song lists
|
||||
- **Infinite Scroll:** Uses Ionic InfiniteScrollList for pagination
|
||||
- **Search Integration:** Artist search functionality included
|
||||
- **Song Counts:** Displays song count per artist
|
||||
|
||||
### **Song Lists Implementation:**
|
||||
- **Modal Interface:** Uses Ionic modals for viewing list contents
|
||||
- **Infinite Scroll:** Uses Ionic InfiniteScrollList for pagination
|
||||
- **Expandable Views:** Available versions shown with expandable sections
|
||||
- **Availability Status:** Shows which songs are available in catalog
|
||||
|
||||
### **History Implementation:**
|
||||
- **Infinite Scroll:** Uses Ionic InfiniteScrollList for pagination
|
||||
- **Automatic Tracking:** Songs automatically added when played
|
||||
- **Timestamp Display:** Shows when each song was last played
|
||||
- **Append-only:** History is append-only, shared across all clients
|
||||
|
||||
### **Top Played Implementation:**
|
||||
- **Infinite Scroll:** Uses Ionic InfiniteScrollList for pagination
|
||||
- **Play Count Display:** Shows play count for each song
|
||||
- **Real-time Updates:** Popular songs generated by backend
|
||||
- **Backend Integration:** Based on history data
|
||||
|
||||
### **Singer Management:**
|
||||
- **Admin-only UI:** Singer management available only to admins via settings page
|
||||
- **Unique Names:** Singer names must be unique and non-empty
|
||||
- **Auto-addition:** Singers automatically added when they join
|
||||
- **Last Join Tracking:** Tracks when each singer last joined
|
||||
|
||||
### **Playback Control:**
|
||||
- **Admin-only Controls:** Player controls only rendered for admins
|
||||
- **State-based UI:** Play/pause/stop buttons shown/hidden based on current state
|
||||
- **Queue Validation:** Play button disabled when queue is empty
|
||||
- **Real-time Sync:** Playback state synchronized across all clients
|
||||
|
||||
### **Error Handling & Sync:**
|
||||
- **Toast Notifications:** Uses web-specific toast notifications for user feedback
|
||||
- **Error Boundaries:** React error boundaries for component-level error handling
|
||||
- **Retry Patterns:** Automatic retry for failed Firebase operations
|
||||
- **Connection Monitoring:** Real-time connection status tracking
|
||||
|
||||
### **Disabled Songs:**
|
||||
- **Modal Management:** Disabled songs managed via modal dialog
|
||||
- **Search & Filter:** Search and filter capabilities in management interface
|
||||
- **Hash Storage:** Disabled songs stored using hash of song path
|
||||
- **Admin-only Access:** Only admins can disable or enable songs
|
||||
|
||||
### **Settings Implementation:**
|
||||
- **Debug Logging:** Web-only feature, toggled via settings page
|
||||
- **Admin-only Access:** Only admins can change player settings
|
||||
- **Real-time Updates:** Settings changes synchronized across all clients
|
||||
- **UI Controls:** Settings interface with toggle switches and controls
|
||||
|
||||
### **Navigation Implementation:**
|
||||
- **Admin-based Navigation:** Navigation adapts based on admin status
|
||||
- **Hidden Pages:** Settings page only visible to admins
|
||||
- **Role-based UI:** Different navigation options for different user roles
|
||||
- **Dynamic Menus:** Menu items shown/hidden based on permissions
|
||||
|
||||
### **UI/UX Implementation:**
|
||||
- **Ionic React:** Uses Ionic React and Tailwind CSS for UI
|
||||
- **Component Library:** Infinite scroll, swipe actions, modals, and toasts using Ionic components
|
||||
- **Responsive Design:** Mobile-first approach with touch-friendly interface
|
||||
- **Theme Support:** Light/dark mode support with consistent styling
|
||||
|
||||
## Implementation Notes
|
||||
|
||||
### **Critical Web-Specific Patterns:**
|
||||
|
||||
#### **Firebase Integration:**
|
||||
```typescript
|
||||
// src/firebase/services.ts
|
||||
export const queueService = {
|
||||
addToQueue: async (song: Song, singerId: string) => {
|
||||
const newKey = await getNextKey('queue');
|
||||
await set(ref(database, `queue/${newKey}`), {
|
||||
songId: song.id,
|
||||
singerId,
|
||||
timestamp: Date.now(),
|
||||
key: newKey,
|
||||
});
|
||||
},
|
||||
};
|
||||
```
|
||||
|
||||
#### **Real-time Listeners:**
|
||||
```typescript
|
||||
// src/hooks/useQueue.ts
|
||||
useEffect(() => {
|
||||
const queueRef = ref(database, 'queue');
|
||||
const unsubscribe = onValue(queueRef, (snapshot) => {
|
||||
const data = snapshot.val();
|
||||
if (data) {
|
||||
const queueItems = Object.values(data) as QueueItem[];
|
||||
dispatch(setQueue(queueItems));
|
||||
}
|
||||
});
|
||||
return () => unsubscribe();
|
||||
}, [dispatch]);
|
||||
```
|
||||
|
||||
#### **Error Handling:**
|
||||
```typescript
|
||||
// src/hooks/useFirebaseSync.ts
|
||||
const retryOperation = async (operation: () => Promise<void>, maxRetries = 3) => {
|
||||
for (let i = 0; i < maxRetries; i++) {
|
||||
try {
|
||||
await operation();
|
||||
return;
|
||||
} catch (error) {
|
||||
if (i === maxRetries - 1) throw error;
|
||||
await new Promise(resolve => setTimeout(resolve, 1000 * (i + 1)));
|
||||
}
|
||||
}
|
||||
};
|
||||
```
|
||||
|
||||
### **Hook Implementation Patterns:**
|
||||
|
||||
#### **Custom Hook Structure:**
|
||||
```typescript
|
||||
// src/hooks/useQueue.ts
|
||||
export const useQueue = () => {
|
||||
const dispatch = useAppDispatch();
|
||||
const queue = useAppSelector(selectQueue);
|
||||
const [loading, setLoading] = useState(false);
|
||||
const [error, setError] = useState<string | null>(null);
|
||||
|
||||
const addToQueue = useCallback(async (song: Song, singerId: string) => {
|
||||
try {
|
||||
setLoading(true);
|
||||
setError(null);
|
||||
await queueService.addToQueue(song, singerId);
|
||||
} catch (err) {
|
||||
setError(err instanceof Error ? err.message : 'Failed to add to queue');
|
||||
} finally {
|
||||
setLoading(false);
|
||||
}
|
||||
}, []);
|
||||
|
||||
return {
|
||||
queue,
|
||||
loading,
|
||||
error,
|
||||
addToQueue,
|
||||
};
|
||||
};
|
||||
```
|
||||
|
||||
#### **Hook Dependencies:**
|
||||
- **Hooks depend on Redux state** and services
|
||||
- **Business logic** implemented in hooks, not components
|
||||
- **Error handling** and loading states managed in hooks
|
||||
- **Memoization** used for expensive operations
|
||||
|
||||
#### **Hook Usage in Components:**
|
||||
```typescript
|
||||
// src/features/Queue/Queue.tsx
|
||||
const Queue: React.FC = () => {
|
||||
const { queue, loading, error, addToQueue } = useQueue();
|
||||
const { songs } = useSongs();
|
||||
|
||||
const handleAddToQueue = useCallback((song: Song) => {
|
||||
addToQueue(song, currentSingerId);
|
||||
}, [addToQueue, currentSingerId]);
|
||||
|
||||
if (loading) return <LoadingSpinner />;
|
||||
if (error) return <ErrorMessage message={error} />;
|
||||
|
||||
return (
|
||||
<IonList>
|
||||
{Object.values(queue).map((item) => (
|
||||
<SongItem
|
||||
key={item.key}
|
||||
song={songs[item.songId]}
|
||||
onAddToQueue={handleAddToQueue}
|
||||
/>
|
||||
))}
|
||||
</IonList>
|
||||
);
|
||||
};
|
||||
```
|
||||
|
||||
### **Performance Optimizations:**
|
||||
- **React.memo** for expensive components
|
||||
- **useMemo** and **useCallback** for expensive calculations
|
||||
- **Redux selectors** with memoization
|
||||
- **Lazy loading** for route-based code splitting
|
||||
- **Service worker** for PWA caching
|
||||
|
||||
### **Critical Implementation Rules:**
|
||||
- **Never import directly from slice files** - always use the main redux index
|
||||
- **Always use type imports** for TypeScript interfaces
|
||||
- **Implement business logic in hooks**, not components
|
||||
- **Use memoization** for expensive operations
|
||||
- **Handle loading and error states** in all async operations
|
||||
|
||||
---
|
||||
|
||||
## Migration Guide
|
||||
|
||||
### **To Other Web Frameworks:**
|
||||
|
||||
#### **Vue.js Migration:**
|
||||
- Replace React components with Vue components
|
||||
- Replace Redux with Pinia or Vuex
|
||||
- Replace Ionic React with Ionic Vue
|
||||
- Keep all business logic and Firebase integration
|
||||
|
||||
#### **Svelte Migration:**
|
||||
- Replace React components with Svelte components
|
||||
- Replace Redux with Svelte stores
|
||||
- Replace Ionic React with Ionic Svelte
|
||||
- Keep all business logic and Firebase integration
|
||||
|
||||
### **To Mobile Platforms:**
|
||||
|
||||
#### **React Native Migration:**
|
||||
- Replace Ionic components with React Native components
|
||||
- Replace web-specific APIs with React Native APIs
|
||||
- Keep Redux state management
|
||||
- Keep all business logic and Firebase integration
|
||||
|
||||
#### **Native iOS/Android Migration:**
|
||||
- Replace React components with native UI components
|
||||
- Replace Redux with native state management
|
||||
- Keep all business logic and Firebase integration
|
||||
- Adapt UI patterns to platform conventions
|
||||
|
||||
---
|
||||
|
||||
_This document contains web-specific implementation details. For core business logic and platform-agnostic requirements, see the main `../../PRD.md`._
|
||||
132
docs/platforms/web/README.md
Normal file
@ -0,0 +1,132 @@
|
||||
# Web Platform Documentation
|
||||
|
||||
> **Platform:** Web (React + Ionic + TypeScript)
|
||||
> **Core Business Logic:** See `../../PRD.md`
|
||||
|
||||
This folder contains **web-specific implementation details** for the Karaoke App.
|
||||
|
||||
---
|
||||
|
||||
## 📁 File Structure
|
||||
|
||||
```
|
||||
docs/platforms/web/
|
||||
├── PRD-web.md # Web-specific implementation guide
|
||||
└── README.md # This file - quick reference
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 🚀 Quick Start
|
||||
|
||||
### **For AI-Assisted Development:**
|
||||
1. **Read the main PRD:** `../../PRD.md` (core business logic)
|
||||
2. **Read this web PRD:** `PRD-web.md` (web implementation details)
|
||||
3. **Follow the implementation guide** in the main PRD
|
||||
4. **Reference design assets:** `design/`
|
||||
|
||||
### **For Human Developers:**
|
||||
1. **Review business requirements** in main PRD
|
||||
2. **Study web implementation** patterns in `PRD-web.md`
|
||||
3. **Set up development environment** using provided configs
|
||||
4. **Follow component architecture** and state management patterns
|
||||
|
||||
---
|
||||
|
||||
## 📋 What's Included
|
||||
|
||||
### **PRD-web.md Contains:**
|
||||
- **UI/UX Behavior** - Web-specific patterns and interactions
|
||||
- **Component Architecture** - React/Ionic component structure
|
||||
- **State Management** - Redux Toolkit implementation
|
||||
- **Development Setup** - Project configuration and environment
|
||||
- **Design Assets** - Web-specific visual references
|
||||
- **Toolset Choices** - Technology rationale and migration notes
|
||||
- **Implementation Notes** - Critical web-specific patterns
|
||||
- **Migration Guide** - How to adapt to other platforms
|
||||
|
||||
### **Key Web Technologies:**
|
||||
- **React 18** + **TypeScript** for component architecture
|
||||
- **Ionic React** for mobile-first UI components
|
||||
- **Redux Toolkit** for state management
|
||||
- **Firebase Realtime Database** for backend
|
||||
- **Vite** for build tooling
|
||||
|
||||
---
|
||||
|
||||
## 🔗 Cross-References
|
||||
|
||||
### **Main PRD Sections:**
|
||||
- **Business Logic:** See `../../PRD.md#business-logic`
|
||||
- **Data Models:** See `../../PRD.md#data-models`
|
||||
- **User Roles:** See `../../PRD.md#user-roles`
|
||||
- **Feature Specs:** See `../../PRD.md#feature-overview`
|
||||
|
||||
### **Design Assets:**
|
||||
- **Web Mockups:** See `design/`
|
||||
- **30+ Visual References** for all features
|
||||
|
||||
### **Implementation Guide:**
|
||||
- **Core Requirements:** See `../../PRD.md#implementation-guide`
|
||||
- **Web-Specific Details:** See `PRD-web.md#implementation-notes`
|
||||
|
||||
---
|
||||
|
||||
## 🛠️ Development Workflow
|
||||
|
||||
### **1. Setup Project:**
|
||||
```bash
|
||||
# Install dependencies
|
||||
npm install
|
||||
|
||||
# Set up environment
|
||||
cp .env.template .env.local
|
||||
# Edit .env.local with your Firebase config
|
||||
|
||||
# Start development server
|
||||
npm run dev
|
||||
```
|
||||
|
||||
### **2. Follow Architecture:**
|
||||
- **Components:** Use React functional components with TypeScript
|
||||
- **State:** Use Redux Toolkit for global state
|
||||
- **Styling:** Use Ionic components with custom CSS variables
|
||||
- **Data:** Use Firebase Realtime Database with custom hooks
|
||||
|
||||
### **3. Reference Patterns:**
|
||||
- **Firebase Integration:** See `PRD-web.md#firebase-integration`
|
||||
- **Real-time Listeners:** See `PRD-web.md#real-time-listeners`
|
||||
- **Error Handling:** See `PRD-web.md#error-handling`
|
||||
|
||||
---
|
||||
|
||||
## 🔄 Migration Paths
|
||||
|
||||
### **To Other Web Frameworks:**
|
||||
- **Vue.js:** Replace React with Vue, Redux with Pinia
|
||||
- **Svelte:** Replace React with Svelte, Redux with Svelte stores
|
||||
- **Keep:** All business logic and Firebase integration
|
||||
|
||||
### **To Mobile Platforms:**
|
||||
- **React Native:** Replace Ionic with React Native components
|
||||
- **Native iOS/Android:** Replace React with native UI frameworks
|
||||
- **Keep:** All business logic and Firebase integration
|
||||
|
||||
---
|
||||
|
||||
## 📚 Additional Resources
|
||||
|
||||
### **Documentation:**
|
||||
- **Main PRD:** `../../PRD.md` - Core business logic
|
||||
- **Design Assets:** `design/` - Visual references
|
||||
- **Type Definitions:** `../../types.ts` - Data models
|
||||
|
||||
### **External Resources:**
|
||||
- **Ionic React:** https://ionicframework.com/docs/react
|
||||
- **Redux Toolkit:** https://redux-toolkit.js.org/
|
||||
- **Firebase:** https://firebase.google.com/docs
|
||||
- **React:** https://react.dev/
|
||||
|
||||
---
|
||||
|
||||
_This document provides web-specific implementation details. For core business logic and platform-agnostic requirements, see the main `../../PRD.md`._
|
||||
|
Before Width: | Height: | Size: 204 KiB After Width: | Height: | Size: 204 KiB |
|
Before Width: | Height: | Size: 236 KiB After Width: | Height: | Size: 236 KiB |
|
Before Width: | Height: | Size: 120 KiB After Width: | Height: | Size: 120 KiB |
|
Before Width: | Height: | Size: 246 KiB After Width: | Height: | Size: 246 KiB |
|
Before Width: | Height: | Size: 247 KiB After Width: | Height: | Size: 247 KiB |
|
Before Width: | Height: | Size: 243 KiB After Width: | Height: | Size: 243 KiB |
|
Before Width: | Height: | Size: 245 KiB After Width: | Height: | Size: 245 KiB |
|
Before Width: | Height: | Size: 105 KiB After Width: | Height: | Size: 105 KiB |
|
Before Width: | Height: | Size: 123 KiB After Width: | Height: | Size: 123 KiB |
|
Before Width: | Height: | Size: 109 KiB After Width: | Height: | Size: 109 KiB |
|
Before Width: | Height: | Size: 293 KiB After Width: | Height: | Size: 293 KiB |
|
Before Width: | Height: | Size: 270 KiB After Width: | Height: | Size: 270 KiB |
|
Before Width: | Height: | Size: 274 KiB After Width: | Height: | Size: 274 KiB |
|
Before Width: | Height: | Size: 658 KiB After Width: | Height: | Size: 658 KiB |
|
Before Width: | Height: | Size: 275 KiB After Width: | Height: | Size: 275 KiB |
|
Before Width: | Height: | Size: 500 KiB After Width: | Height: | Size: 500 KiB |
|
Before Width: | Height: | Size: 206 KiB After Width: | Height: | Size: 206 KiB |
|
Before Width: | Height: | Size: 168 KiB After Width: | Height: | Size: 168 KiB |
|
Before Width: | Height: | Size: 168 KiB After Width: | Height: | Size: 168 KiB |
|
Before Width: | Height: | Size: 268 KiB After Width: | Height: | Size: 268 KiB |
|
Before Width: | Height: | Size: 498 KiB After Width: | Height: | Size: 498 KiB |
|
Before Width: | Height: | Size: 521 KiB After Width: | Height: | Size: 521 KiB |
|
Before Width: | Height: | Size: 459 KiB After Width: | Height: | Size: 459 KiB |
|
Before Width: | Height: | Size: 394 KiB After Width: | Height: | Size: 394 KiB |
|
Before Width: | Height: | Size: 472 KiB After Width: | Height: | Size: 472 KiB |
|
Before Width: | Height: | Size: 444 KiB After Width: | Height: | Size: 444 KiB |
|
Before Width: | Height: | Size: 312 KiB After Width: | Height: | Size: 312 KiB |
|
Before Width: | Height: | Size: 196 KiB After Width: | Height: | Size: 196 KiB |
|
Before Width: | Height: | Size: 397 KiB After Width: | Height: | Size: 397 KiB |
|
Before Width: | Height: | Size: 481 KiB After Width: | Height: | Size: 481 KiB |
|
Before Width: | Height: | Size: 239 KiB After Width: | Height: | Size: 239 KiB |