class Ban < ApplicationRecord after_create :update_feedback after_create :update_user_on_create after_create :create_mod_action after_destroy :update_user_on_destroy belongs_to :user belongs_to :banner, :class_name => "User" attr_accessible :reason, :duration, :user_id, :user_name validate :user_is_inferior validates_presence_of :user_id, :reason, :duration before_validation :initialize_banner_id, :on => :create scope :unexpired, -> { where("bans.expires_at > ?", Time.now) } scope :expired, -> { where("bans.expires_at <= ?", Time.now) } def self.is_banned?(user) exists?(["user_id = ? AND expires_at > ?", user.id, Time.now]) end def self.reason_matches(query) if query =~ /\*/ where("lower(bans.reason) LIKE ?", query.mb_chars.downcase.to_escaped_for_sql_like) else where("bans.reason @@ plainto_tsquery(?)", query) end end def self.search(params) q = where("true") if params[:banner_name] q = q.where("banner_id = (select _.id from users _ where lower(_.name) = ?)", params[:banner_name].mb_chars.downcase) end if params[:banner_id] q = q.where("banner_id = ?", params[:banner_id].to_i) end if params[:user_name] q = q.where("user_id = (select _.id from users _ where lower(_.name) = ?)", params[:user_name].mb_chars.downcase) end if params[:user_id] q = q.where("user_id = ?", params[:user_id].to_i) end if params[:reason_matches].present? q = q.reason_matches(params[:reason_matches]) end case params[:expired] when "true" then q = q.expired when "false" then q = q.unexpired end case params[:order] when "expires_at_desc" q = q.order("bans.expires_at desc") else q = q.order("bans.id desc") end q end def initialize_banner_id self.banner_id = CurrentUser.id if self.banner_id.blank? end def user_is_inferior if user if user.is_admin? errors[:base] << "You can never ban an admin." false elsif user.is_moderator? && banner.is_admin? true elsif user.is_moderator? errors[:base] << "Only admins can ban moderators." false elsif banner.is_admin? || banner.is_moderator? true else errors[:base] << "No one else can ban." false end end end def update_feedback if user feedback = user.feedback.build feedback.category = "negative" feedback.body = "Banned: #{reason}" feedback.creator_id = banner_id feedback.save end end def update_user_on_create user.update_attribute(:is_banned, true) end def update_user_on_destroy user.update_attribute(:is_banned, false) end def user_name user ? user.name : nil end def user_name=(username) self.user_id = User.name_to_id(username) end def duration=(dur) self.expires_at = dur.to_i.days.from_now @duration = dur end def duration @duration end def expired? expires_at < Time.now end def create_mod_action ModAction.log(%{Banned "#{user_name}":/users/#{user_id} until #{expires_at}}) end end