Manejo de Sesiones
Las sesiones permiten mantener datos del usuario entre diferentes páginas, como el contenido de un carrito de compras o el estado de inicio de sesión. En esta lección aprenderás a usar $_SESSION, configurarlas de forma segura y gestionar su ciclo de vida.
Introducción
Una sesión es un mecanismo para almacenar datos en el servidor, asociados a un ID único que se envía al cliente (normalmente vía cookie). PHP usa la superglobal $_SESSION para gestionar estos datos.
Ejemplo básico:
<?php
session_start();
$_SESSION["usuario"] = "Ana";
echo "Sesión iniciada para: " . $_SESSION["usuario"] . "\n";
?>
Iniciar y Usar Sesiones
Para usar sesiones, siempre llama a session_start() al inicio de tu script. Esto crea o reanuda una sesión.
<?php
session_start();
// Almacenar datos
$_SESSION["nombre"] = "Jorge";
$_SESSION["visitas"] = ($_SESSION["visitas"] ?? 0) + 1;
// Mostrar datos
echo "Hola, " . $_SESSION["nombre"] . "\n";
echo "Has visitado esta página " . $_SESSION["visitas"] . " veces\n";
?>
Nota: session_start() debe ejecutarse antes de cualquier salida (HTML, echo, etc.). Usa (string) o (int) para forzar tipos al leer de $_SESSION.
<?php
$_SESSION["edad"] = (int)($_SESSION["edad"] ?? 0);
?>
Seguridad en Sesiones
- Regenerar ID: Evita ataques de fijación de sesión con
session_regenerate_id():
<?php
session_start();
$_SESSION["autenticado"] = true;
session_regenerate_id(true); // Elimina el ID anterior
?>
- Sanitización: Valida datos antes de guardarlos:
<?php
$nombre = filter_input(INPUT_POST, "nombre", FILTER_SANITIZE_FULL_SPECIAL_CHARS) ?? "";
if ($nombre !== "") {
$_SESSION["nombre"] = $nombre;
}
?>
- XSS: Usa
htmlspecialchars()al mostrar datos:
<?php
echo htmlspecialchars($_SESSION["nombre"] ?? "", ENT_QUOTES, "UTF-8");
?>
Nota: FILTER_SANITIZE_STRING está obsoleto desde PHP 8.1 y eliminado en PHP 8.3. Usa FILTER_SANITIZE_FULL_SPECIAL_CHARS en su lugar.
Cerrar Sesiones
Para cerrar una sesión:
<?php
session_start();
$_SESSION = []; // Vaciar datos
session_destroy(); // Destruir sesión
session_unset(); // Opcional: libera variables de sesión
echo "Sesión cerrada\n";
?>
- Usa
unset($_SESSION["clave"])para eliminar una clave específica. - Puedes almacenar strings, arrays y otros datos serializables en
$_SESSION, pero evita guardar grandes cantidades de datos. session_destroy()elimina los datos en el servidor, pero la cookie del navegador puede seguir existiendo hasta que expire o se elimine manualmente.
Configuración de Sesiones
Ajusta la configuración en php.ini o con ini_set() antes de llamar a session_start().
<?php
ini_set("session.cookie_lifetime", (string)(60 * 60)); // 1 hora
ini_set("session.cookie_secure", "1"); // Solo si usas HTTPS
ini_set("session.cookie_httponly", "1"); // Protege contra XSS
ini_set("session.use_strict_mode", "1"); // Evita sesiones no inicializadas
session_start();
?>
Opciones comunes:
session.cookie_lifetime: Tiempo de vida de la cookie de sesión.session.use_strict_mode: Rechaza IDs de sesión no inicializados por el servidor.session.cookie_httponly: Impide acceso al ID de sesión desde JavaScript.session.cookie_secure: Solo envía la cookie por HTTPS.
Ejemplo Práctico: Contador de Visitas
Para contar visitas, podemos usar una variable de sesión que se incrementa en cada carga de la página:
<?php
session_start();
$_SESSION["contador"] = ($_SESSION["contador"] ?? 0) + 1;
echo "Visitas: " . $_SESSION["contador"] . "\n";
?>
¿Qué hace esa línea?
- El operador
??comprueba si$_SESSION["contador"]existe y no esnull. - Si no existe, se usa
0como valor inicial. - Luego se le suma
1y se asigna el resultado de nuevo a$_SESSION["contador"].
Esta forma es compacta y segura. Equivale a:
<?php
if (!isset($_SESSION["contador"])) {
$_SESSION["contador"] = 0;
}
$_SESSION["contador"] += 1;
?>
Recapitulación
- Llama a
session_start()al inicio de cada script que use sesiones, antes de cualquier salida HTML. - Los datos se guardan en el servidor y se asocian al usuario mediante un ID de sesión, normalmente transmitido en una cookie.
- Usa
session_regenerate_id(true)tras autenticar al usuario para prevenir ataques de fijación de sesión. - Para cerrar una sesión completa: vacía
$_SESSION = [], destruye consession_destroy(). Para eliminar solo una clave, usaunset($_SESSION["clave"]). - Sanitiza los datos antes de guardarlos en
$_SESSIONy usahtmlspecialchars()al mostrarlos. - Configura
session.cookie_httponly,session.cookie_secureysession.use_strict_modepara endurecer la seguridad de las sesiones.
En la próxima lección: subida de ficheros en PHP: el formulario con enctype, $_FILES, validación de tipo y tamaño, y almacenamiento seguro.