Validar NIF, CIF, NIE según ley vigente

Escrito por | Lenguaje JavaScript

Función en javascript que nos permite validar los NIF, CIF y NIE españoles según las leyes vigentes teniendo en cuenta todas las combinaciones incluidas las nuevas variantes de NIE con ‘T’, ‘Y’ y ‘Z’ así como todas las variantes de CIF para empresas, entidades, asociaciones, etc.

La función retorna los siguientes valores:

  • 1 > NIF correcto / -1 > NIF incorrecto
  • 2 > CIF correcto / -2 > CIF incorrecto
  • 3 > NIE correcto / -3 > NIE incorrecto
  • 0 > Valor desconocido (campo vacio, formato incorrecto, etc)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
//Retorna: 1 = NIF ok, 2 = CIF ok, 3 = NIE ok, -1 = NIF error, -2 = CIF error, -3 = NIE error, 0 = ??? error
function valida_nif_cif_nie(a) 
{
	var temp=a.toUpperCase();
	var cadenadni="TRWAGMYFPDXBNJZSQVHLCKE";
 
	if (temp!==''){
		//si no tiene un formato valido devuelve error
		if ((!/^[A-Z]{1}[0-9]{7}[A-Z0-9]{1}$/.test(temp) && !/^[T]{1}[A-Z0-9]{8}$/.test(temp)) && !/^[0-9]{8}[A-Z]{1}$/.test(temp))
		{
			return 0;
		}
 
		//comprobacion de NIFs estandar
		if (/^[0-9]{8}[A-Z]{1}$/.test(temp))
		{
			posicion = a.substring(8,0) % 23;
			letra = cadenadni.charAt(posicion);
			var letradni=temp.charAt(8);
			if (letra == letradni)
			{
			   	return 1;
			}
			else
			{
				return -1;
			}
		}
 
		//algoritmo para comprobacion de codigos tipo CIF
		suma = parseInt(a[2])+parseInt(a[4])+parseInt(a[6]);
		for (i = 1; i < 8; i += 2)
		{
			temp1 = 2 * parseInt(a[i]);
			temp1 += '';
			temp1 = temp1.substring(0,1);
			temp2 = 2 * parseInt(a[i]);
			temp2 += '';
			temp2 = temp2.substring(1,2);
			if (temp2 == '')
			{
				temp2 = '0';
			}
 
			suma += (parseInt(temp1) + parseInt(temp2));
		}
		suma += '';
		n = 10 - parseInt(suma.substring(suma.length-1, suma.length));
 
		//comprobacion de NIFs especiales (se calculan como CIFs)
		if (/^[KLM]{1}/.test(temp))
		{
			if (a[8] == String.fromCharCode(64 + n))
			{
				return 1;
			}
			else
			{
				return -1;
			}
		}
 
		//comprobacion de CIFs
		if (/^[ABCDEFGHJNPQRSUVW]{1}/.test(temp))
		{
			temp = n + '';
			if (a[8] == String.fromCharCode(64 + n) || a[8] == parseInt(temp.substring(temp.length-1, temp.length)))
			{
				return 2;
			}
			else
			{
				return -2;
			}
		}
 
		//comprobacion de NIEs
		//T
		if (/^[T]{1}/.test(temp))
		{
			if (a[8] == /^[T]{1}[A-Z0-9]{8}$/.test(temp))
			{
				return 3;
			}
			else
			{
				return -3;
			}
		}
 
		//XYZ
		if (/^[XYZ]{1}/.test(temp))
		{
			pos = str_replace(['X', 'Y', 'Z'], ['0','1','2'], temp).substring(0, 8) % 23;
			if (a[8] == cadenadni.substring(pos, pos + 1))
			{
				return 3;
			}
			else
			{
				return -3;
			}
		}
	}
 
	return 0;
}

