8768 sujets

Développement web côté serveur, CMS

Bonjour à tous !
Je me présente, Akariu Smiley lol , infographiste autodidacte et qui tente de se débrouiller avec php, mysql et compagnie en puisant dans tous les tutos que le web peut offrir (et ça ne manque pas).

Voilà, si je suis là c'est que j'ai un petit problème avec une session.
Je dois créer une section d'administration d'un site car les personnes qui vont le mettre à jour y connaissent que dalle et le site doit pourtant continuer de fonctionner nickel.
J'ai donc créé des pages de création/modification du contenu. Lorsque je quitte ses pages, un lien me permet de déconnecter ma session utilisateur, sensé rendre les pages d'administration inaccessibles.
Mais voilà, il suffit de cliquer sur la flèche <- du navigateur, de renvoyer les données transmises en POST (le navigateur le propose lui-même!!!) et hop! On la session se rouvre sans avoir même à connaître login et password... Smiley eek

Et ça, je veux pas que ça se passe !
Comment puis-je faire...?

Le code du lien de déconnexion :

<p><br><br><a href="disconnected.php" target="_self">Se déconnecter</a></p></body>


Le code de la page disconnected.php :
<?php
// On appelle la session
session_start();

// On écrase le tableau de session
$_SESSION = array();

// On détruit la session
session_destroy();
?>


Je suis sûr que j'ai fait une erreur de procédure énorme mais je ne la vois pas...
Merci d'avance à tous et bonne nuit! Smiley biggol

Akarius
Salut Akarius Smiley cligne ,

Et oui, c'est le problème des sessions : bien souvent les utilisateurs ne se déconnectent pas. Cela dit le cookie de session (par défaut PHPSESSID) à une durée de vie limitée (souvent jusqu'à la fermeture du navigateur) mais cela n'est pas très sécurisé, notamment sur un ordinateur public. Pour limiter ce risque on utilise la méthode du timeout expliquée sur cette page. Voir également celle-ci pour un logout amélioré.

A+ Smiley smile
Ok, merci beaucoup pour ta réponse rapide!
Je vais potasser tout ça et tenter d'améliorer mon truc..
Smiley smile
Bonne nuit!
Bonjour, ton problème m'étonne.

Par pur hasard, n'ouvrirais tu pas deux "session_start()" ?

Sinon, tu détruis proprement les sessions, mais si j'ai bien compris :

Opérations :

- 1 - La personne s'identifie par un formulaire en méthode POST.
- 2 - La personne se déconnecte aussi tôt
- 3 - La personne refait en retour arrière, le navigateur averti que la page précédente était accessible, mais après avoir envoyé le formulaire, donc le navigateur demande si il doit renvoyé les données
- 4 - Je renvoies les données envoyer par le formulaire, et je recrée donc ma session.

Pour éviter que les données ne soit renvoyée, personnellement j'utilise une redirection (peut importe la manière, header php, meta etc ... la plus perfomante selon moi est la redirection par les header (php) ).

Pour que ça fonctionne, il faut que tu ais :

- La page d'identification
- La page qui traite les informations, si c'est OK, elle redirige vers la page d'accueil de l'admin, si c'est faux, elle renvoie vers la page d'identification en notifiant un message d'erreur.
- La page de déconnexion.

Si tu redirige vers une autre page après la vérification de l'identification, la personne pourra faire un retour en arrière, mais elle n'auras pas la possibilité de renvoyé les données envoyées.

Ce n'est donc pas une question de timeout, mais un problème de traitement du formulaire. (c'est le fonctionnement d'un nombre important de forum, ça évite le double post en faisant un refresh sur la page).
Salut et tout d'abord, merci pour ta réponse! Smiley cligne

Tu as bien compris mon problème et effectivement, j'y ai réfléchis et je crois que j'ai disons mal "organisé" mes pages de sessions...
Si je te comprends bien :
On imagine que je me suis logué, je suis sur ma page d'administration de mon site (après redirection par headder). Cette page me propose donc de modifier mes pages, en créer (etc) et aussi de me déconnecter.
Si je clique sur le liens "Me déconnecter", j'appelle la page qui contient le code de fermeture de session
<?php

// On appelle la session

session_start();



// On écrase le tableau de session

$_SESSION = array();



// On détruit la session

session_destroy();

?>

et me redirige aussitôt par headder sur une troisième page qui annonce par exemple "Vous êtes maintenant déconnecté".
C'est ça? Smiley sweatdrop

Si c'est le cas, n'y a-t-il pas un problème de placement du code car, si mes souvenirs sont bons, le code d'ouverture de session doit toujours se trouver en tout début de code et le headder aussi... enfin, je crois hein! Smiley lol

Merci et à bientôt !
Salut Super_baloo8 Smiley cligne ,

mon post se voulait didactique et je n'ai pas dit qu'il y avait un problème de timeout Smiley murf .

