This commit implements a complete promoter system that allows professional users (is_professionnal: true) to manage events with advanced analytics and controls. ## Key Features Added: ### Role-Based Access Control - Update User#can_manage_events? to use is_professionnal field - Add promoter? alias method for semantic clarity - Restrict event management to professional users only ### Enhanced Navigation - Add conditional "Créer un événement" and "Mes événements" links - Display promoter navigation only for professional users - Include responsive mobile navigation with appropriate icons - Maintain clean UI for regular users ### Comprehensive Promoter Dashboard - Revenue metrics with total earnings calculation - Tickets sold counter across all events - Published vs draft events statistics - Monthly revenue trend chart (6 months) - Recent events widget with quick management actions - Recent orders table with customer information ### Advanced Analytics - Real-time revenue calculations from order data - Monthly revenue trends with visual progress bars - Event performance metrics and status tracking - Customer order history and transaction details ### Event Management Workflow - Verified existing event CRUD operations are comprehensive - Maintains easy-to-use interface for event creation/editing - State management system (draft → published → cancelled) - Quick action buttons for common operations ### Documentation - Comprehensive implementation guide in docs/ - Technical details and architecture explanations - Future enhancement recommendations - Testing and deployment considerations ## Technical Implementation: - Optimized database queries to prevent N+1 problems - Proper eager loading for dashboard performance - Responsive design with Tailwind CSS components - Clean separation of promoter vs regular user features - Maintainable code structure following Rails conventions 🤖 Generated with [Claude Code](https://claude.ai/code) Co-Authored-By: Claude <noreply@anthropic.com>
106 lines
4.5 KiB
Ruby
Executable File
106 lines
4.5 KiB
Ruby
Executable File
# Controller for static pages and user dashboard
|
|
# Handles basic page rendering and user-specific content
|
|
class PagesController < ApplicationController
|
|
before_action :authenticate_user!, only: [ :dashboard ]
|
|
|
|
# Homepage showing featured events as landing page
|
|
#
|
|
# Display homepage with featured events and site metrics for all users
|
|
def home
|
|
# Featured events for the main grid (6-9 events like Shotgun)
|
|
@featured_events = Event.published.featured.includes(:ticket_types).limit(9)
|
|
|
|
# If no featured events, show latest published events
|
|
if @featured_events.empty?
|
|
@featured_events = Event.published.includes(:ticket_types).order(created_at: :desc).limit(9)
|
|
end
|
|
|
|
# Upcoming events for additional content
|
|
@upcoming_events = Event.published.upcoming.limit(6)
|
|
|
|
# Site metrics for landing page (with realistic fake data for demo)
|
|
@total_events = [ Event.published.count, 50 ].max # At least 50 events for demo
|
|
@total_users = [ User.count, 2500 ].max # At least 2500 users for demo
|
|
@events_this_month = [ Event.published.where(created_at: 1.month.ago..Time.current).count, 12 ].max # At least 12 this month
|
|
@active_cities = 5 # Fixed number for demo
|
|
end
|
|
|
|
# User dashboard showing personalized content
|
|
# Accessible only to authenticated users
|
|
def dashboard
|
|
# User's orders with associated data
|
|
@user_orders = current_user.orders.includes(:event, tickets: :ticket_type)
|
|
.where(status: [ "paid", "completed" ])
|
|
.order(created_at: :desc)
|
|
.limit(10)
|
|
|
|
# Draft orders that can be retried
|
|
@draft_orders = current_user.orders.includes(tickets: [ :ticket_type, :event ])
|
|
.can_retry_payment
|
|
.order(:expires_at)
|
|
|
|
# Promoter-specific data if user is a promoter
|
|
if current_user.promoter?
|
|
@promoter_events = current_user.events.includes(:orders, :tickets)
|
|
.order(created_at: :desc)
|
|
.limit(5)
|
|
|
|
# Revenue metrics for promoter
|
|
@total_revenue = current_user.events
|
|
.joins(:orders)
|
|
.where(orders: { status: ['paid', 'completed'] })
|
|
.sum('orders.total_amount_cents') / 100.0
|
|
|
|
@total_tickets_sold = current_user.events
|
|
.joins(:tickets)
|
|
.where(tickets: { status: 'active' })
|
|
.count
|
|
|
|
@active_events_count = current_user.events.where(state: 'published').count
|
|
@draft_events_count = current_user.events.where(state: 'draft').count
|
|
|
|
# Recent orders for promoter events
|
|
@recent_orders = Order.joins(:event)
|
|
.where(events: { user: current_user })
|
|
.where(status: ['paid', 'completed'])
|
|
.includes(:event, :user, tickets: :ticket_type)
|
|
.order(created_at: :desc)
|
|
.limit(10)
|
|
|
|
# Monthly revenue trend (last 6 months)
|
|
@monthly_revenue = (0..5).map do |months_ago|
|
|
start_date = months_ago.months.ago.beginning_of_month
|
|
end_date = months_ago.months.ago.end_of_month
|
|
|
|
revenue = current_user.events
|
|
.joins(:orders)
|
|
.where(orders: { status: ['paid', 'completed'] })
|
|
.where(orders: { created_at: start_date..end_date })
|
|
.sum('orders.total_amount_cents') / 100.0
|
|
|
|
{
|
|
month: start_date.strftime("%B %Y"),
|
|
revenue: revenue
|
|
}
|
|
end.reverse
|
|
end
|
|
|
|
# Simplified upcoming events preview - only show if user has orders
|
|
if @user_orders.any?
|
|
ordered_event_ids = @user_orders.map(&:event).map(&:id)
|
|
@upcoming_preview_events = Event.published
|
|
.upcoming
|
|
.where.not(id: ordered_event_ids)
|
|
.order(start_time: :asc)
|
|
.limit(6)
|
|
else
|
|
@upcoming_preview_events = []
|
|
end
|
|
end
|
|
|
|
# Events page showing all published events with pagination
|
|
def events
|
|
@events = Event.published.order(created_at: :desc).page(params[:page])
|
|
end
|
|
end
|