Para los cálculos se usa esta función auxiliar que emula el str_replace de PHP

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
function str_replace(search, replace, subject) {
    // http://kevin.vanzonneveld.net
    // +   original by: Kevin van Zonneveld (http://kevin.vanzonneveld.net)
    // +   improved by: Gabriel Paderni
    // +   improved by: Philip Peterson
    // +   improved by: Simon Willison (http://simonwillison.net)
    // +    revised by: Jonas Raoni Soares Silva (http://www.jsfromhell.com)
    // +   bugfixed by: Anton Ongson
    // +      input by: Onno Marsman
    // +   improved by: Kevin van Zonneveld (http://kevin.vanzonneveld.net)
    // +    tweaked by: Onno Marsman
    // *     example 1: str_replace(' ', '.', 'Kevin van Zonneveld');
    // *     returns 1: 'Kevin.van.Zonneveld'
    // *     example 2: str_replace(['{name}', 'l'], ['hello', 'm'], '{name}, lars');
    // *     returns 2: 'hemmo, mars'
 
    var f = search, r = replace, s = subject;
    var ra = r instanceof Array, sa = s instanceof Array, f = [].concat(f), r = [].concat(r), i = (s = [].concat(s)).length;
 
    while (j = 0, i--) {
        if (s[i]) {
            while (s[i] = s[i].split(f[j]).join(ra ? r[j] || "" : r[0]), ++j in f){};
        }
    };
 
    return sa ? s : s[0];
}
Compartir:
  • Digg
  • del.icio.us
  • Facebook
  • Google
  • BarraPunto
  • BlogMemes
  • Meneame
  • Technorati
  • TwitThis

Entradas relacionadas:

  1. Validar el dígito de control de una cuenta bancaria española

Comentarios

