The StreamSource admin interface is a modern web application built with Rails 8 and Hotwire, providing a rich, interactive experience for managing streamers, streams, timestamps, users, and application settings without page refreshes. It includes real-time collaborative editing via ActionCable WebSockets, allowing multiple administrators to work together seamlessly.
- Backend: Rails 8.0.x with session-based authentication
- Frontend Framework: Hotwire (Turbo + Stimulus) with ActionCable
- CSS Framework: Tailwind CSS 3.4
- JavaScript Bundler: ESBuild
- Package Manager: Yarn
- Real-time: ActionCable WebSockets
- CRUD Operations: Create, read, update, and delete streamers
- Platform Accounts: Manage streamer accounts across different platforms
- Associated Streams: View and manage all streams for a streamer
- CRUD Operations: Create, read, update, and delete streams
- Real-time Search: Filter streams as you type with debounced search
- Advanced Filtering: Filter by status, platform, streamer, city, state, and more
- Pin/Unpin: Mark important streams with a single click
- Archive/Unarchive: Archive old streams while keeping data
- Stream Attributes: Manage platform, orientation, kind, timestamps
- Pagination: Efficient browsing with Pagy pagination
- Modal Forms: Edit streams in modal dialogs without page refresh
- Real-time Collaboration: Multiple admins can edit streams simultaneously with cell-level locking
- Event Tracking: Create and manage event timestamps across streams
- Stream Association: Link timestamps to multiple streams with time offsets
- Timeline View: View events in chronological order
- User Attribution: Track who added each timestamp
- User List: View all users with their roles and stream counts
- Role Management: Promote/demote users between roles
- User Creation: Add new users with specified roles
- User Editing: Update user information
- Cell-level Locking: Prevents conflicts when multiple users edit
- User Presence: See who else is editing with color-coded indicators
- Auto-unlock: Cells automatically unlock when users disconnect
- Edit Timeout: 5-second timeout ensures cells don't stay locked
- Flipper Integration: Toggle features on/off in real-time
- Group Management: Enable features for specific user groups
- Percentage Rollouts: Gradually roll out features to user percentages
- Navigate to
http://localhost:3000/admin/login - Enter admin credentials:
- Email:
admin@example.com - Password:
Password123!(in development)
- Email:
- Click "Sign In"
The admin interface features a sidebar with the following sections:
- Streams: Main stream management interface
- Streamers: Content creator management
- Timestamps: Event tracking with time references
- Users: User management
- Feature Flags: Feature toggle management
- Logout: End admin session
Base controller for all admin controllers providing:
- Session-based authentication
- Admin user authorization
- Maintenance mode checking
- Common layout and helpers
Handles all stream-related operations:
- Index with filtering and pagination
- Create/update with Turbo Stream responses
- Delete with confirmation
- Pin/unpin toggle functionality
- Archive/unarchive functionality
- Platform and status filtering
Manages content creators:
- CRUD operations for streamers
- Platform account management
- Associated streams view
Handles event timestamp tracking:
- Create and manage timestamps
- Stream association with time offsets
- Timeline visualization
- Resolve and dismiss actions
Manages admin authentication:
- Login page rendering
- Authentication logic
- Session management
- Logout functionality
app/views/
├── admin/
│ ├── streams/
│ │ ├── index.html.erb # Main streams list
│ │ ├── new.html.erb # New stream form
│ │ ├── edit.html.erb # Edit stream form
│ │ ├── _stream.html.erb # Stream row partial
│ │ └── _form.html.erb # Shared form partial
│ ├── streamers/
│ │ ├── index.html.erb # Streamers list
│ │ ├── show.html.erb # Streamer details
│ │ ├── new.html.erb # New streamer form
│ │ ├── edit.html.erb # Edit streamer form
│ │ └── _form.html.erb # Shared form partial
│ ├── timestamps/
│ │ ├── index.html.erb # Timestamps list
│ │ ├── show.html.erb # Timestamp details
│ │ ├── new.html.erb # New timestamp form
│ │ ├── edit.html.erb # Edit timestamp form
│ │ └── _form.html.erb # Shared form partial
│ ├── sessions/
│ │ └── new.html.erb # Login page
│ └── shared/
│ ├── _flash.html.erb # Flash messages
│ └── maintenance.html.erb # Maintenance mode page
└── layouts/
├── admin.html.erb # Main admin layout
└── admin_login.html.erb # Login page layout
Manages modal dialogs for forms:
- Opens/closes modals
- Handles ESC key and outside clicks
- Integrates with Turbo Frames
Implements real-time search:
- Debounces input (300ms delay)
- Submits form via Turbo
- Maintains filter state
Handles dropdown menus:
- Toggle visibility
- Click outside to close
- Keyboard navigation
Manages advanced filtering:
- Platform selection
- Status filtering
- Date range pickers
The interface uses Tailwind CSS with a custom color scheme:
- Primary: Indigo (buttons, links)
- Success: Green (active status, success messages)
- Danger: Red (delete actions, error states)
- Neutral: Gray (backgrounds, borders)
Used for partial page updates:
#modal- Modal dialog container#streams_list- Streams table and pagination#streamers_list- Streamers table and pagination#timestamps_list- Timestamps table and pagination#flash- Flash message container#sidebar_counts- Live count updates
Provides real-time updates after actions:
- Prepends new streams/streamers/annotations to lists
- Removes deleted items
- Updates flash messages
- Closes modals after successful operations
- Live updates via ActionCable broadcasts
Real-time WebSocket channels:
CollaborativeStreamsChannel- Real-time collaborative editing with cell locking- Automatic UI updates when other admins make changes
- User presence tracking and color-coded indicators
Enhance interactivity:
- Modal Controller: Manages modal lifecycle
- Search Controller: Handles search input debouncing
- Dropdown Controller: Dropdown menu management
- Filters Controller: Advanced filtering interface
- Confirm Controller: Confirmation dialogs
- Flash Controller: Auto-dismiss flash messages
- Character Counter Controller: Shows character count for text inputs
- Mobile Menu Controller: Responsive navigation menu
- Collaborative Spreadsheet Controller: Manages real-time collaborative editing
- Cell locking and unlocking
- User presence indicators
- Edit timeout management
- ActionCable integration
- Session-based authentication separate from API JWT
- Secure password storage with bcrypt
- CSRF protection on all forms
- Session timeout after inactivity
- Only users with
adminrole can access - Checks performed in
BaseController - Redirects to login if unauthorized
- Create Controller
module Admin
class YourController < BaseController
before_action :set_item, only: [:show, :edit, :update, :destroy]
def index
@pagy, @items = pagy(
YourModel.includes(:associations),
items: 25
)
end
def new
@item = YourModel.new
end
def create
@item = YourModel.new(item_params)
if @item.save
redirect_to admin_items_path,
notice: 'Item was successfully created.'
else
render :new, status: :unprocessable_entity
end
end
private
def set_item
@item = YourModel.find(params[:id])
end
def item_params
params.require(:your_model).permit(:allowed, :attributes)
end
end
end- Add Routes
namespace :admin do
resources :your_resources do
member do
post :custom_action
end
collection do
get :export
end
end
end- Create Views
- Follow existing patterns in
app/views/admin/ - Use Turbo Frames for dynamic updates
- Apply Tailwind classes for consistency
# Build JavaScript
docker compose exec web yarn build
# Build CSS
docker compose exec web yarn build:css
# Watch mode for development (using profiles)
docker compose --profile donotstart up js
docker compose --profile donotstart up css- Controller Tests
RSpec.describe Admin::StreamsController do
let(:admin) { create(:user, :admin) }
before { sign_in(admin) }
describe "GET #index" do
it "returns success" do
get :index
expect(response).to be_successful
end
end
end-
Assets not loading
- Run
yarn build && yarn build:css - Check that symlinks exist in
public/assets/ - Clear browser cache
- Run
-
Turbo not working
- Ensure
data-turbo-frameattributes are correct - Check browser console for JavaScript errors
- Verify Stimulus controllers are registered
- Ensure
-
Authentication issues
- Check session configuration in
application.rb - Verify middleware stack includes session support
- Ensure cookies are enabled in browser
- Check session configuration in
- Enable Turbo debugging
Turbo.session.drive = false // Disable Turbo temporarily- Check Stimulus controllers
// In browser console
Stimulus.controllers- Rails logs
docker compose logs -f web
tail -f log/development.log-
Keep controllers thin
- Use scopes and filters in models
- Extract complex logic to service objects
-
Optimize queries
- Use
includesto avoid N+1 queries - Implement proper pagination
- Use
-
Maintain consistency
- Follow existing UI patterns
- Use shared partials for common elements
- Apply consistent Tailwind classes
-
Enhance progressively
- Ensure basic functionality works without JavaScript
- Add Stimulus enhancements on top
- Test with JavaScript disabled
- Dashboard with analytics and metrics
- Bulk operations for streams and timestamps
- Advanced user permissions and roles
- Comprehensive activity logging
- Export functionality for all data types
- API for admin operations
- Mobile-responsive improvements
- Advanced search with Elasticsearch
- Implement caching for frequently accessed data
- Add background jobs for heavy operations
- Optimize asset delivery with CDN
- Implement infinite scroll for large lists