Accueil
Accueil Le Club Delphi Kylix C C++ Java J2EE DotNET & C# Visual Basic Access Pascal Dev Web PHP ASP XML UML SQLSGBD Windows Linux Autres
logo

precedent    sommaire    suivant   


Comment conserver des variables de page en page ?
auteur : Cyberzoide
  • En stockant leurs valeurs dans une base de données.
  • En les enregistrant dans un fichier sur le serveur (mais oblige à donner des droits d'écriture aux visiteurs).
  • Utiliser des cookies (malheureusement certains navigateurs ne les acceptent pas).
  • En les envoyant dans l'URL (mais seront visibles aux visiteurs dans la barre d'adresse et cela leur impose de toujours utiliser les liens hypertextes).
  • En les passant par un formulaire (mais impose aux visiteurs de cliquer sur un bouton d'envoi).
  • En utilisant une session.


Pourquoi utiliser les sessions ?
auteur : Cyberzoide
  • Pour conserver de page en page les valeurs de certaines variables.
  • Pour pister le parcours du visiteur.
  • Pour effectuer des statistiques fines en termes de visiteurs réels et pas en hits (nombre d'appels d'un fichier).


Comment fonctionne une session ?
auteur : Cyberzoide
Les sessions permettent tout du long de la visite d'un internaute sur le site, de conserver des informations de façon transparente.

Cela est sans ralentissement de performances car le client ne stocke sous forme de cookie que l'ID de session (généré aléatoirement), le serveur stockant sur disque le contenu des variables dans le répertoire défini par session.save_path.

Les sessions sont activées manuellement par la commande session_start() ou automatiquement si session.auto_start est à 1 ou encore implicitement par la commande session_register()(obsolète).

Le serveur attribue à chaque visiteur un identifiant unique qui est soit envoyé au client sous forme de cookie (par défaut), soit passé de façon systématique dans l'URL.


Comment démarrer une session ?
auteur : Cyberzoide
Il existe trois manières de démarrer une session :

Syntaxe : boolean session_start ( void) Crée une session ou continue la session courante, en fonction de l'identifiant de session passé par l'URL (méthode GET) ou par un cookie.
Exemple :
<?php
session_start() ;
...
?>

Comment sauvegarder une variable dans une session ?
auteur : Cyberzoide
Par l'usage de la commande session_register()(obsolète) dont voici la syntaxe :
boolean session_register ( mixed name [, mixed ...])
Elle prend en paramètre une chaîne de caractères contenant le nom de la variable à sauvegarder ou bien un tableau de chaînes de caractères ou encore un tableau de tableaux...

Exemple avec une variable chaîne de caractères :
<?php
session_start() ;
$foobar = "Hello Word !";
session_register("foobar");
...
?>
Autre exemple avec le tableau superglobal $_SESSION :
<?php
session_start() ;
$_SESSION["foobar"] = "Hello Word !";
...
?>
Toute modification ultérieure dans le script des variables de session (avant la fermeture de la session) sera automatiquement répercutée autant dans la session que dans l'espace mémoire des données du script en exécution.

Tous les types de variable, hormis les ressources, sont acceptés : chaînes, nombres, tableaux, objets (dont la classe doit être incluse avant le démarrage de la session).

Exemple avec une variable objet :
<?php
require("../common/visitor.class.php");
session_start() ;
$_SESSION["myVisitor"] = new Visitor();
...
?>

Comment savoir si une variable appartient déjà a la session ?
auteur : Cyberzoide
La commande session_is_registered (obsolète) renvoie TRUE si la variable dont l'identificateur est passé en paramètre a déjà été engegistrée parmi les variables de session.

Exemple :
<?ph
psession_start() ;
$foobar = "toto";
if(!session_is_registered("foobar")) {
    session_register("foobar");
}
...
?>
Si vous utilisez l'option register_globals=off, il faudra tester l'existence d'une variable dans la session à l'aide de la fonction isset().

Exemple :
<?php
session_start() ;
$_SESSION["foobar"] = "toto";
if(!isset($_SESSION["foobar"])) {
    $_SESSION["foobar"] = "toto";
}
...
?>

Comment supprimer une variable d'une session ?
auteur : Cyberzoide
La commande session_unregister() (obsolète) supprime une variable dans la session courante. Elle a pour syntaxe :
boolean session_unregister (string name)
Elle retourne TRUE en cas de succès, FALSE sinon.

Si vous utilisez le tableau superglobal $_SESSION, il suffit alors d'utiliser unset() :
unset($_SESSION["mavariable"]);
Il est aussi possible de purger toutes les variables de la session avec session_unset().

Note : Si vous utilisez $_SESSION (ou $HTTP_SESSION_VARS), utilisez plutôt ceci :
$_SESSION = array();

Quelle est la durée de vie d'une session ?
auteur : Cyberzoide
Dès que l'on ferme le navigateur la session est détruite. Sauf à configurer le fichier php.ini avec session.lifetime qui fixe la durée de vie, en secondes, du cookie envoyé au client. La valeur 0 signifie "jusqu'à ce que le client soit fermé". Par défaut à 0.
Donc si on le laisse à zéro, la session dure jusqu'à la fermeture du navigateur, pour laisser les données durant 30 minutes, il faut remplacer 0 par 1800 (= 30 minutes * 60 secondes dans une minute).
session.lifetime = 0


Comment fermer une session ?
auteur : Cyberzoide
Fermeture conservatrice :
La commande session_write_close() écrit les valeurs des variables de session sur le serveur et ferme la session.

Fermeture destructive :
La commande session_destroy() détruit toutes les données enregistrées d'une session. Cette dernière commande est la plus utilisée car n'impose aucune sauvegarde au serveur. Retourne TRUE en cas de succès, et FALSE sinon.


Quelles sont les méthodes PHP associées aux sessions ?
auteur : Cyberzoide


Quelles sont les erreurs possibles ?
auteur : Cyberzoide
Répertoire de session inaccessible
Warning: open(/tmp\sess_3c80883ca4e755aa72803b05bce40c12, O_RDWR) failed: m (2) in c:\phpdev\www\bp\header.php on line 2
ou encore :
PHP Warning: Unknown(): open(/tmp\sess_3c80883ca4e755aa72803b05bce40c12, O_RDWR) failed: No such file or directory (2) in Unknown on line 0
PHP Warning: Unknown(): Failed to write session data (files). Please verify that the current setting of session.save_path is correct (/tmp) in Unknown on line 0

Cette erreur est due à l'absence du répertoire de sauvegarde (ici /tmp) des sessions ou bien au manque du droit d'écriture dans ce répertoire pour les visiteurs (utilisateur nobody, www-data ou autre... sous Apache).

Le répertoire de sauvegarde est défini dans le php.ini : session.save_path = /tmp

Il faut donc:
  • Créer un répertoire
  • Lui donner les droits d'écriture pour tous
  • En spécifier le chemin dans le php.ini

PHP n'est pas autorisé à utiliser les sessions
Il faut s'assurer que le PHP est bien autorisé a créer des sessions. C'est juste un paramètre à activer. Faire un phpinfo() pour voir ces paramètres. La commande phpinfo() se contente d'afficher dans le navigateur le contenu du fichier de configuration php.ini.

Avoir déjà écrit dans la page
Warning: Cannot send session cookie - headers already sent by (output started at /home/SiteWeb/SiteAnalyse/index.php:3) in /home/SiteWeb/SiteAnalyse/index.php on line 6
Cette erreur survient lorsqu'on tente d'ouvrir une session après avoir déjà écrit dans le document, ce qui interdit, bien sûr.

Tentative d'envoi d'en-têtes
Warning: Cannot add header information - headers already sent by (output started at /home/SiteWeb/SiteAnalyse/index.php:3) in /home/SiteWeb/SiteAnalyse/index.php on line 25
Cette erreur survient lorsqu'on tente d'envoyer des en-têtes grâce à la fonction header() après avoir écrit dans la page.

On ne peut pas commencer une session après que le serveur ait envoyé au client les en-têtes HTTP/1.0 (ou supérieures) de la page.

Ainsi, la commande session_start() doit impérativement être exécutée avant tout envoi par le serveur d'en-têtes HTTP au navigateur.

L'identifiant de session étant envoyé sous forme de cookie au client, ce dernier doit être envoyé avant que la page ne s'affiche car l'affichage force l'envoi d'en-têtes.

Tout contenu texte placé avant session_start() (même un saut de ligne) provoque un affichage et donc l'envoi d'en-têtes qui doivent précéder le contenu de la page.

Ce qu'il ne faut pas faire :
<html>
<body>
<?php 
session_start();
...
ceci non plus :
<?php
echo "<html>";
...
session_start();
Car cela provoque l'envoi d'en-têtes au navigateur. Donc ces deux essais sont erronés. Il faut faire le session_start() avant toute chose !!!

Même un simple saut de ligne dans le script avant session_start() provoque cette erreur.

Défaut de déclaration de classe
Fatal error: The script tried to execute a method or access a property of an incomplete object. Please ensure that the class definition utilisateur of the object you are trying to operate on was loaded _before_ the session was started in /home/SiteWeb/SiteAnalyse/test.php on line 12
Lorsqu'une variable que l'on veut enregistrer dans une session est un objet, PHP doit pouvoir en connaître la description, il faut donc déclarer les classes avant de faire un session_start().


Que sont les en-têtes HTTP ?
auteur : Cyberzoide
Le rôle des en-têtes est d'échanger des méta-informations (informations à propos des informations échangées que sont les pages html générées ou non dynamiquement à partir de PHP) entre le serveur et le client.

Exemples d'en-têtes
Server: Apache/1.3.9 (Unix) Debian/GNU qui renseigne le client sur la nature du serveur distant
Last-Modified: Sun, 07 Apr 2002 14:30:30 GMT qui donne la date de dernière modification du document

Envoyer des en-têtes
La commande header() du php permet l'envoi d'en-têtes personnalisés.
Par exemple :
header("Location: home2.php3");
pour rediriger le navigateur sur la page "home2.php3"

Les en-têtes peuvent servir à la redirection, à l'authentification, à l'envoi d'images au navigateur...

lien : fr Le Protocole HTTP

Comment configurer php.ini ?
auteur : Cyberzoide
Ci-après les options de configuration des sessions du fichier php.ini

session.save_handler
définit les noms des fonctions qui seront utilisées pour enregistrer et retrouver les données associées à une session. Par défaut, les sessions sont enregistrées dans des fichiers. Mais on pourrait les enregister dans une base de données ; il faudrait alors définir les fonctions d'écriture dans la base et les spécifier à session.save_handler.

session.save_path
définit l'argument qui est passé à la fonction de sauvegarde. Si vous utilisez la sauvegarde par fichier, cet argument est le chemin jusqu'au dossier où les fichiers sont créés. Par défaut, le dossier est /tmp. Si le dossier que vous utilisez a les droits de lecture universelle, comme /tmp (valeur par défaut), les autres utilisateurs du serveur peuvent aussi lire ces fichiers, et s'immiscer dans vos sessions.

session.name
spécifie le nom de la session, qui sera utilisé comme nom de cookie. Par défaut : PHPSESSID.

session.auto_start
indique qu'une session doit commencer automatiquement lors de la premiere requête. Par défaut, la valeur est à 0 (inactivé) ; il faut donc utiliser session_start().

session.lifetime
fixe la durée de vie, en secondes, du cookie envoyé au client. La valeur 0 signifie "jusqu'à ce que le client soit fermé". Par défaut à 0 (inactivé).

session.serialize_handler
définit le nom de la fonction qui sera utilisée pour enregistrer et relire les donnés. Actuellement, c'est un format interne de PHP (nom : php) et WDDX (nom : wddx). WDDX n'est utilisable que si PHP a été compilé avec le support WDDX. Par défaut, c'est le mode php qui est sélectionné.

session.gc_probability
précise la probabilité que la routine gc (garbage collection) soit lancée, en pourcentage. Par défaut, la valeur est à 1.

session.gc_maxlifetime
fixe la durée, en secondes, au-delà de laquelle les données considérées comme inutiles seront supprimées.

session.referer_check
représente la sous-chaîne que vous utilisez pour vérifier la provenance de l'internaute. Si l'en-tête HTTP Referer vous est fournie par le navigateur et que cette sous-chaîne n'est pas trouvée, la session qui vous est fournie sera considérée comme invalide (car provenant probablement d'un autre site que le vètre). Par défaut, cette chaîne est vide.

