Подтвердить что ты не робот

Где переопределить метод-помощник current_user для создания драгоценного камня

Как я могу переопределить current_user из devem gem. На самом деле мне нужно добавить веб-службы для мобильного приложения.

В настоящее время разрабатывается сеанс управления и "current_user" для веб-приложения.

Теперь мобильное приложение отправит user_id на сервер. Мне нужно переопределить текущего пользователя, как этот

def current_user
  if params[:user_id].blank?
    current_user
  else
    User.find(params[:user_id])
  end   
end

Нужно ли мне модифицировать devise gem как плагин? или что-то еще?
Пожалуйста, подробно объясните, как я новичок в рельсах.

С уважением,

4b9b3361

Ответ 1

Согласно модулю Devise :: Controllers :: Helpers, current_user (вместе со всеми другими помощниками devise) добавляется в ApplicationController, что означает, что вы можете переопределить его следующим образом:

# in application_controller.rb

def devise_current_user
  @devise_current_user ||= warden.authenticate(scope: :user)
end

def current_user
  if params[:user_id].blank?
    devise_current_user
  else
    User.find(params[:user_id])
  end   
end

Ответ 2

Другой ответ, предлагающий наложение метода, на самом деле не является лучшим решением. Doug Английский комментарий - лучшее решение:

# In ApplicationHelper
def devise_current_user
   @devise_current_user ||= warden.authenticate(:scope => :user)
end

Вот причина:

Предположим, вы включили свой ApplicationHelper в свой контроллер. Если вам нужен метод в ApplicationHelper, который полагается на devise_current_user, учитывая решение псевдонима внутри контроллера, вам не повезло.

Но с явным определением метода выше вы можете переместить определение в помощник и вызвать его из других методов, и вы все равно можете включить его в контроллер.

Это полезно, например, когда вы разрабатываете решение для олицетворения пользователя, и вам нужно показать двух разных пользователей в представлении, один для реального администратора (devise_current_user), а другой - олицетворенного пользователя (current_user).

Ответ 3

Предполагая, что мы можем доверять нашим данным сеанса (который зависит от того, вводите ли вы там вход пользователя без надлежащей авторизации или нет), это может работать как Концерн:

module Concerns
  module ControllerWithImpersonation
    extend ActiveSupport::Concern

    included do
      helper_method :devise_current_user
    end

    def current_user
      if session[:impersonated_user_id].blank?
        devise_current_user
      else
        User.find(session[:impersonated_user_id])
      end
    end

    def devise_current_user
      @devise_current_user ||= warden.authenticate(:scope => :user)
    end

  end
end

Я использую это в проекте на данный момент.

Небольшой вопрос (в ответе, извините)... должен ли я знать о любых изменениях в Devise или Warden, которые делают devise_current_user выше устаревшего?

Ответ 4

Ответ Limbo-Peng велик, но его можно немного улучшить, чтобы убедиться, что только администраторы могут это сделать:

Вам также необходимо определить метод is_admin? или is_admin в классе User.

Вы также можете использовать другой ключ, чем user_id, поэтому он никогда не будет противоречить вашим обычным параметрам.

# to impersonate another user, e.g. for customer support
# only admins can do this..
#
alias_method :devise_current_user, :current_user
def current_user
  if ! params[:user_id].blank? \
     && devise_current_user && devise_current_user.is_admin? 
    User.find(params[:user_id])
  else
    devise_current_user
  end
end