Login automático com trilhos?
-
20-09-2019 - |
Pergunta
Estou tentando criar um sistema de autenticação simples com o plug-in de autenticação de Rails e estou apenas me perguntando como funciona, porque não consigo descobrir quais são os requisitos para os cookies e como fazê-lo assim O navegador sempre se lembra de você (por mais de 6 meses).
Algumas perguntas:
1) Como você se lembra de_me para o RUBY's RESTful_authentication? Não consigo encontrar uma boa linha para resolver esse problema ...
Se um usuário se inscrever e verificar "Lembre -se de mim", como o aplicativo Rails recebe a sessão/cookie sem que o usuário faça nada além de ir para a página na próxima vez que eles vão para a página, digamos três meses depois?
2) Preciso enviar algum tipo de informação ao servidor, como o endereço IP do seu ou algo assim? O que é cookies[:auth_token]
, onde isso é definido?
O objetivo é: eu não quero que eles tenham que inserir o e -mail/senha novamente, como o StackOverflow funciona :)
Solução
Aqui está o que estamos fazendo (amplamente retirado do sistema autenticado) ... Este é o método do controlador que lida com o login que estamos executando ...
def login
if logged_in?
flash[:notice] = "You are already logged in."
redirect_to "/" and return
end
unless request.post?
render :layout => 'task' and return
end
self.current_user = User.authenticate(params[:login], params[:password])
if logged_in?
if params[:remember_me].to_i == 1
self.current_user.remember_me
cookies[:auth_token] = {:domain => "#{DOMAIN}", :value => self.current_user.remember_token , :expires => self.current_user.remember_token_expires_at }
else
self.current_user.forget_me
cookies.delete(:auth_token, :domain => "#{DOMAIN}")
cookies[:auth_token] = nil
end
current_user.last_seen_at = Time.now
current_user.save
session[:notice] = "You logged in successfully"
flash[:notice] = "You logged in successfully"
redirect_back_or_default(:controller => 'dashboard') and return
#redirect_back_or_default(:controller => 'index', :action => 'index') and return
else
if $failed_login_counter.add_attempt(params[:login]) > MAXIMUM_LOGIN_ATTEMPTS
logger.info("login rate limiter kicking in, #{MAXIMUM_LOGIN_ATTEMPTS} login attempts failed")
redirect_to "/denied.html" and return
end
flash[:error] = "Unable to authenticate username and password"
render(:layout => 'task') and return
end
end
E use isso para logout
def logout
current_user.last_seen_at = Time.now
current_user.save
self.current_user.forget_me if logged_in?
cookies.delete(:auth_token, :domain => "#{DOMAIN}")
reset_session
flash[:notice] = "You have been logged out."
#redirect_to :back
redirect_back_or_default(:controller => 'index', :action => 'index') and return
end
Então - em seu aplicativo.rb você precisará de algo como:
before_filter :login_from_cookie
def login_from_cookie
return unless cookies[:auth_token] && !logged_in?
user = User.find_by_remember_token(cookies[:auth_token])
if user && user.remember_token?
user.remember_me
self.current_user = user
cookies[:auth_token] = { :domain => "#{DOMAIN}", :value => self.current_user.remember_token , :expires => self.current_user.remember_token_expires_at }
flash[:notice] = "#{self.current_user.login}, you have logged in successfully"
end
end
E - no seu modelo de usuário tem alguns métodos como este:
# Encrypts some data with the salt.
def self.encrypt(password, salt)
Digest::SHA1.hexdigest("--#{salt}--#{password}--")
end
# Encrypts the password with the user salt
def encrypt(password)
self.class.encrypt(password, salt)
end
def remember_token?
remember_token_expires_at && Time.now.utc < remember_token_expires_at
end
# These create and unset the fields required for remembering users between browser closes
def remember_me
self.remember_token_expires_at = 2.weeks.from_now.utc
self.remember_token = encrypt("#{email}--#{remember_token_expires_at}")
save(false)
end
def forget_me
self.remember_token_expires_at = nil
self.remember_token = nil
save(false)
end
Outras dicas
Sinceramente, não tenho certeza de que a implementação específica. Mas um método de autenticação comum é passar uma versão de hash do usuário/senha com cada solicitação como cabeçalho. Como alternativa, você pode usar um valor de cookie de hash como cabeçalho.
Eu também vi sistemas híbridos que envolvem ambos. Você passa na sessão, se souber, além do usuário/Pass. Em seguida, o lado do servidor, se a sessão for válido, usa isso e pode cache a sessão -> relacionamento do usuário para desempenho. Se a sessão for inválida, ela tenta autenticar usando o usuário/passagem.
Nesse tipo de sistema, você passaria a sessão de volta à resposta como cabeçalho.
É claro que esse é apenas um rápido resumo de como um sistema pode funcionar, não como a biblioteca da Ruby.
Você pode encontrar aqui um tutorial inteiro sobre autenticação RESTful.http://railsforum.com/viewtopic.php?id=14216&p=13