LOGIN SEGURO (contra inyección sql, XSS e intro en páginas interiores)
Básicamente tenemos 3 páginas, la de login, logout y las interiores.
La de
login compara user y clave con la DB mediante sentencias preparadas (anti inyección SQL) y
la función limpiar:
Con
Trim() eliminamos de principio y final espacios, tabuladores, etc (\t \n \r \0 \v).
Con
strip_tags() eliminamos todas las etiquetas html y PHP para evitar ataques XSS
(Cross Site Scripting).
Luego valido las entradas (según las características de usuario y contraseña) Aquí pedimos que usuario sea
alfanumérico (validado con
ctype_alnum() y usuario y contraseña menores de 12 char con
strlen()).
La acción del form en
echo htmlspecialchars($_SERVER['PHP_SELF']); impide una XSS al
convertir cualquier etiqueta de script en sus equivalentes html
Si se valida se generan 2 cokies de seguridad (arriba se les da el tiempo en segundos de vida
para que la página de un time out y se cierre si permanece inactiva).
El script en jquery maneja el aspecto clásico de un login (ver detalles en el código).
Las
interiores solo se encabezan con un control de si existe la cokie de seguridad,
si no existe se redirecciona al login.
La de
logout es un script php que destruye la session, las cokies y el id.
Los detalles y explicaciones están como comentarios del código
VALORES RECOMENDADOS (en .htaccess o php.ini) PARA LAS CONSTANTES SESSION
- php_value session.cookie_lifetime 0
- php_value session.use_cookies 1
- php_value session.use_only_cookies 1
- php_value session.use_strict_mode 1
- php_value session.cookie_httponly 1
- php_value session.cookie_secure 1
- php_value session.use_trans_sid 0
- php_value session.cache_limiter nocache
- php_value session.use_trans_sid 0
Detalles en:
SESSION
*************CÓDIGO PHP EN LOGIN ANTES DE <htlm>**************
*************JAVASCRIPT EN LOGIN EN <head> para manejo de form**************
<link href="../css/font-awesome.min.css" rel="stylesheet">
<script type="text/javascript" src="../scripts/jquery-1.11.3.min.js"></script>
<script type="text/javascript">
$(window).load(function() {
$("#user").val("Tu usuario"); /*están aqui por si se retrocede en el doc. */
$("#pass").val("Tu clave"); /*y se borren los valores anteriores*/
$("#guion1").css("visibility","hidden"); /*y se borran los epigrafes*/
$("#guion2").css("visibility","hidden");
});
$(document).ready(function(){
/* usuario*/
$("#user").click(function(evento){
if ($("#user").val()== "Tu usuario" ){ /*si esta la leyenda*/
$("#user").val(""); /*la borro*/
$("#guion1").css("visibility","visible"); /*aparece la leyenda chiquita*/
$("#user").css("color","#000"); /*el color de gris a negro*/
}
});
$("#user").focusout(function(evento){
if ($("#user").val().length == 0 ){ /*al perder foco si no hay nada escrito*/
$("#user").val("Tu usuario"); /*repongo la leyenda*/
$("#guion1").css("visibility","hidden"); /*desaparece la leyenda chiquita*/
$("#user").css("color","#AAA"); /*el color vuelve a gris*/
}
});
/* password*/
$("#pass").click(function(evento){
if ($("#pass").val()== "Tu clave" ){ /*si esta la leyenda todo igual que con usuario*/
$("#pass").val("");
$("#guion2").css("visibility","visible");
$("#pass").css("color","#000");
$("#pass").attr("type","password"); /*por defecto el input lo hago password asi*/
} /*queda ofuscado lo que escriba*/
});
$("#pass").focusout(function(evento){ /*al peerder foco todo igual que usuario*/
if ($("#pass").val().length == 0 ){
$("#pass").attr("type","text");
$("#pass").val("Tu clave");
$("#pass").css("color","#AAA");
$("#guion2").css("visibility","hidden");
$("#eye").css("visibility","hidden"); /* si borré el pass y le quito foco apago ojito*/
$("#eye").css("color","black"); /* lo vuelvo a negro*/
$("#eye").attr("class","fa fa-eye-slash"); /* y lo vuelvo a ojo cerrado*/
}
});
/* control del ojito*/
$("#pass").keypress(function(evento){ /* si se tipea dentro de pass aparece el ojito*/
$("#eye").css("visibility","visible");
});
$("#eye").click(function(evento){
if ($("#eye").attr("class")== "fa fa-eye-slash" ){ /*al clicar el ojo cerrado.....*/
$("#eye").css("color","orange");
$("#eye").attr("class","fa fa-eye"); /* lo abro*/
$("#pass").attr("type","text"); /* y hago visible el pass*/
}else{ /* al clicarlo abierto*/
$("#eye").css("color","black"); /* lo vuelvo a negro*/
$("#eye").attr("class","fa fa-eye-slash"); /* lo cierro*/
$("#pass").attr("type","password"); /* y hago ofusco el pass*/
}
});
/*activación desactivacion de submit*/
$("#form1").keypress(function(evento){ /* si se tipea dentro del formulario:*/
a=$("#user").val().length;
b=$("#pass").val().length;
if ((a != 0 )&& (b != 0 )&& ($("#user").val() != "Tu usuario") && ($("#pass").val() != "Tu clave")){
$("#boton").prop( "disabled", false ); /*Enable boton*/
$("#boton").css("cursor","pointer"); /* cursor de prohibido a manito*/
}else{
$("#boton").prop( "disabled", true ); /*Disable boton*/
$("#boton").css("cursor","not-allowed"); /* cursor de manito a prohibido*/
}
});
});
</script>
*************HTML EN LOGIN EN <body>, form DE ENTRADA**************
<div class="formu" >
<form id="form1" name="form1" method="post" action="">
<div class="linea" >
<div id="guion1" class="lineachica">Tu usuario</div>
<input type="text" name="usuario" id="user" class="ingresologin" maxlength="50" value="Tu usuario" /></i>
</div>
<div class="linea" >
<div id="guion2" class="lineachica">Tu clave</div>
<input name="password" id="pass" class="ingresologin" type="text" maxlength="50" value="Tu clave" /><i id="eye" class="fa fa-eye-slash" style="visibility:hidden; color:black;"></i>
</div<
<div style=" padding-top:20px; padding-left:20px;">
<input name="login" type="submit" value="Iniciar sesión" class="botonlogin" id="boton" disabled="true" style="cursor:not-allowed;" /> </i>
</div>
</form>
<div id="msg" class="mensaje"><?php echo ($msg); ?></div>
</div>
*************PHP EN TARGET ANTES DE <html>**************
*************PHP EN LOGOUT ANTES DE <html>**************
<?php
session_start(); //inicia la sesión a destruir
session_unset(); //borra todas las variables del array $_SESSION
session_destroy(); //borra toda la info de sesión
session_start(); //reinicia una sesión nueva
session_regenerate_id(true); //genera un nuevo id con lo cual desaparece el anterior en el server
header('location: tec-php-login02-prototipo.php'); //mando al login
?>