session.entropy_file
est le chemin jusqu'à une source externe (fichier) d'entropie, qui sera utilisée lors de la création de l'identifiant de session. Par exemple, /dev/random ou /dev/urandom qui sont disponibles sur de nombreux systèmes UNIX.

session.entropy_length
précise le nombre d'octets qui seront lus dans le fichier ci-dessus. Par défaut, 0 (inactivé).

session.use_cookies
indique si le module doit utiliser des cookies pour enregistrer l'identifiant de session chez le client. Par défaut, 1 (activé). Ce qui suppose que le client accepte les cookies, ce qui n'est pas acquis ! C'est pourquoi certains serveurs font le choix de ne pas stocker l'identifiant de session sous forme de cookie mais le rajoutent systématiquement en paramètre dans toutes les URL.

session.cookie_path
spécifie le chemin à utiliser avec session_cookie. Par défaut, /.

session.cookie_domain
spécifie le domaine à utiliser avec session_cookie. Par défaut, rien du tout.

session.cache_limiter
spécifie le contrèle du cache, à utiliser avec les pages de session (nocache/private/public). Par défaut, nocache.

session.cache_expire
spécifie la durée de vie des pages de session cachées, en minutes, mais sans que cela ait d'effets sur le limiteur "nocache". Par défaut, 180.