Hay (14) comentarios para Validar NIF, CIF, NIE según ley vigente

  1. Hola,

    Muy buena función, sin embargo solo me funcionaba en FF y no en IE. El motivo era la utilización de “a[2]“, que al tratarse de cadenas no me lo pillaba bien. Lo cambié por a.charAt(), como también se usa en la función (pero en la sección de NIFs) et voila!

    Saludos

  2. La función falla en la validación de los NIES. La correcta arreglada es la siguiente:

    //Retorna: 1 = NIF ok, 2 = CIF ok, 3 = NIE ok, -1 = NIF error, -2 = CIF error, -3 = NIE error, 0 = ??? error
    function valida_nif_cif_nie(a)
    {

    var temp=a.toUpperCase();
    var cadenadni=”TRWAGMYFPDXBNJZSQVHLCKE”;
    if (temp!==”){

    //si no tiene un formato valido devuelve error
    if ((!/^[A-Z]{1}[0-9]{7}[A-Z0-9]{1}$/.test(temp) && !/^[T]{1}[A-Z0-9]{8}$/.test(temp)) && !/^[0-9]{8}[A-Z]{1}$/.test(temp))
    {
    return 0;
    }

    //comprobacion de NIFs estandar
    if (/^[0-9]{8}[A-Z]{1}$/.test(temp))
    {
    posicion = a.substring(8,0) % 23;
    letra = cadenadni.charAt(posicion);
    var letradni=temp.charAt(8);
    if (letra == letradni)
    {
    return 1;
    }
    else
    {
    return -1;
    }
    }

    //algoritmo para comprobacion de codigos tipo CIF
    suma = parseInt(a.charAt(2))+parseInt(a.charAt(4))+parseInt(a.charAt(6));

    for (i = 1; i < 8; i += 2)
    {
    temp1 = 2 * parseInt(a.charAt(i));
    temp1 += ”;
    temp1 = temp1.substring(0,1);
    temp2 = 2 * parseInt(a.charAt(i));
    temp2 += ”;
    temp2 = temp2.substring(1,2);
    if (temp2 == ”)
    {
    temp2 = ‘0′;
    }

    suma += (parseInt(temp1) + parseInt(temp2));
    }
    suma += ”;
    n = 10 - parseInt(suma.substring(suma.length-1, suma.length));

    //comprobacion de NIFs especiales (se calculan como CIFs)
    if (/^[KLM]{1}/.test(temp))
    {
    if (a.charAt(8) == String.fromCharCode(64 + n))
    {
    return 1;
    }
    else
    {
    return -1;
    }
    }
    //comprobacion de CIFs
    if (/^[ABCDEFGHJNPQRSUVW]{1}/.test(temp))
    {
    temp = n + ”;
    if (a.charAt(8) == String.fromCharCode(64 + n) || a.charAt(8) == parseInt(temp.substring(temp.length-1, temp.length)))
    {
    return 2;
    }
    else
    {
    return -2;
    }
    }

    //comprobacion de NIEs
    //T
    if (/^[T]{1}/.test(temp))
    {
    if (a.charAt(8) == /^[T]{1}[A-Z0-9]{8}$/.test(temp))
    {
    return 3;
    }
    else
    {
    return -3;
    }
    }

    //XYZ
    if (/^[XYZ]{1}/.test(temp))
    {

    temp = temp.replace(’X',’0′)
    temp = temp.replace(’Y',’1′)
    temp = temp.replace(’Z',’2′)
    pos = temp.substring(0, 8) % 23;

    if (a.charAt(8) == cadenadni.substring(pos, pos + 1))
    {
    return 3;
    }
    else
    {
    return -3;
    }
    }
    }
    return 0;
    }

  3. ¿Esto va a funcionar bien en la validacion de los NIE’s?


    temp = temp.replace(’X’,’0′)
    temp = temp.replace(’Y’,’1′)
    temp = temp.replace(’Z’,’2′)

    Los digo porque asi puede que la ultima letra del NIE coincida con alguna de estas tres y se reemplace de manera incorrecta por un numero.

  4. Buenas he estado probando la funcion y la nueva version que creo que sería mas correcta es la siguiente, ya que he modificado la funcion str_replace y solo modifica el primer digito.

  5. function str_replace(search, position, replace, subject) {

    var f = search, r = replace, s = subject, p = position;
    var ra = r instanceof Array, sa = s instanceof Array, f = [].concat(f), r = [].concat(r), i = (s = [].concat(s)).length;

    while (j = 0, i–) {
    if (s[i]) {
    while (s[p] = s[p].split(f[j]).join(ra ? r[j] || “” : r[0]), ++j in f){};
    }
    };

    return sa ? s : s[0];

    }

  6. y el la zona de validacion de NIE cambiar a esta linea

    pos = str_replace(['X', 'Y', 'Z'], 0, ['0','1','2'], temp).substring(0, 8) % 23;

    Tambien en la validacion de los NIE’s que comienzan con T el if correcto seria


    if (/^[T]{1}[A-Z0-9]{8}$/.test(temp))
    ..

    Espero que os ayude un saludo

  7. Gracias todos, tanto a josep rosell por el código original como a los demás que habeis ayudado a pulirlo, me habeis sacado de un apuro. Gracias!

  8. Moltes gràcies, muchas gracias!!!

    Me he encontrado con problemas, que debido a mi bajo nivel de conocimiento de javascript he tenido que ir depurando. Básicamente, he tenido que substituir todas las referencias a los carácteres de strings (referenciados en formato array como a[8]) por una característica que ya se utilizaba en la parte de validación de NIF, .charAt(8) ).

    Una vez aplicado, ya he podido validar los CIF’s introducidos por pantalla.

  9. pero ¿la version original se ha modificado para cumplir los errores comentados?

    gracias

  10. Gracias por todo, a mi me ha sido util tb

  11. Duda muy tonta. Como recoger lo que devuelve la funcion

  12. Elena, realmente pregunta muy tonta, tontísima diria yo. Cuanto intrusismo en esta profesió, que asco ….

  13. Eleno, hay una posibilidad de que Elena esté empezando a estudiar javascript y programación. Tu naciste enseñado, por lo que vemos.

    Gracias por el aporte

  14. Eleno, gente como tu hace que me sienta orgulloso de ser lo que tu calificas un “intruso”… aunque probablemente me haya echando mas años y horas de estudio que tu…

Deja un comentario