validar email en PHP

Valoración del artículo:
Comprobar la validez de una dirección de correo electrónico, es decir, validar la buena redacción de un email.
Publicado: 03/12/02
Atención: Contenido exclusivo de DesarrolloWeb.com. No reproducir. Copyright.
Vamos a ver una función muy útil en PHP que sirve para comprobar la validez de un correo. En realidad comprueba si una dirección de correo electrónico está bien escrita sintácticamente, dejando de lado las comprobaciones de si ese mail existe o no realmente, que no se pueden hacer tan fácilmente.

Vamos a escribir una función que se llama comprobar_email y recibe la cadena de texto con el email que queremos validar. Si dicho email es correcto desde el punto de vista sintáctico, es decir, si tiene un nombre de usuario, una arroba y una terminación con el nombre de un dominio o subdominio, etc, devolverá un 1, es decir, verdadero. En caso de que el email no esté correctamente escrito, la función devolvería 0, que equivale a falso.

La función en si da por hecho inicialmente que el email es erróneo y realiza una serie de comprobaciones que, si todas responden correctamente, dan por conclusión que el email sí estaba bien escrito. Si alguna de esas comprobaciones no era correcta, no se llegaría al final de las comprobaciones y quedaría el resultado como se ha supuesto en un principio, es decir, como incorrecto.

código de la función

function comprobar_email($email){
    $mail_correcto = 0;
    //compruebo unas cosas primeras
    if ((strlen($email) >= 6) && (substr_count($email,"@") == 1) && (substr($email,0,1) != "@") && (substr($email,strlen($email)-1,1) != "@")){
       if ((!strstr($email,"'")) && (!strstr($email,"\"")) && (!strstr($email,"\\")) && (!strstr($email,"\$")) && (!strstr($email," "))) {
          //miro si tiene caracter .
          if (substr_count($email,".")>= 1){
             //obtengo la terminacion del dominio
             $term_dom = substr(strrchr ($email, '.'),1);
             //compruebo que la terminación del dominio sea correcta
             if (strlen($term_dom)>1 && strlen($term_dom)<5 && (!strstr($term_dom,"@")) ){
                //compruebo que lo de antes del dominio sea correcto
                $antes_dom = substr($email,0,strlen($email) - strlen($term_dom) - 1);
                $caracter_ult = substr($antes_dom,strlen($antes_dom)-1,1);
                if ($caracter_ult != "@" && $caracter_ult != "."){
                   $mail_correcto = 1;
                }
             }
          }
       }
    }
    if ($mail_correcto)
       return 1;
    else
       return 0;
}


Las comprobaciones

En el primer if compruebo que el email tiene por lo menos 6 caracteres (el mínimo), que tiene una arroba y sólo una y que no está colocada ni al principio ni al final.

En el segundo if comprueba que no tiene algunos caracteres no permitidos. Y los restantes hacen comprobaciones de las distintas partes de la dirección de correo, a saber: Que hay un punto en algún lado y que la terminación del dominio es correcta y que el principio de la dirección también es correcto.

Finalmente, se devuelve la variable local utilizada para guardar la validez o incorrección del correo.

Descarga del script

La persona que lo desee, puede descargar el archivo con el código fuente de este script, para utilizarlo en sus aplicaciones web.

Comentarios
Fueron enviados 15 comentarios al artículo
2 comentarios no revisados
13 comentarios revisados:
Por: sQalo
09/12/02
Otra forma mas "sencilla de hacerlo". Con expresiones regulares.

if ((!ereg("^[_a-zA-Z0-9-]+(\.[_a-zA-Z0-9-]+)*@[a-zA-Z0-9-]+(\.[a-zA-Z0-9-]+)*$", $email)) or (!getmxrr($emailhost1, $mxhostarr)))
    $mensajeerror .= "ERROR, $email no es una direccion válida";

Por: Juam R
20/11/03
Mejor utiliza esta:

"^[_a-zA-Z0-9-]+(\.[_a-zA-Z0-9-]+)*@[a-zA-Z0-9-]{2,200}\.[a-zA-Z]{2,6}$"
Por: moz
05/10/04
Con esta ademas dejas que pasen emails con subdominios (soibre todo para los gratuitos) del tipo mail@finka.homeip.net

function ValidaMail($pMail) {
    if (ereg("^[_a-zA-Z0-9-]+(\.[_a-zA-Z0-9-]+)*@+([_a-zA-Z0-9-]+\.)*[a-zA-Z0-9-]{2,200}\.[a-zA-Z]{2,6}$", $pMail ) ) {
       return true;
    } else {
       return false;
    }
}
Por: Fernando Cuadrado
08/4/05
Doy fe por el de "MOZ", funciona correctamente.

Gracias MOZ.
Por: Cristina
06/6/05
La expresión regular de "MOZ" deja pasar e-mails con mas de una @ seguidas. Del tipo user@@dominio.com
Por: Souza SED
22/7/05
CODIGO
<!--
//VALIDAMOS LOS E-MAILS RECIBIDOS
function validar_mail(&$email){
global $error_email;
$email=trim($email);
$email=strtolower($email);
$email=addslashes($email);
if(!$email){
$error_email= "- Rellene este campo.";
}else{
if(!eregi("^[a-zA-Z0-9]+[a-zA-Z0-9_.-]+[a-zA-Z0-9]+@[a-zA-Z0-9]+[a-zA-Z0-9-]+[a-zA-Z0-9.-]+[a-zA-Z0-9]+.[a-z]{2,4}$", $email)){
$error_email= "- E-mail incorrecto.";
}
}
}
//-->