session.use_trans_sid
indique si le support du SID est activé ou pas, lors de la compilation avec l'option --enable-trans-sid. Par défaut, elle vaut 1 (activée).

url_rewriter.tags
spécifie si les balises html sont réécrites pour inclure l'identifiant de session si sid est activé. Par défaut, a=href, area=href, frame=src, input=src, form=fakeentry. Permet de passer l'identifiant de session de page en page par l'URL pour parer au refus de cookie, c'est la seule alternative à session.use_cookies.


Cas particulier de l'hébergeur FREE.FR
auteur : Cyberzoide
Chez free, le répertoire de sessions doit être à la racine de votre compte FTP. Il suffit donc de créer le répertoire sessions (au pluriel).


Comment faire cohabiter sur le même serveur deux applications utilisant les sessions ?
auteur : Cyberzoide
Dans le cas où un serveur HTTP héberge plusieurs applications PHP utilisant chacune les sessions, il peut y avoir des problèmes si plusieurs applications utilisent les mêmes variables de sessions (lorsque un utilisateur visite simultanément plusieurs applications).

Pour résoudre ce problème il suffit de définir un nom de session différent pour chacune des applications lors de la création de la session :

Puis de rappeler ce nom lors de l'utilisation des variables de la session dans l'application.
Autre solution, au démarrage d'une nouvelle session, pour éviter tout conflit dans l'utilisation des noms de variables de session, spécifier un autre chemin de sauvegarde des données de session avec session_save_path().


