web-dev-qa-db-fra.com

Comment tuer une / toutes les sessions php?

J'ai un script de connexion de session php très basique. Je veux forcer la déconnexion d'un certain utilisateur ou forcer la déconnexion de tous les utilisateurs.

Comment puis-je lire toutes les sessions effectuées sur mon site Web et détruire certaines ou toutes les sessions?

24
TDSii

Vous pouvez essayer de forcer PHP pour supprimer toutes les sessions en faisant

ini_set('session.gc_max_lifetime', 0);
ini_set('session.gc_probability', 1);
ini_set('session.gc_divisor', 1);

Cela oblige PHP à traiter toutes les sessions comme ayant une durée de vie de 0 seconde et une probabilité de 100% de se nettoyer.

L'inconvénient est que, quel que soit l'utilisateur malchanceux qui exécute cette première, il y aura une longue pause pendant que PHP fait le nettoyage, surtout s'il y a beaucoup de fichiers de session à parcourir.

Pour un utilisateur particulier, vous devez ajouter du code à votre gestionnaire de session:

 if ($_SESSION['username'] == 'user to delete') {
     session_destroy();
 }

Le garbage collector de PHP n'est pas contrôlable, vous ne pouvez donc pas lui donner des paramètres tels que "supprimer toutes les sessions sauf celles de l'utilisateur X". Il examine strictement les horodatages modifiés en dernier/dernier accès sur les fichiers de session et les compare au paramètre max_lifetime. Il ne traite pas réellement les données de session.

15
Marc B

Vous pouvez utiliser session_save_path() pour trouver le chemin où PHP enregistre les fichiers de session, puis les supprimer à l'aide de unlink() .

6
m4rc

Mise à jour - août 2012

Ce code est basé sur le officiel PHP , et un autre bien écrit extrait sur SO .

<?php
// Finds all server sessions
session_start();
// Stores in Array
$_SESSION = array();
// Swipe via memory
if (ini_get("session.use_cookies")) {
    // Prepare and swipe cookies
    $params = session_get_cookie_params();
    // clear cookies and sessions
    setcookie(session_name(), '', time() - 42000,
        $params["path"], $params["domain"],
        $params["secure"], $params["httponly"]
    );
}
// Just in case.. swipe these values too
ini_set('session.gc_max_lifetime', 0);
ini_set('session.gc_probability', 1);
ini_set('session.gc_divisor', 1);
// Completely destroy our server sessions..
session_destroy();
?>

Fonctionne bien. Des serveurs comme NGinx vous pouvez désactiver, nettoyer le cache, réinitialiser la mémoire, effacer les journaux, etc. et généralement supprimer l'utilisation temporaire. Laissez tomber même les limites de la mémoire.

6
TheBlackBenzKid

Cela dépend du stockage de votre session.

Si vous utilisez PHP stockage de session, ils peuvent se trouver dans le répertoire temporaire de votre serveur. La suppression des fichiers sélectionnés "tuera" la session. Cependant, si votre serveur est en cours d'exécution, ce fichier de session peut être occupé par le processus HTTP et vous ne pourrez pas le supprimer. Regardez simplement l'image ci-dessous. Le fichier nommé en commençant par "+ ~" sont tous des fichiers de session. Screenshot of Session Occupied by Process and could not delete it

Une meilleure solution consiste à utiliser un stockage de session de base de données et à supprimer les sessions sélectionnées à partir de là. Vous pouvez vérifier HTTP_Session2 qui a plusieurs conteneurs .

3
KARASZI István

Pour effacer toutes les sessions à la fois, il faudrait d'abord savoir laquelle session.save_handler est utilisée pour stocker les sessions et localiser le session.save_path pour supprimer toutes les sessions. Pour supprimer la session en cours uniquement, reportez-vous à la documentation de session_destroy() .

Voici quelques exemples courants de suppression de toutes les sessions à l'aide de fichiers standard et de gestionnaires de sauvegarde memcached:

Utilisation du gestionnaire d'enregistrement de fichiers

foreach(glob(ini_get("session.save_path") . "/*") as $sessionFile) {
    unlink($sessionFile);
}

Utilisation du gestionnaire de sauvegarde memcached

$memcached = new Memcached;
$memcached->addServers($listOfYourMemcachedSesssionServers);

// Memcached session keys are prefixed with "memc.sess.key." by default
$sessionKeys = preg_grep("@^memc\.sess\.key\.@", $memcached->getAllKeys());
$memcached->deleteMulti($sessionKeys);

Bien sûr, vous voudrez peut-être envisager de ne le faire que hors bande à partir de vos demandes client HTTP normales, car le nettoyage du stockage de grandes sessions peut prendre un certain temps et avoir des effets secondaires par inadvertance dans un cycle de vie de demande normal.

3
Sherif

Je vais créer un fichier txt contenant le jeton qui a la même valeur que la session de connexion générée à titre de comparaison chaque fois que l'utilisateur est connecté:

if($_SERVER['REQUEST_METHOD'] == 'POST') {
    $token = sha1(uniqid(mt_Rand(), true));
    if($everything_is_valid) {
        // Set login session
        $_SESSION[$_POST['username']] = $token;
        // Create token file
        file_put_contents('log/token.' . $_POST['username'] . '.txt', $token);
        // Just to be safe
        chmod('log/token.' . $_POST['username'] . '.txt', 0600);
    }
}

Vérifie les utilisateurs connectés:

if(isset($_SESSION['charlie']) && file_exists('log/token.charlie.txt') && $_SESSION['charlie'] == file_get_contents('log/token.charlie.txt')) {
    echo 'You are logged in.';
}

Donc, si vous souhaitez forcer la déconnexion de cet utilisateur charlie, supprimez simplement le fichier de jeton:

// Force logout the `charlie` user
unlink('log/token.charlie.txt');
2
Taufik Nurrohman

J'ai trouvé ce code très utile et cela a vraiment fonctionné pour moi

<?php

$path = session_save_path();

$files = glob($path.'/*'); // get all file names
foreach($files as $file){ // iterate files
  if(is_file($file))
    unlink($file); // delete file
}

?>
2
Nahid Sultan

La réponse de Taufik est la meilleure que j'ai pu trouver.
Cependant, vous pouvez encore le modifier
Après avoir authentifié l'utilisateur et créé les variables de session, ajoutez ces lignes:

$token = "/sess_" . session_id();
file_put_contents('log/' . $_SESSION['id'] . '.txt', $token);

Si vous devez forcer l'utilisateur à se déconnecter lors d'un cronjob ou par une demande d'administrateur:

$path = session_save_path();
$file = file_get_contents('log/xxx.txt'); // xxx is user's id
$url = $path.$file;
unlink($url);
0
Robin LeBon