I have two models User and Admin(with RailsAdmin) that use Devise. I sign in as user and then sign in as admin. But the result of signing out from one of that models is signing out of two models at the same time. How can I fix it?
Please, help :)
The problem was in one string in config/initializers/devise.rb:
Default:
# Configure sign_out behavior.
# Sign_out action can be scoped (i.e. /users/sign_out affects only :user scope).
# The default is true, which means any logout action will sign out all active scopes.
# config.sign_out_all_scopes = true
Need:
config.sign_out_all_scopes = false
The scope of Devise is the entire application -- you sign in to the site, not a model. Perhaps you want to add the distinction of roles - a user may have one or more roles that allow them certain privileges. Devise just gets you an authenticated user. Consider a gem such as CanCan which provides support for "role based authorization".
Related
If I've got a rails application and I'd like to add authentication to with Devise, how would I allow users who have a null password in the database to sign in without one?
I'm interested in hearing answers along the lines of the lifecycle and what files I'd have to author to get it done.
Step 1: Allow the record to be saved.
Step 2: Sign in the record
To allow the record to be saved, you'll want to do validations yourself. I describe here how to do custom validations: http://jessewolgamott.com/blog/2011/12/08/the-one-where-devise-validations-are-customized/ .... In your case, you'll want to remove the password validations.
To sign in the record, you'll need to have a custom sign in path. You can override the devise sessions controller, but this could do the trick:
class SessionsController < ApplicationController
def create
user = User.find_by_email!(params[:session][:email])
sign_in user
redirect_to root_path
end
end
It turns out, Devise is built on Warden. This means that I only have to create my own custom Warden strategy:
https://github.com/hassox/warden/wiki/Strategies
I want to use devise' token_authenticatable helper to authenticate users against the system.
I found some older documentations where a method named valid_authentication_token?(...) is used but couldn't find the same in newer devise version.
So what's the right way to authenticate a user?
Should I request the Model for user with named token and checking if email-adresses match?
Thanks a lot for your help.
PascalTurbo
If you add
t.token_authenticatable
to you user ActionRecord, and add
devise :token_authenticatable
to your User model
and specify which param is your token key in config/initializer/devise, something like this:
config.token_authentication_key = :auth_token
then controllers that use
before_filter :authenticate_user! # Tell devise to use :user map
to authenticate. after the authenticate_user!, individual methods can test using
user_signed_in?
will authorize users either by the login session or the devise authorization token that is passed on the query string or passed using HTTP basic authentication. See Devise helper code for details.
I'm using devise for authentication. How can I set the sign-in scope? For example, say I only want to authenticate the user for the scope:
User.where(:active => true)
Am I being clear? It's simple, but I can elaborate more if needed.
(I realize there is a lockable module, but my actual scope isn't for active users, it's more like current_site.users, where the current_site is based off the domain)
Just overwrite these two methods in your User model to check if the active flag is true:
# Called by Devise to see if an user can currently be signed in
def active_for_authentication?
active? && super
end
# Called by Devise to get the proper error message when an user cannot be signed in
def inactive_message
!active? ? :deactivated : super
end
And in your devise.en.yml, add the proper error message:
devise:
failure:
deactivated: "Luke, I'm your father and your account was locked!"
You could use default_scope... but that might get in your way.
Why not override devise's find_for_database_authentication method? See the wiki.
I would like to manually create new Users, without forcing them to verify their email address.
The idea is to allow existing users to automatically add their friends without requiring their registration. It makes sense for the business case I'm working to solve.
How can this be achieved with Devise?
The skip_confirmation! method is available to any confirmable model.
#user = User.new params[:user]
#user.skip_confirmation! # Sets confirmed_at to Time.now, activating the account
#user.save
The user account will be activated though. If you don't want that, continue reading.
Devise uses conditional callbacks to generate the confirmation token and send the email. The callbacks will be called only if confirmation_required? returns true. Redefine it on your model:
def confirmation_required?
false
end
However, this will make the active_for_authentication? method always return true because it takes whether or not confirmation is required into account. We have to redefine that as well:
def active_for_authentication?
confirmed? || confirmation_period_valid?
end
This way, the account will stay inactive and no confirmation email will be sent. You will have to manually activate the user by calling confirm! on the record or just setting confirmed_at to any date.
It's quite a hack, but it should work.
For reference: confirmable.rb
I just want to add for future reference that since Devise 2.2 there is now a skip_confirmation_notification! method available as well which basically does everything from Matheus' post without redefining the methods in the model.
In Devise, I'm signing in my user like this:
sign_in_and_redirect(:user, user)
In the default sign in page, there's a checkbox that the user can select so that they don't have to sign in again when they return to the site. But when you do the sign in with the sign_in_and_redirect(:user, user) line, I can't work out how to set that parameter to yes. Does anyone know how? Thanks for reading.
current_user.remember_me!
https://github.com/plataformatec/devise/blob/master/lib/devise/models/rememberable.rb#L54
Note that this only updates the remember_created_at value of the user record. But for this to work correctly, a validation token also needs to be stored in the Devise cookie. To achieve both these things, follow Dmytrii's advise and user the remember_me <USER> controller method instead:
include Devise::Controllers::Rememberable
...
remember_me <USER_OBJECT>
Did some testing. Presenting the findings for others.
The simplest solution, assuming the user object has the rememberable module defined on the devise declarable, is to set remember_me to true on the user before sign in and redirect:
#user.remember_me = true
sign_in_and_redirect(#user, :event => :authentication)