class User < ApplicationRecord has_secure_password has_many :sessions, dependent: :destroy has_many :images, dependent: :destroy normalizes :email_address, with: ->(e) { e.strip.downcase } validates :email_address, presence: true, uniqueness: true validates :name, presence: true # Session security settings attribute :require_two_factor, :boolean, default: false attribute :session_timeout_minutes, :integer, default: 60 attribute :notify_on_new_login, :boolean, default: true attribute :max_sessions, :integer, default: 5 # 确保 roles 字段始终是数组 # attribute :roles, :json, default: -> { [] } serialize :roles, coder: JSON, yaml: true # 定义可用的角色 AVAILABLE_ROLES = %w[admin editor viewer] # 添加角色 def add_role(role) return unless AVAILABLE_ROLES.include?(role.to_s) current_roles = (roles || []).map(&:to_s) current_roles << role.to_s unless current_roles.include?(role.to_s) update(roles: current_roles) end # 移除角色 def remove_role(role) current_roles = (roles || []).map(&:to_s) current_roles.delete(role.to_s) update(roles: current_roles) end # 检查是否有指定角色 def has_role?(role) Rails.logger.info("roles#{roles.class}") (roles || []).map(&:to_s).include?(role.to_s) end # 向后兼容的 admin? 方法 def admin? has_role?("admin") end def security_settings { require_two_factor: require_two_factor, session_timeout_minutes: session_timeout_minutes, notify_on_new_login: notify_on_new_login, max_sessions: max_sessions } end def enforce_max_sessions return unless max_sessions > 0 # Get all sessions except the current one, ordered by last activity other_sessions = sessions.where.not(id: Current.session&.id).order(updated_at: :desc) # If we have more sessions than allowed, destroy the oldest ones if other_sessions.count >= max_sessions sessions_to_remove = other_sessions.offset(max_sessions - 1) sessions_to_remove.destroy_all end end def notify_on_new_login? notify_on_new_login end end