Devise authentication error when entering site'

2019-05-11 22:36发布

问题:

When user enters our web site's root or logs out, Devise authentication displays "You need to sign in or sign up before continuing" the first time. After page reload this message disappears.

Root of our web site is set to controller which has:

before_filter :authenticate_user!

We need this controller to be the root. How to eliminate this message?

回答1:

The correct solution would be to set an authenticated block as noted in the official wiki: https://github.com/plataformatec/devise/wiki/How-To:-Require-authentication-for-all-pages

  authenticated :user do
    root to: 'home#index', as: :authenticated_root
  end
  root to: redirect('/users/sign_in')

The scoped authenticated block will only be called once they are logged in, so you can happily direct users to a controller of your choice. In the example it redirects them to the sign in page when unauthenticated, but this could be any action in your routes.



回答2:

Do you want to get rid of the message on just the index? If so you can just do something like this:

before_filter :authenticate_user!, :except => [:index]

You can add other actions to the array as well.

Note this won't call authenticate_user! on the specified actions, so make sure the user doesn't need to be authenticated for the given actions!



回答3:

I did not find the solution better than defining

unauthenticated: ''

in /config/locales/devise.en.yml file.



回答4:

Assuming that you have encapsulated your devise error messages as shown below.

<p class="notice"><%= notice %></p>
<p class="alert"><%= alert %></p>

You can add the following CSS code to your index view file for the root controller.

<style type="text/css">
  .notice, .alert { visibility: hidden; }
</style>

This should hide the error messages from root of your website.



回答5:

In a scenario where all of your pages (except login, signup, etc) are protected against before_action :authenticate_user!, I'd override Devise's SessionController as so:

app/controllers/sessions_controller.rb

class SessionsController < Devise::SessionsController
  def new
    if flash[:alert] == unauthenticated_message
      flash.delete(:alert) unless requested_protected_page?
    end
    super
  end

  private

  def requested_protected_page?
    session[:user_return_to] != root_path
  end

  def unauthenticated_message
    I18n.t('devise.failure.unauthenticated')
  end
end

And then tell your config/routes.rb file to use that overridden controller:

devise_for :users, controllers: {
  sessions: :sessions,
}


回答6:

You may create a separate action in your controller, just to resolve whether user is logged in or not and then redirect to desired place.

class WelcomeController < ApplicationController
  skip_before_filter :authenticate_user!, only: :root

  def index
  end

  def root
    flash.keep
    redirect_to current_user ? welcome_index_path : new_user_session_path
  end
end

This should work, of course you should have in your ApplicationController

before_filer: authenticate_user!

and in routes root configured to welcome#root