Invece di memorizzare se l'utente è attivo \ inattivo, è meglio memorizzare alcuni attributi che possono essere controllati dall'utente per ogni azione; come in, ogni volta che l'utente prova a fare qualcosa che richiede l'autenticazione, controllerà che questo attributo corrisponda prima che proceda.
Si consiglia di effettuare le seguenti operazioni;
Innanzitutto, creare un hash per identificare univocamente l'utente ogni volta che si accede. Immagino che uno sha1
di time()
sia sufficiente per evitare collisioni.Qualunque cosa scegliate, assicurarsi che sia abbastanza variato in modo che un altro utente login avrà un incredibilmente basso possibilità di ricevere lo stesso hash (ad esempio, non hash l'indirizzo IP o del browser user-agent, in quanto questi non sono variati abbastanza).
In secondo luogo, conservare questo hash nel database e l'utente del session al momento della log in. In questo modo si efficacemente 'log out' l'utente precedente, come l'hash dovrebbe essere diverso ogni volta che qualcuno accede.
Dal momento che stiamo usando le sessioni, un cookie deve essere posto automaticamente nel browser dell'utente che conterrà un ID univoco che identifica l'utente ai suoi dati di sessione. I contenuti del cookie non sono davvero preoccupanti.
Successivamente, creare una funzione denominata authenticateUser()
o simile, che verrà richiamata all'inizio di ogni script per garantire che l'utente sia autenticato. Questo script dovrebbe interrogare il database, controllando se un utente con l'ID dell'utente ha un hash che corrisponde all'hash dell'utente.
Ad esempio:
function authenticateUser($id, $hash, $databaseLink) {
# SQL
$sql = 'SELECT EXISTS(
SELECT 1
FROM `tbl_users`
WHERE `id` = \''.mysql_real_escape_string($id).'\'
AND `hash` = \''.mysql_real_escape_string($hash).'\'
LIMIT 1
);';
# Run Query
if ($query = mysql_query($sql, $databaseLink)) {
# Get the first row of the results
# Assuming 'id' is your primary key, there
# should only ever be one row anyway.
$result = mysql_fetch_row($query);
# Casting to boolean isn't strictly necessary here
# its included to indicate the mysql result should
# only ever been 1 or 0.
return (bool)($result[0]);
} else {
# Query error :(
return false;
}
}
Poi, abbiamo semplicemente passare authenticateUser()
dell'utente ID
, hash
(per i dati di sessione) e una database link
(per una connessione al database si dovrà aver aperto in precedenza).
Se authenticateUser()
restituisce true
, l'utente è autenticato. Se false
, l'utente non è OR il database non è disponibile o c'è un errore SQL.
Si prega di notare, tuttavia, che questo aumenterà il carico del server come una richiesta di database viene inviata una volta per ogni richiesta di pagina. Probabilmente non è del tutto saggio farlo su progetti giganti in cui migliaia di persone si collegano in un dato momento. Sono sicuro che qualcuno può suggerire miglioramenti.
Inoltre, attendere che il cookie scada non è il modo migliore per forzare le persone che sono state inattive a disconnettersi, poiché non si dovrebbe mai fidarsi dei cookie. Invece, è possibile aggiungere in una colonna chiamata last_active
che è possibile aggiornare ogni volta che l'utente è autenticato. Questo aumenterà anche il carico del server, ma vi permetterà di ignorare manualmente stantii log-in rimuovendo il hash
per gli utenti che erano, diciamo, inattivo per 3 ore.
Il bit di domanda reale di questo ("come posso disconnettere gli utenti che diventano inattivi?"), È stato chiesto qui prima (vedi http://stackoverflow.com/questions/247412/) –