Accesso automatico con Rails?
-
20-09-2019 - |
Domanda
Sto cercando di ottenere un semplice sistema di autenticazione con il plugin riposante-autenticazione Rails', e chiedo solo come funziona, b / c non riesco a capire quali sono i requisiti per i biscotti, e come fare in modo il browser che si ricorda sempre (per 6+ mesi).
Alcune domande:
1) Come si fa a fare remember_me di per restful_authentication di Ruby? Non riesco a trovare un buon one-liner per risolvere questo problema ...
Se un utente si iscrive e controlli "Ricordati di me", come fa l'applicazione rotaie ottenere la sessione / biscotto senza che l'utente di fare qualsiasi cosa, ma andando alla pagina la prossima volta che vai alla pagina, dire 3 mesi più tardi?
2) Ho bisogno di inviare una sorta di informazioni al server, come il loro indirizzo IP o qualcosa del genere? Qual è cookies[:auth_token]
, dove è quello definito?
L'obiettivo è: non voglio loro di avere a inserire di nuovo la loro e-mail / password, come come funziona StackOverflow:)
Soluzione
Ecco quello che stiamo facendo (in gran parte tratto dal sistema di autenticazione) ... questo è il metodo di controllo che gestisce login che stiamo correndo ...
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 di utilizzare per il 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
Poi - nel vostro application.rb avrete bisogno di qualcosa di simile:
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 - nel modello dell'utente avere alcuni metodi come questo:
# 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
Altri suggerimenti
Io non sono onestamente sicuro che aboout particolare implementazione. Ma un metodo RESTful comune di autenticazione è quello di passare una versione hash della utente / password con ciascuna richiesta di cui un colpo di testa. In alternativa è possibile utilizzare un valore di cookie hash come intestazione.
Ho visto anche sistemi ibridi che coinvolgono entrambi. Si passa nella sessione, se lo conosci, oltre per l'utente / passaggio. Poi lato server se la sessione è valida si utilizza tale e può memorizzare nella cache della sessione -> rapporto utente per le prestazioni. Se la sessione non è valido, tenta di autenticare utilizzando l'utente / passaggio.
In questo tipo di sistema che ci si passa la sessione di nuovo sul problema con un colpo di testa.
Naturalmente questo è solo un breve riassunto di come un sistema potrebbe funzionare, non come biblioteca di rubino fa.
Potete trovare qui un intero tutorial su autenticazione riposante. http://railsforum.com/viewtopic.php?id=14216&p=13