La méthode que tu préconises est celle qui est expliquée dans le premier lien que j'ai donné avec en plus la gestion d'un timeout. Je trouve son utilisation particulièrement intéressante car la plupart des utilisateurs ne savent pas (et n'ont d'ailleurs pas à savoir) qu'il faut cliquer sur le lien déconnexion pour fermer proprement une session. Ils ouvrent simplement une autre page et n'y pensent plus. Il suffirait à une personne mal intentionnée Smiley scared qui arriverait devant l'ordinateur (dont le navigateur ne serait pas fermé) de cliquer plusieurs fois sur Précédent pour arriver sur la partie privée...

Quant au deuxième lien il parle de supprimer également le cookie de session, ce qui est selon moi une bien bonne idée !

Voili, voilà !

A+
Je t'en pris pour la réponse. Pour la déconnexion, tu n'est pas obliger d'utiliser la redirection header.

Pour le header et session_start, effectivement, il ne faut rien avant, enfin, pas de code html renvoyé au navigateur.

Personnellement, je place en premier session_start, et ensuite je fait ce que je veux, puis une fois finis, je redirige, mais, je n'envoie aucun code html, j'effectue uniquement du script, rien d'autre.

Un exemple de redirection après identification :

<?php
$host  = $_SERVER['HTTP_HOST'];  // Préparation de la redirection, je prend le sous domaine du site
$uri   = rtrim(dirname($_SERVER['PHP_SELF']), '/\\');  // Préparation de la redirection, je prends le nom de domaine

$membre_req = "SELECT groupe, password, id FROM ma_base WHERE pseudo='".$_POST['login_user_form']."'"; // Requêtes SQL tout ce qu'il y a de plus classique
$membre_res = mysql_query($membre_req);

$compte_resultat_membre = mysql_num_rows($membre_res);  // Nombre de résultats par rapport aux pseudo donné


	if($compte_resultat_membre == 0)  // Si le nombre de résultats est zéro, alors je redirige vers la page qui indique qu'il a rentré un mauvais pseudo
	{
	$extra = 'identification/connexion-inconnu/'; // Fin de la préparation de la redirection, j'indique le chemin qui sera mis après le nom de domaine
	header("Location:  http://$host$uri/$extra");  // Redirection vers la page citée plus haut
	mysql_close(); // Fermeture connextion MySQL
	exit; // J'arrête tout puisque je suis en train de rediriger
	}
	else
	{	
$membre = mysql_fetch_assoc($membre_res); // Si je trouve un résultat en base

	if(md5($_POST['password']) != $membre['password']) // Je compare le mot de passe et celui donnée par l'utilisateur
	{
	$extra = 'identification/connexion-de-passe/'; // Si ce n'est pas bon, je recommence comme au dessus, je redirige
	header("Location:  http://$host$uri/$extra");
 
	mysql_close();
	exit;
	}
	else // Sinon, j'affecte mes sessions (le session_start() se trouve au début de toutes mes pages sur un autre fichier)
	{
	$_SESSION['id'] = $membre['id'];
	$_SESSION['login'] = $_POST['login_user_form'];
	$_SESSION['groupe'] = $membre['groupe'];
	setcookie('gateau', serialize(array($membre['id'], md5($membre['password']))), time() + 183*24*3600, '/', '', 0); // Création d'un gateau (cookie) pour faire jolie [lol]
	$extra = 'gestion/';
	header("Location:  http://$host$uri/$extra");  // Allez encore une redirection puisque l'utilisateur est reconnu
	mysql_close();
	exit;
	
}


Edit : en écrivant le post, j'ai lu ta réponse Heyoan, je me suis précipité, désolé ... Smiley cligne

Mais a quoi sert la suppression du cookie si ce n'est de ne plus avoir le cookie ? (En mettant à zero les session, le cookie aussi reviens à zéro, ce qui équivaut à sa suppression non ? Un cookie n'est jamais physiquement supprimé tant que le navigateur est ouvert).
Heyoan a écrit :

La méthode que tu préconises est celle qui est expliquée dans le premier lien que j'ai donné avec en plus la gestion d'un timeout. Je trouve son utilisation particulièrement intéressante car la plupart des utilisateurs ne savent pas (et n'ont d'ailleurs pas à savoir) qu'il faut cliquer sur le lien déconnexion pour fermer proprement une session. Ils ouvrent simplement une autre page et n'y pensent plus. Il suffirait à une personne mal intentionnée Smiley scared qui arriverait devant l'ordinateur (dont le navigateur ne serait pas fermé) de cliquer plusieurs fois sur Précédent pour arriver sur la partie privée...


Je n'ai pas pris le temps de survoler plus en profondeur le lien que tu donnais, il est très interessant, je pensais que tu parlais du Timeout par défaut (environ 30 minutes, mais qui peut être différent suivant config apache).

Mettre un time out est bien, mais en même temps, l'utilisation d'un cookie est tellement pratique (pas le cookie de session Smiley cligne ). En général l'utilisateur aime bien resté connecté sur le site où il viens fréquemment. Après, si il s'identifie sur un ordinateur publique, on ne peut malheureusement pas être derrière lui pour lui dire de faire attention.

