2016-07-23 2 views
-1

Я начинаю работать с Ruby on Rails, и это рубин на рельсах, который был разработан кем-то.Ruby on Rails Ошибка ERR_TOO_MANY_REDIRECTS для данной роли пользователя

Существует 2 типа пользователей: зарегистрированный пользователь с ролью пользователя и зарегистрированный пользователь с ролью «admin».

Это слишком много перенаправлений происходит только в том случае, если роль пользователя = «пользователь», но не так, если пользователь является «администратором». Я еще не понял, почему.

Во-первых, если пользователь является администратором, я получаю это в журнале:

Started GET "/" for ::1 at 2016-07-22 18:18:17 -0700 
Processing by ProductsController#home as HTML 
    ^[[1m^[[35mUser Load (0.1ms)^[[0m SELECT "users".* FROM "users" WHERE "users"."id" = ? ORDER BY "users"."id" ASC LIMIT 1 [["id", 11]] 
controller_path: products 
resource: product 
method: product_params 
after the parms setting => ${params} 
Debugging in the Ability.rb... 
User: #<User:0x007fe6d7f0f670> 
user is admin 
    ^[[1m^[[36mProduct Load (0.3ms)^[[0m ^[[1mSELECT "products".* FROM "products"^[[0m 
    ^[[1m^[[35mVersion Load (1.1ms)^[[0m SELECT "versions".* FROM "versions" 
    ^[[1m^[[36mReltype Load (1.0ms)^[[0m ^[[1mSELECT "reltypes".* FROM "reltypes"^[[0m 

и многие другие заявления SQL; Я хотел бы упростить это, но это другой вопрос и еще одна возможность обучения.

Если пользователь является обычным пользователем, то «перенаправление» произойдет сразу после того, как пользователь обычный пользователь

Started GET "/" for ::1 at 2016-07-22 18:25:23 -0700 
Processing by ProductsController#home as HTML 
    ^[[1m^[[36mUser Load (0.1ms)^[[0m ^[[1mSELECT "users".* FROM "users" WHERE "users"."id" = ? ORDER BY "users"."id" ASC LIMIT 1^[[0m [["id", 11]] 
controller_path: products 
resource: product 
method: product_params 
after the parms setting => ${params} 
Debugging in the Ability.rb... 
User: #<User:0x007fe6d13dca88> 
user is regular user 
Redirected to http://localhost:3000/ 
Completed 302 Found in 6ms (ActiveRecord: 0.1ms) 


Started GET "/" for ::1 at 2016-07-22 18:25:23 -0700 
Processing by ProductsController#home as HTML 
    ^[[1m^[[35mUser Load (0.1ms)^[[0m SELECT "users".* FROM "users" WHERE "users"."id" = ? ORDER BY "users"."id" ASC LIMIT 1 [["id", 11]] 
controller_path: products 
resource: product 
method: product_params 
...repeat... for many more 

Я думаю, что целевая страница пытается вытянуть все данные для использования на этой странице и каждый SQL запускает перенаправление ... Но сначала мне нравится находить, почему это делает разницу между пользователем с ролью пользователя и роли admin. Я буду беспокоиться об оптимизации позже. Любая помощь будет высоко ценится.

Вот конфиг/routes.rb

Rails.application.routes.draw do 
    resources :groupings 
    resources :platforms 
    resources :versions 
    resources :reltypes 
    resources :products 

    # Devise stuff 
    devise_for :users 
    devise_scope :user do 
    get '/login' => 'devise/sessions#new' 
    get '/logout' => 'devise/sessions#destroy' 
    end 

    resources :users, :controller => "users" 
    unauthenticated :user do 
    resources :products, only: [:index, :show] 
    resources :versions, only: [:index, :show] 
    resources :reltypes, only: [:index, :show] 
    resources :platforms, only: [:index, :show] 
    resources :groupings, only: [:index, :show] 
    end 

    # You can have the root of your site routed with "root" 
    root to: 'products#home' 

    namespace :api, :defaults => {:format => :json} do 
    resources :platforms 
    resources :versions 
    resources :reltypes 
    resources :products 
    resources :groupings 
    end 
end 

Далее контроллеры/application.rb

class ApplicationController < ActionController::Base 
    # include DeviseTokenAuth::Concerns::SetUserByToken 
    # Prevent CSRF attacks by raising an exception. 
    # For APIs, you may want to use :null_session instead. 
    protect_from_forgery with: :exception 

    # Devise: redirect to login page if user not logged in 
    before_action :authenticate_user! 

    before_filter do 
    resource = controller_path.singularize.to_sym 
    method = "#{resource}_params" 
    Rails.logger.debug("controller_path: #{controller_path}") 
    Rails.logger.debug("resource: #{resource}") 
    Rails.logger.debug("method: #{method}") 

    params[resource] &&= send(method) if respond_to?(method, true) 
    end 

    protected 

    def configure_permitted_parameters 
    devise_parameter_sanitizer.for(:sign_up) {|u| u.permit(:email, :password, :password_confirmation, roles: [])} 
    end 

    # CanCan: if user authorization fails, catch and modify 
    check_authorization :unless => :devise_controller? 

    rescue_from CanCan::AccessDenied do |exception| 
    redirect_to root_url, :alert => exception.message 
    end 
end 

Вот модели/user.rb

class User < ActiveRecord::Base 
    devise :database_authenticatable, :registerable, 
    :recoverable, :rememberable, :trackable, :validatable 

    before_save :default_values 

    def default_values 
    # self.role ||= 'user' 
    self.role = "user" 
    end 

    def is?(requested_role) 
    self.role == requested_role 
    end 
end 

Наконец, Я нашел эти модели/activity.rb (я попытался включить некоторые инструкции для отладки:

class Ability 
    include CanCan::Ability 

    def initialize(user) 
    # Define abilities for the passed in user here. For example: 
    # 
    user ||= User.new # guest user (not logged in) 
    Rails.logger.debug("Debugging in the Ability.rb...") 
    Rails.logger.debug("User: #{user}") 

    if user.is? "admin" 
     Rails.logger.debug("user is admin") 
     can :manage, :all 
    else 
     Rails.logger.debug("user is regular user") 
     can :read, :all 
    end 
    end 
end 

Добавлены контроллеры/products_controller.rb (как предложено Шри Вишну Тотакура). Я пропустил код для обновления/уничтожения, чтобы сохранить небольшое пространство.

class ProductsController < ApplicationController 
    load_and_authorize_resource #for CanCan 

    before_action :set_product, only: [:show, :edit, :update, :destroy] 

    # GET /products 
    # GET /products.json 
    def index 
    @products = Product.all 
    end 

    def home 
    @products = Product.all 
    @versions = Version.all 
    @platforms = Platform.all 
    @reltypes = Reltype.all 
    @prevrels = Prevrel.all 
    end 

    # GET /products/1 
    # GET /products/1.json 
    def show 
    end 

    # GET /products/new 
    def new 
    # puts "params for new: " 
    # puts params 
    @product = Product.new 
    end 

    # GET /products/1/edit 
    def edit 
    end 

    # POST /products 
    # POST /products.json 
    def create 
    puts "params for create: " 
    puts params 
    @product = Product.new(product_params) 

    respond_to do |format| 
     if @product.save 
     format.html { redirect_to @product, notice: 'Product was successfully created.' } 
     format.json { render :show, status: :created, location: @product } 
     else 
     format.html { render :new } 
     format.json { render json: @product.errors, status: :unprocessable_entity } 
     end 
    end 
    end 

    def update 
    ... 
    end 

    def destroy 
    ... 
    end 

    private 
    # Use callbacks to share common setup or constraints between actions. 
    def set_product 
     @product = Product.find(params[:id]) 
     @versions = @product.versions 
    end 

    # Never trust parameters from the scary internet, only allow the white list through. 
    def product_params 
     params.require(:product).permit(:name) 
    end 
end 
+0

Возможно, существует код, который вызывает это в действии 'ProductsController # home'. Было бы полезно, если бы вы могли вставить код из 'ProductsController' – aBadAssCowboy

ответ

1

кажется, что проблема здесь:

rescue_from CanCan::AccessDenied do |exception| 
    redirect_to root_url, :alert => exception.message 
end 

По какой-то причине, когда вы не являетесь администратором, то возбуждается исключение, и вы попадаете в петлю, как вы перенаправлять ProductsController#home который является root to: 'products#home'

Я не вижу ваш код контроллера продукта, но проблема должна быть там. Дай мне знать.

+0

только что опубликованного/добавленного. Благодаря! –

0

Поскольку я не могу прокомментировать или отменить ответ Paulo Я оставляю это здесь для всех, имеющих аналогичную проблему.

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

Я использовал devise/cancancan.

В частности, у меня был companies_controller.rb.

Кроме того, в before_action у меня было что-то вроде следующего

before_action :set_company, only: :show 

и действия set_company был этот

def set_company 
    ... 
    authorize! params[:action].to_sym, @company || Company 
end 

Как только я удалил Авторизовать! вызовите цикл переадресации. Я не понял, что вызвало цикл, поскольку мои роли пользователя выглядели просто отлично, но это определенно было причиной.