100% vibe coded - Built with AI assistance and good vibes 🤖✨
Warning
Early Development Software - OpsDec is currently in active development and testing. While functional, you may encounter bugs or incomplete features. Use in production environments at your own risk. Feedback and contributions are welcome!
A modern, self-hosted media server monitoring and statistics platform inspired by Tautulli. Track your Plex, Emby, Audiobookshelf, and Sappho server activity with real-time monitoring, detailed statistics, and a beautiful dark-themed interface.
- 📊 Real-time Activity Monitoring - Track current playback sessions in real-time
- 📈 Detailed Statistics - View comprehensive statistics for users and media
- 👥 User Management - Monitor individual user activity and watch history with user mapping across servers
- 📜 Watch History - Complete history of all playback sessions
- 🎨 Tautulli-inspired UI - Dark, modern interface with smooth animations
- 📱 Mobile Responsive - Fully optimized mobile interface with touch-friendly controls
- 🔌 Multi-Server Support - Supports Plex, Emby, Audiobookshelf, and Sappho
- 🐳 Docker Ready - Easy deployment with Docker and Docker Compose
- 🚀 Fast & Lightweight - Built with React and Express.js
- 💾 SQLite Database - Simple, file-based database with no external dependencies
- 🎯 User Mapping - Consolidate the same user across different media servers
- Node.js with Express.js
- SQLite3 with better-sqlite3
- WebSocket for real-time updates
- Node-cron for scheduled tasks
- Axios for API calls
- React 18
- Vite for fast development
- TailwindCSS for styling
- Recharts for data visualization
- React Router for navigation
- Lucide React for icons
- For Docker: Docker and Docker Compose
- For Manual Install: Node.js 18.0.0 or higher
- Media Server: Plex Media Server, Emby Media Server, Audiobookshelf, and/or Sappho with API access
If you're running Unraid, you can install OpsDec using the Community Applications plugin:
-
Install from Community Applications (when available):
- Open Unraid's Apps tab
- Search for "OpsDec"
- Click Install
-
Or install manually from the template:
- Download the template file: opsdec-unraid-template.xml
- Place it in
/boot/config/plugins/dockerMan/templates-user/on your Unraid server - Go to the Docker tab in Unraid
- Click Add Container
- Select OpsDec from the template dropdown
-
Configure your servers:
- Fill in the URLs and API keys/tokens for your media servers (Plex, Emby, Audiobookshelf, Sappho)
- You can leave servers blank if you don't use them
- Choose your preferred Repository Tag (latest, 0.1.0, or date-based for stability)
-
Access OpsDec at
http://[UNRAID-IP]:3001
The easiest way to run OpsDec is with Docker. Pre-built images are automatically published to GitHub Container Registry.
Pre-built images are available with multiple tags for version pinning:
- Latest (main branch):
ghcr.io/mondominator/opsdec:latest - Date-based:
ghcr.io/mondominator/opsdec:20251118(format: YYYYMMDD) - Commit SHA:
ghcr.io/mondominator/opsdec:main-abc1234 - Semantic versions:
ghcr.io/mondominator/opsdec:1.0.0(when releases are tagged)
Recommended for production: Use date-based or version tags instead of latest for stability.
- Create a
docker-compose.ymlfile or use the provided one - Create a
.envfile with your configuration:
# Plex Configuration (optional)
PLEX_URL=http://your-plex-server:32400
PLEX_TOKEN=your_plex_token
# Emby Configuration (optional)
EMBY_URL=http://your-emby-server:8096
EMBY_API_KEY=your_emby_api_key
# Audiobookshelf Configuration (optional)
AUDIOBOOKSHELF_URL=http://your-audiobookshelf-server:13378
AUDIOBOOKSHELF_TOKEN=your_audiobookshelf_token
# Sappho Configuration (optional)
SAPPHO_URL=http://your-sappho-server:3000
SAPPHO_API_KEY=your_sappho_api_key
# Polling interval (seconds)
POLL_INTERVAL=30- Start the container:
docker-compose up -d- Access at
http://localhost:3001
docker build -t opsdec .
docker run -d \
--name opsdec \
-p 3001:3001 \
-v $(pwd)/data:/app/backend/data \
-e PLEX_URL=http://your-plex-server:32400 \
-e PLEX_TOKEN=your_plex_token \
-e EMBY_URL=http://your-emby-server:8096 \
-e EMBY_API_KEY=your_emby_api_key \
-e AUDIOBOOKSHELF_URL=http://your-audiobookshelf-server:13378 \
-e AUDIOBOOKSHELF_TOKEN=your_audiobookshelf_token \
-e SAPPHO_URL=http://your-sappho-server:3000 \
-e SAPPHO_API_KEY=your_sappho_api_key \
opsdecgit clone https://github.com/mondominator/opsdec.git
cd opsdecnpm installThis will install dependencies for both the backend and frontend using npm workspaces.
Create a .env file in the backend directory:
cp backend/.env.example backend/.envEdit backend/.env with your configuration:
# Server Configuration
PORT=3001
NODE_ENV=development
# Database
DB_PATH=./data/opsdec.db
# Plex Configuration (optional - leave blank if not using)
PLEX_URL=http://localhost:32400
PLEX_TOKEN=your_plex_token_here
# Emby Configuration (optional - leave blank if not using)
EMBY_URL=http://localhost:8096
EMBY_API_KEY=your_emby_api_key_here
# Audiobookshelf Configuration (optional - leave blank if not using)
AUDIOBOOKSHELF_URL=http://localhost:13378
AUDIOBOOKSHELF_TOKEN=your_audiobookshelf_token_here
# Sappho Configuration (optional - leave blank if not using)
SAPPHO_URL=http://localhost:3000
SAPPHO_API_KEY=your_sappho_api_key_here
# Polling interval in seconds
POLL_INTERVAL=30- Sign in to Plex Web App
- Open any media item
- Click the three dots (•••) → "Get Info"
- Click "View XML"
- In the URL, find
X-Plex-Token=xxxxx- that's your token
Alternative method:
# Get token via curl (replace username and password)
curl -X POST \
'https://plex.tv/users/sign_in.xml' \
-H 'X-Plex-Client-Identifier: opsdec' \
-d 'user[login]=your_email' \
-d 'user[password]=your_password'Look for <authentication-token> in the response.
- Log into your Emby server
- Go to Settings → Advanced → API Keys
- Click New API Key
- Enter "OpsDec" as the app name
- Copy the generated API key
- Log into your Audiobookshelf server
- Click on your profile icon (top right)
- Go to Settings → Account
- Click Generate New API Token
- Copy the generated token
- Log into your Sappho server
- Go to Settings → API Keys
- Click Create New API Key
- Enter "OpsDec" as the name
- Copy the generated API key
For development (runs both backend and frontend):
npm run devThis will start:
- Backend API server on
http://localhost:3001 - Frontend development server on
http://localhost:3000
OpsDec can monitor multiple media servers simultaneously using two methods:
Configure servers via environment variables in your .env file or docker-compose.yml:
- Plex - Set
PLEX_URLandPLEX_TOKEN - Emby - Set
EMBY_URLandEMBY_API_KEY - Audiobookshelf - Set
AUDIOBOOKSHELF_URLandAUDIOBOOKSHELF_TOKEN - Sappho - Set
SAPPHO_URLandSAPPHO_API_KEY
Environment variable servers will appear in the Settings UI as read-only with a special badge.
Add and manage servers directly through the Settings page:
- Navigate to Settings in the web interface
- Click Add Server
- Fill in server details (type, name, URL, API key/token)
- Click Save Server
Note: You can use both methods simultaneously. Environment variable servers and UI-configured servers will both appear in the Settings page. Environment variable servers are marked with an "Environment Variable" badge and cannot be edited or deleted through the UI.
Activity from all configured servers will be aggregated in a single dashboard.
The Docker image is production-ready and has NODE_ENV=production set by default. No additional configuration needed!
# Build the frontend
npm run build
# Set environment to production
export NODE_ENV=production
# Start the backend (will serve built frontend)
npm startThe backend automatically serves the frontend in production mode from the /frontend/dist directory.
opsdec/
├── backend/
│ ├── src/
│ │ ├── database/
│ │ │ └── init.js # Database schema and initialization
│ │ ├── routes/
│ │ │ └── api.js # API endpoints
│ │ ├── services/
│ │ │ ├── emby.js # Emby API integration
│ │ │ ├── plex.js # Plex API integration
│ │ │ ├── audiobookshelf.js # Audiobookshelf API integration
│ │ │ ├── sappho.js # Sappho API integration
│ │ │ └── monitor.js # Activity monitoring service
│ │ └── index.js # Express server and WebSocket
│ ├── .env.example
│ └── package.json
├── frontend/
│ ├── src/
│ │ ├── components/
│ │ │ └── Layout.jsx # Main layout component
│ │ ├── pages/
│ │ │ ├── Dashboard.jsx # Dashboard with stats
│ │ │ ├── Activity.jsx # Current activity view
│ │ │ ├── History.jsx # Watch history
│ │ │ ├── Users.jsx # User list
│ │ │ └── UserDetail.jsx # Individual user stats
│ │ ├── utils/
│ │ │ ├── api.js # API client
│ │ │ └── format.js # Formatting utilities
│ │ ├── App.jsx
│ │ ├── main.jsx
│ │ └── index.css
│ ├── index.html
│ ├── vite.config.js
│ ├── tailwind.config.js
│ └── package.json
├── package.json
└── README.md
- Live activity counter
- Total plays and users statistics
- 30-day play history chart
- Top users by watch time
- Most watched content
- Current streaming sessions
- Real-time view of active playback sessions
- Progress tracking with visual indicators
- Playback state (playing/paused/buffering)
- User information and timestamps
- Auto-refresh every 3 seconds
- Complete history of all playback sessions
- Advanced search functionality (title, show, username)
- Multi-filter system (user, server, media type)
- Flexible pagination (25, 50, 100, 250 items per page)
- Sortable columns (all 7 columns)
- Media thumbnails and metadata
- Completion percentage tracking
- Server identification with logos
- Individual user profiles
- Total plays and watch time
- Watch distribution by media type
- Recent watches
- Most watched content
- Activity timeline
GET /api/activity- Get current active sessions
GET /api/history- Get watch history (supports pagination and user filtering)
GET /api/users- Get all usersGET /api/users/:userId/stats- Get detailed user statistics
GET /api/stats/dashboard- Get dashboard statistics
GET /api/emby/test- Test Emby connectionGET /api/emby/libraries- Get Emby librariesGET /api/media/recent- Get recently added media from all servers
ws://localhost:3001/ws- Real-time activity updates
- Jellyfin support
- Notifications (Discord, Email, etc.)
- Custom dashboard widgets
- Export statistics to CSV/JSON
- Mobile-responsive design - Fully optimized!
- Dark/Light theme toggle
- User authentication
- Date range filtering for history
- User mapping across servers - Implemented!
Contributions are welcome! Please feel free to submit a Pull Request.
MIT License - feel free to use this project for personal or commercial purposes.
- Inspired by Tautulli - the excellent monitoring tool for Plex
- Built with modern web technologies and best practices
- Thanks to the Emby community for their excellent API documentation
If you encounter any issues or have questions:
- Check the Issues page
- Create a new issue with detailed information
- Include logs from both backend and frontend
The main dashboard provides an overview of your media server activity with real-time statistics, charts, and current streaming sessions.
Monitor live playback sessions with detailed information about what users are watching, playback progress, and streaming state.
Deep dive into individual user activity with comprehensive statistics, watch patterns, and favorite content.
Happy monitoring! 🎬📊