He realizado una función de patrones de expresiones regulares que os puede ser muy útil para validar los E-mails. He tenido en cuenta detalles como no permitir el inicio del email por _ ó - ó . pues no suele ser habitual que los proovedores de correo lo permitan a la hora de darse de alta, al igual que dejar _ ó - ó . antes de la "@" y por tanto despues tampoco. Si se permiten los correos tipo correo.loquesea@server.subdomain.dtl
correo_loquesea@server-subdomain.dtl

El problema es que para permitir estas conbinaciones también debo dejar combinaciones erroneas como
correo_.loquesea@server-.subdomain.dtl
ya que el caracter - me da problemas a la hora de restringirlo. Supongo que será un error de php.
Es muy curioso si escribo "^[a-zA-Z0-9_-.]..." no me reconoce el caracter guion - ahora si lo pongo así "^[a-zA-Z0-9_.-]..." si que lo hace... jejejeje. De todas formas es muy poco probable que el usuario se moleste en combinar estos caracteres para dar un falso email . Y como punto final habia pensado indicar una lista de los tdl más comerciales y más usados para que la terminación del e-mail siempre fuera .com .net etc.... pero lleva mucha faena y es tonteria porque si nos la quieren meter nos la meten doblada... a no ser que pongas muchas condiciones y lo unico que conseguiras es una lista muy pequeñita de usuarios...jejejejeje mas vale tener un email que otro erroneo y no pocos pues puedes perder usuarios con emails raros gratuitos.

Espero que os haya servido de ayuda.
By Souza
www.clased.com
www.rocsite.net
Por: Souza SED
22/7/05
function validar_mail(&$email){
global $error_email;
$email=trim($email);
$email=strtolower($email);
$email=addslashes($email);
if(!$email){
$error_email= "Rellene este campo.";
}
else
{

if(!eregi("^[a-zA-Z0-9]+[a-zA-Z0-9_.-]+[a-zA-Z0-9]+@[a-zA-Z0-9]+[a-zA-Z0-9-]+[a-zA-Z0-9.-]+[a-zA-Z0-9]+.[a-z]{2,4}$", $email)){
$error_email= "- E-mail incorrecto.";
}
}
}

A ver si ahora es más legible el código. Sorry. Es la primara vez que escribo aqui.
Por: Souza SED
26/7/05
//VALIDAMOS LOS E-MAILS RECIBIDOS ESTE SI ES VÁLIDO
function validar_mail(&$email){
  global $error_email;
  $email=trim($email);
  $email=strtolower($email);
  $email=addslashes($email);
  if(!$email){
    $error_email= "- Rellene este campo.";
  }else{
  if(!eregi("^[a-z]+[_\.\-]{0,1}[a-z0-9]+@[a-z0-9]+[_\.\-]{0,1}[a-z0-9]+\.[a-z]{2,4}$", $email)){
    $error_email= "- E-mail incorrecto.";
  }
  }
}
Por: BETTO
12/12/05
posiblemente resulte esta validación
$texto_mail
$mail=strpos("@",$texto_mail);
if($mail===false) echo "mail no valido";

espero coentarios
gracias
Por: NeZ
12/3/06
El de Moz se cae al escribir @@, hay que quitarle el +
Por: georkis
04/12/06
Esta muy interesante el script, pero le falta algo muy importante. ¿cómo va a saber el usuario que tipo d error que ha cometido? hace falta imprimir los resultados de la dirección del correo. Esta script la probé, pero no así, pero me ha dado una idea genial... Grasias MOZ
Por: iñaki
26/7/07
muy buenos los algoritmos, pero lo único que comprueban es que la sintaxis sea la correcta, ahi va uno que ademas mira si el dominio existe. Me falta preguntarle al dominio si el usuario es válido, a ver si a alguien se le ocurre.

function ValidaEmail($email)
{
$valida=false;
if (ereg("^[_a-zA-Z0-9-]+(.[_a-zA-Z0-9-]+)*@+([_a-zA-Z0-9-]+.)*[a-zA-Z0-9-]{2,200}.[a-zA-Z]{2,6}$", $email ))
{
$cr=split("@",$email);
$dominio=$cr[1];
$validar = @fsockopen($dominio, 80, $errno, $errstr, 5);
if ($validar)
{
$valida=true;
fclose($validar);
}
}
return $valida;
}
Por: Saúl
10/12/07
La de Moz esta muy bien, me sirvio para ver unos errores que tenía, sin embargo falla en algunos casos, da como válidas:
_soy_saul@algo.com
_soy_saul@_algo.otro.com

y lo que ya mencionaron del arroba


creo que la mía es casi infalibre:
^[[:alnum:]]+((.|_)[[:alnum:]]+)*@([[:alnum:]]+.)+[[:alnum:]]{2,6}$

Manuales relacionados
Categorias relacionadas
El autor
Lectura recomendada
Compra este libro en Agapea, la librería urgente a domicilio.
Últimas noticias
Alojados en el grupo