Il existe une solution entre les deux ? Entre le resté connecté et la sécurité publique ?
Super_baloo8 a écrit :
Mais a quoi sert la suppression du cookie si ce n'est de ne plus avoir le cookie ? (En mettant à zero les session, le cookie aussi reviens à zéro, ce qui équivaut à sa suppression non ?
Non : le cookie n'est pas remis à 0 et l'id de session est toujours lisible et à priori utilisable par un hacker (même si je ne sais pas exactement comment on s'y prend Smiley cligne )

Super_baloo8 a écrit :
Un cookie n'est jamais physiquement supprimé tant que le navigateur est ouvert).
Si : en utilisant la technique du deuxième lien le cookie est physiquement supprimé...

Super_baloo8 a écrit :
Il existe une solution entre les deux ? Entre le resté connecté et la sécurité publique ?
Pour ma part j'utilise toujours la méthode du timeout (je rajoute même un meta refresh d'une durée égale au timeout sur chaque page privée) et selon les cas j'ajoute une case à cocher "se souvenir de moi" qui crée un autre cookie de connexion automatique...

A+ Smiley smile
Heyoan a écrit :
Non : le cookie n'est pas remis à 0 et l'id de session est toujours lisible et à priori utilisable par un hacker (même si je ne sais pas exactement comment on s'y prend Smiley cligne )


Je me suis mal exprimé, la session est remis à zéro, et le cookie de session (celui sur le serveur) est aussi remis à zéro.

Heyoan a écrit :

Si : en utilisant la technique du deuxième lien le cookie est physiquement supprimé...

Non, la fonction set_cookie réécris le cookie de session (utilisateur) en écrivant un cookie vide. Physiquement il existe toujours, mais il n'a aucune valeur.

Heyoan a écrit :

Pour ma part j'utilise toujours la méthode du timeout (je rajoute même un meta refresh d'une durée égale au timeout sur chaque page privée) et selon les cas j'ajoute une case à cocher "se souvenir de moi" qui crée un autre cookie de connexion automatique...


Le problème du refresh, c'est que parfois, c'est trop long, et parfois c'est trop court, par exemple l'utilisateur est en train de rédiger un article, le time out arrive, il a tout perdu.

Si le time out est trop long, l'utilisateur ne se déconnecte pas, et une autre personne arrive et on revient au même problème.
Super_baloo8 a écrit :
Je me suis mal exprimé, la session est remis à zéro, et le cookie de session (celui sur le serveur) est aussi remis à zéro.
Je ne connaissais pas la notion de cookie de session serveur Smiley murf : il va falloir que je me renseigne !
Mais j'avais lu que l'identifiant de session (PHPSESSID) pouvait être réutilisé et du coup j'ai pris l'habitude de le supprimer.

Super_baloo8 a écrit :
Non, la fonction set_cookie réécris le cookie de session (utilisateur) en écrivant un cookie vide. Physiquement il existe toujours, mais il n'a aucune valeur.
Ben je viens de refaire un test sur un site où j'utilises cette technique et le cookie PHPSESSID n'est plus visible dans la liste des cookies du site (je me sers de Firefox : Afficher les cookies) Smiley ohwell

Super_baloo8 a écrit :
Le problème du refresh, c'est que parfois, c'est trop long, et parfois c'est trop court, par exemple l'utilisateur est en train de rédiger un article, le time out arrive, il a tout perdu.
Si le time out est trop long, l'utilisateur ne se déconnecte pas, et une autre personne arrive et on revient au même problème.
C'est vrai que c'est pas simple et que c'est toujours approximatif mais à part le cas d'écriture d'articles ou de textes longs un timeout court me semble un bon compromis...

Bon ben merci pour la discussion et à une prochaine (le lit m'appelle Smiley lol ) !
Heyoan a écrit :
Je ne connaissais pas la notion de cookie de session serveur Smiley murf : il va falloir que je me renseigne !
Mais j'avais lu que l'identifiant de session (PHPSESSID) pouvait être réutilisé et du coup j'ai pris l'habitude de le supprimer.


C'est celui qui permet de stocker les informations de la session, il porte le nom de la session. Le cookie stocker sur la machine ne sert qu'a identifier la session avec le serveur.

Heyoan a écrit :
Ben je viens de refaire un test sur un site où j'utilises cette technique et le cookie PHPSESSID n'est plus visible dans la liste des cookies du site (je me sers de Firefox : Afficher les cookies) Smiley ohwell


J'utilise moi aussi la technique de réécriture du cookie de Session, et je le vois toujours, mais c'est normal, du moment qu'on est sur le site (que je réalise), j'utilise les sessions (qui me servent à autres choses).

Heyoan a écrit :
Bon ben merci pour la discussion et à une prochaine (le lit m'appelle Smiley lol ) !


J't'en pris lol, moi j'étais déjà parti au dodo avant que tu ne répondes Smiley cligne