A comprehensive web application for managing YouTube Shorts production with team collaboration, scheduling, and real-time tracking
ShortHub is a modern collaborative platform designed for YouTube Shorts content production teams. It enables administrators, video editors (videastes), and assistants to efficiently manage the entire Shorts workflow from discovery to publication, with advanced scheduling, assignment tracking, and real-time notifications.
- Admin Dashboard: Full control over teams, channels, and assignments
- Videaste Workspace: Dedicated interface for video editors to manage their assignments
- Assistant Support: Specialized view for assistants working with videastes
- Dual Channel Types: Separate SOURCE channels (for content discovery) and PUBLICATION channels (for publishing)
- Smart Organization: Tag channels by language, country, content type, and edit style
- YouTube Integration: Automatic data extraction via YouTube Data API v3
- Smart Rolling: Generate random YouTube Shorts from source channels with filtering
- Assignment System: Assign shorts to team members with scheduled publication dates
- Status Tracking: Follow shorts through their lifecycle (ROLLED → ASSIGNED → IN_PROGRESS → COMPLETED → VALIDATED → PUBLISHED)
- Publication Calendar: Visual timeline of scheduled shorts with color-coded status
- Deadline Tracking: Automatic detection and highlighting of late assignments
- Date Management: Flexible scheduling with drag-and-drop support
- Live Updates: WebSocket-based notifications for assignments, completions, and reminders
- Multi-Channel: Email and WhatsApp notifications (configurable per user)
- In-App Alerts: Dropdown notification center with read/unread tracking
- Team Performance: Track completion rates, productivity metrics, and workload
- Channel Statistics: Monitor subscriber growth and content performance
- Custom Reports: Filter and export data for analysis
- React 19 with TypeScript for type-safe component development
- Vite 6 for lightning-fast build tooling and HMR
- TailwindCSS v4 for utility-first styling
- React Router v7 for client-side routing
- Apollo Client 4 for GraphQL state management
- HTTP Link for queries and mutations
- WebSocket Link for real-time subscriptions
- InMemoryCache with pagination support
- Optimistic UI updates
- Iconsax React & Phosphor Icons for comprehensive icon library
- Recharts for interactive data visualizations
- date-fns for date formatting and manipulation
- Class Variance Authority for variant-based component styling
- Tailwind Merge for intelligent class merging
The client connects to a GraphQL API powered by:
- Apollo Server 4 - GraphQL server with subscriptions
- MongoDB + Mongoose - NoSQL database with ODM
- JWT Authentication - Token-based auth with refresh tokens
- GraphQL Subscriptions - Real-time updates via WebSockets
- DataLoader - Batch and cache database queries (N+1 problem prevention)
- Bull - Background job processing and task queues
- Node-cron - Scheduled tasks (reminders, notifications)
- Winston - Structured logging
- YouTube Data API v3 - Channel and video metadata extraction
- NodeMailer - Email notifications
- Twilio - WhatsApp notifications
- ImageKit - Image optimization and CDN
- Custom form components with real-time validation
- Modal system for CRUD operations
- Toast notifications with auto-dismiss
- Dropdown menus and context actions
- Responsive design optimized for desktop and mobile
- Interactive calendars with drag-and-drop
- Data tables with sorting, filtering, and pagination
- Real-time notification center
Before getting started, ensure you have:
- Node.js (v18 or higher)
- npm or yarn
- MongoDB instance (local or cloud via Railway/MongoDB Atlas)
- ShortHub GraphQL API running (see server documentation)
- YouTube Data API key (optional, for automatic channel data extraction)
git clone https://github.com/your-username/shorthub.git
cd shorthub/clientnpm installCreate a .env file in the client directory:
touch .env# GraphQL API Endpoints
VITE_GRAPHQL_ENDPOINT=http://localhost:4000/graphql
VITE_WS_ENDPOINT=ws://localhost:4000/graphql
# YouTube API Configuration (optional - backend handles this)
VITE_YOUTUBE_API_KEY=your-youtube-api-key-here
# App Configuration
VITE_APP_NAME=ShortHubImportant Notes:
- The GraphQL endpoints should match your backend server configuration
- For production, update these URLs to your deployed API endpoints
- YouTube API key is optional and mainly used for client-side previews
The client requires the GraphQL API to be running. Follow the server setup instructions:
# In a separate terminal, navigate to the server directory
cd ../server
# Install dependencies
npm install
# Configure server .env file (see server README)
# Start the server
npm run devThe backend will run on http://localhost:4000 by default.
Back in the client directory:
npm run devThe application will be available at http://localhost:5173
Use the default admin credentials (change immediately after first login):
- Username:
admin - Password:
admin123
- Create Users: Add videastes and assistants with role-based permissions
- Assign Teams: Link assistants to their respective videastes
- Monitor Activity: Track team performance and productivity metrics
- Block/Unblock: Manage user access and permissions
- Source Channels: Add YouTube channels for content discovery
- Automatic metadata extraction via YouTube API
- Categorize by language, country, content type, and edit style
- Track subscriber history and growth
- Publication Channels: Register channels where content will be published
- Link to responsible videastes
- Set publishing preferences and schedules
- Smart Rolling: Generate random shorts from source channels with advanced filters
- Filter by language, country, content type
- Avoid previously rolled or assigned content
- Bulk Assignment: Assign shorts to videastes with scheduled dates
- Calendar View: Visualize all assignments in a timeline
- Track Status: Monitor shorts through all production stages
- Team Performance Dashboard: Completion rates, productivity, workload distribution
- Channel Statistics: Growth trends, content performance
- Custom Filters: Generate reports by date range, team member, or channel
- View all assigned shorts with status indicators
- See upcoming deadlines and late assignments
- Access publication calendar
- Track personal statistics and completion rate
- Review Assignments: View source video details and requirements
- Mark Progress: Update status (In Progress → Completed)
- Reassign to Assistant: Delegate tasks to linked assistants
- Add Comments: Collaborate with team via video comments
- Upload Finals: Submit completed videos for validation
- Manage your publication channels
- View publishing schedule
- Track published content
- View shorts assigned by your videaste
- See deadlines and priorities
- Track your completion progress
- Mark tasks as completed when done
- Add comments for communication
- Upload processed videos
- 🔔 In-App Notifications: Dropdown center with live updates
- 📧 Email Alerts: Configurable email notifications for key events
- 💬 WhatsApp Messages: Optional WhatsApp notifications via Twilio
- Update personal information
- Configure notification preferences
- View your statistics and activity history
- Change password
src/
├── components/ # Reusable UI components
│ ├── forms/ # Form input components
│ ├── modal/ # Modal system
│ ├── layout/ # Layout components
│ └── ui/ # Basic UI elements
├── context/ # React context providers
├── hooks/ # Custom React hooks
├── lib/ # Utility libraries
│ ├── supabase.ts # Database client and services
│ ├── youtube-api.ts # YouTube API integration
│ └── utils.ts # General utilities
├── pages/ # Application pages
├── types/ # TypeScript type definitions
├── utils/ # Helper functions and utilities
└── assets/ # Static assets
- Fields: username, email, password (hashed with bcrypt), role, status
- Roles: ADMIN (full control), VIDEASTE (video editor), ASSISTANT (helper)
- Status: ACTIVE or BLOCKED
- Relations: createdBy (admin who created the user), assignedTo (for assistants → videaste)
- Preferences: emailNotifications, whatsappNotifications, whatsappNumber
- Fields: youtubeUrl, channelId, username, subscriberCount, language, country
- Classification:
channelPurpose: SOURCE (for content discovery) or PUBLICATION (for publishing)contentType: GAMING, EDUCATION, ENTERTAINMENT, etc.editType: NO_EDIT, VOICEOVER, SUBTITLES, FULL_EDIT
- Tracking: subscriberHistory (array of {date, count})
- Relations: managedBy (videaste managing the publication channel)
- Fields: videoId, url, title, description, thumbnailUrl, duration, viewCount
- Channels:
sourceChannel: Where the short was discoveredpublicationChannel: Where it will be published
- Assignment:
assignedTo: Videaste responsible for the shortscheduledDate: Planned publication datenotes: Admin notes for the assignment
- Status Flow: ROLLED → ASSIGNED → IN_PROGRESS → COMPLETED → VALIDATED → PUBLISHED
- Timestamps: rolledAt, assignedAt, startedAt, completedAt, validatedAt, publishedAt
- Collaboration: comments array for team communication
- Fields: type, message, read status
- Types: VIDEO_ASSIGNED, DEADLINE_REMINDER, VIDEO_COMPLETED, VIDEO_VALIDATED, etc.
- Relations: userId (recipient), videoId (related video)
- Real-time: Delivered via GraphQL subscriptions
The application implements granular permissions based on user roles:
| Feature | Admin | Videaste | Assistant |
|---|---|---|---|
| Create/manage users | ✅ | ❌ | ❌ |
| Manage all channels | ✅ | ❌ | ❌ |
| Manage own publication channels | ✅ | ✅ | ❌ |
| Roll shorts | ✅ | ❌ | ❌ |
| Assign shorts to team | ✅ | ✅ (to assistant only) | ❌ |
| View all assignments | ✅ | ❌ | ❌ |
| View own assignments | ✅ | ✅ | ✅ |
| Update video status | ✅ | ✅ | ✅ |
| Mark as completed | ✅ | ✅ | ✅ |
| Validate videos | ✅ | ❌ | ❌ |
| View analytics (all) | ✅ | ❌ | ❌ |
| View analytics (own) | ✅ | ✅ | ✅ |
| Comment on videos | ✅ | ✅ | ✅ |
| Receive notifications | ✅ | ✅ | ✅ |
# Development server
npm run dev
# Build for production
npm run build
# Preview production build
npm run preview
# Type checking
npm run type-check
# Linting
npm run lint- TypeScript: Strict type checking enabled
- ESLint: Code quality and consistency
- Prettier: Code formatting
- Conventional Commits: Standardized commit messages
The application follows GraphQL best practices:
- Apollo Client Cache: InMemoryCache with custom merge policies for pagination
- DataLoader Pattern: Backend uses DataLoader to batch and cache database queries (N+1 prevention)
- Optimistic Updates: Immediate UI feedback before server confirmation
- Error Handling: Centralized error handling with automatic auth token refresh
- Subscriptions: Real-time updates via WebSocket for notifications and live data
- Pagination: Relay-style cursor-based pagination for large datasets
- Apollo Client serves as the primary state management solution
- Local Storage for auth tokens and user preferences
- React Context for theme and UI state
- URL State for filters, sorting, and navigation
- Deploy the Backend First: Follow the server deployment guide
- Deploy to Railway, Render, or any Node.js hosting platform
- Ensure MongoDB is accessible from the backend
- Note the GraphQL API URL (e.g.,
https://your-api.railway.app/graphql)
-
Install Vercel CLI:
npm i -g vercel
-
Configure environment variables in Vercel dashboard or via CLI:
VITE_GRAPHQL_ENDPOINT=https://your-api.railway.app/graphql VITE_WS_ENDPOINT=wss://your-api.railway.app/graphql VITE_YOUTUBE_API_KEY=your-youtube-api-key VITE_APP_NAME=ShortHub
-
Deploy:
vercel --prod
-
Build the application:
npm run build
-
Deploy via Netlify CLI or drag-and-drop:
netlify deploy --prod --dir=dist
-
Set environment variables in Netlify dashboard (Site settings → Environment variables)
-
Build:
npm run build
-
Upload the
distfolder to any static hosting service (Cloudflare Pages, GitHub Pages, AWS S3 + CloudFront)
Update the backend .env to allow requests from your frontend domain:
CORS_ORIGIN=https://your-frontend-domain.comFor multiple domains (staging + production):
CORS_ORIGIN=https://app.shorthub.com,https://staging.shorthub.com| Variable | Description | Required | Example |
|---|---|---|---|
VITE_GRAPHQL_ENDPOINT |
GraphQL API HTTP endpoint | ✅ | http://localhost:4000/graphql |
VITE_WS_ENDPOINT |
GraphQL WebSocket endpoint for subscriptions | ✅ | ws://localhost:4000/graphql |
VITE_YOUTUBE_API_KEY |
YouTube Data API key for client-side previews | AIza... |
|
VITE_APP_NAME |
Application display name | ShortHub |
Production Notes:
- Use
https://for VITE_GRAPHQL_ENDPOINT in production - Use
wss://for VITE_WS_ENDPOINT in production (secure WebSocket) - Keep YouTube API key for client-side features (video thumbnails, previews)
- Fork the repository
- Create a feature branch:
git checkout -b feature/amazing-feature - Commit your changes:
git commit -m 'feat: add amazing feature' - Push to the branch:
git push origin feature/amazing-feature - Open a Pull Request
We use Conventional Commits:
feat:- New featuresfix:- Bug fixesdocs:- Documentation changesstyle:- Code style changes (formatting, etc.)refactor:- Code refactoringtest:- Adding or updating testschore:- Maintenance tasks
This project is licensed under the MIT License - see the LICENSE file for details.
- Apollo GraphQL for the excellent GraphQL client and server ecosystem
- MongoDB & Mongoose for flexible and scalable database solutions
- YouTube Data API for comprehensive channel and video metadata
- Iconsax & Phosphor Icons for beautiful and extensive icon libraries
- Recharts for powerful and customizable data visualizations
- TailwindCSS for the utility-first CSS framework
- Vite for blazing-fast development experience
- React Team for the amazing React 19 updates
- 📧 Email: goddivor7@gmail.com
- 🐛 Issues: GitHub Issues
- 📖 Backend Documentation: Server README
- ShortHub Server: GraphQL API backend with MongoDB
- ShortHub Browser Extension (coming soon): Chrome extension for quick channel addition
This frontend communicates with the ShortHub GraphQL API. Key integration points:
// Login mutation returns JWT tokens
mutation Login {
login(username: "admin", password: "admin123") {
token
refreshToken
user { id, username, role }
}
}// Subscribe to notifications via WebSocket
subscription OnNotification {
notificationReceived(userId: "USER_ID") {
id, type, message, createdAt
}
}// Cursor-based pagination (Relay spec)
query GetVideos {
videos(first: 20, after: "cursor") {
edges { node { id, title } }
pageInfo { hasNextPage, endCursor }
}
}For complete API documentation, see the GraphQL Schema.
Made with ❤️ for YouTube Shorts production teams
© 2025 ShortHub. All rights reserved.