Pourquoi mon site n'est plus valide XHTML depuis que j'utilise des sessions ?
auteur : Emerica
Ce problème se pose lorsque l'on a 'session.use_trans_sid' à 1 (On). Pour chaque lien (balise <a>), formulaire (<form>) et d'autres balises, PHP va apporter des modifications.

Par exemple, pour un lien, PHP va rajouter &PHPSESSID=sid ou sid est l'identifiant de session dans le lien, en transparence. En XHTML, un & indique une référence HTML (par exemple &nbsp; espace insécable). Ce sera donc invalide pour la norme XHTML. Par contre, un &amp; sera valide. PHP va chercher ce caractère d'argument dans sa configuration, c'est a dire dans php.ini. Il est donc possible de modifier le & par défaut en &amp; à l'aide de la fonction ini_set() de la manière suivante :
<?php
// à placer avant session_start();
ini_set('arg_separator.output', '&amp;');
?>
Le problème est maintenant réglé pour les liens. Attaquons nous aux formulaires. Là, c'est plus délicat car PHP rajoute un input de type hidden contenant l'id de session directement à la suite de chaque <form>, ce qui est totalement invalide en XHTML. Pour contrer ceci, la solution est plus radicale. Il nous faut redéfinir quelles balises PHP modifie pour passer son identifiant de session.
<?php
// à placer avant session_start();
ini_set("url_rewriter.tags","a=href,area=href,frame=src,iframe=src,input=src");
?>
A la base, url_rewriter.tags contenait form=fakeentry. Cette partie a été supprimée, et PHP ne modifiera plus les balises <form>. On peut aussi contourner ce problème en utilisant des fieldsets au lieu de forms.


Pourquoi mes sessions ne fonctionnent plus avec EasyPhp 1.7 ?
auteur : Nonothehobbit
Easyphp 1.7 installe php 4.3 dont le fichier de configuration par défaut met la variable register_globals à off ce qui oblige à utiliser les tableaux superglobaux et peut donc poser quelques problèmes pour les sessions.
Pour rendre compatible le code, faites les remplacements suivants :
$ma_variable_de_session  -> $_SESSION['ma_variable_de_session']
                
session_register('variable') -> $_SESSION['variable'] = $variable

session_is_registered('variable') -> isset($_SESSION['variable'])

session_unregister('variable') -> unset($_SESSION['variable'])

session_unset() -> $_SESSION = array();
Il est vrai que remettre register_globals à on pourrait régler tous ces problèmes mais cela est fortement déconseillé car cela crée un énorme trou de sécurité dans votre application. Sachez également que si une application est développée avec register_globals à off, elle restera utilisable et avec le même niveau de sécurité si elle est exécutée avec register_globals à on.


precedent    sommaire    suivant   

Consultez les autres F.A.Q's


Les sources présentés sur cette pages sont libre de droits, et vous pouvez les utiliser à votre convenance. Par contre cette page de présentation de ces sources constitue une oeuvre intellectuelle protégée par les droits d'auteurs. Copyright ©2003  Developpez LLC. Tout droits réservés Developpez LLC. Aucune reproduction, même partielle, ne peut être faite de ce site et de l'ensemble de son contenu : textes, documents et images sans l'autorisation expresse de Developpez LLC. Sinon vous encourez selon la loi jusqu'à 3 ans de prison et jusqu'à 300 000 E de dommages et intérets. Cette page est déposée à la SACD.

Vos questions techniques : forum d'entraide Accueil - Publiez vos articles, tutoriels, cours et rejoignez-nous dans l'équipe de rédaction du club d'entraide des développeurs francophones. Nous contacter - Copyright 2000..2005 www.developpez.com