class PayoutService def initialize(promoter_id = nil) @promoter_id = promoter_id end def process_pending_payouts scope = Earnings.pending scope = scope.where(user_id: @promoter_id) if @promoter_id.present? scope.includes(:user, :order, :event).group_by(&:user_id).each do |user_id, earnings| process_payout_for_user(user_id, earnings) end end def process_event_payout(event) return unless event.can_request_payout? earnings = event.earnings.pending total_cents = earnings.sum(:amount_cents) fees_cents = event.total_fees_cents net_cents = total_cents - fees_cents return if net_cents <= 0 begin event.update!(payout_status: :processing) transfer = Stripe::Transfer.create( amount: net_cents / 100, currency: "eur", destination: event.user.stripe_account_id, description: "Payout for event: #{event.name}", metadata: { event_id: event.id, promoter_id: event.user_id, gross_amount: total_cents, fees: fees_cents, net_amount: net_cents } ) earnings.update_all( status: :paid, fee_cents: fees_cents, net_amount_cents: net_cents, stripe_payout_id: transfer.id ) event.update!( payout_status: :completed, payout_requested_at: Time.current ) Rails.logger.info "Processed event payout #{transfer.id} for event #{event.id}: €#{net_cents / 100.0}" rescue Stripe::StripeError => e event.update!(payout_status: :failed) Rails.logger.error "Payout failed for event #{event.id}: #{e.message}" raise e end end private def process_payout_for_user(user_id, earnings) user = User.find(user_id) return unless user.stripe_account_id.present? total_amount_cents = earnings.sum(:amount_cents) begin transfer = Stripe::Transfer.create( amount: total_amount_cents / 100, currency: "eur", destination: user.stripe_account_id, description: "Payout for promoter #{user_id} - Total: €#{total_amount_cents / 100.0}", metadata: { promoter_id: user_id, earnings_ids: earnings.map(&:id).join(",") } ) earnings.update_all( status: :paid, stripe_payout_id: transfer.id ) Rails.logger.info "Processed payout #{transfer.id} for promoter #{user_id}: €#{total_amount_cents / 100.0}" rescue Stripe::StripeError => e Rails.logger.error "Failed to process payout for promoter #{user_id}: #{e.message}" end end end