Django

Code

Ticket #4036: forms.py

File forms.py, 1.9 kB (added by garcia_marc, 1 year ago)

contrib/localflavor/es/forms.py (Spain NIF validation function)

Line 
1 """
2 Spain-specific Form helpers
3 """
4 from django.newforms import ValidationError
5 from django.newforms.fields import Field, EMPTY_VALUES
6 from django.utils.translation import ugettext_lazy as _
7
8 class ESNifField(Field):
9         """
10         Spanish NIF/NIE/CIF (Fiscal Identification Number) code.
11
12         Validates three diferent formats,
13                 NIF (individuals): 12345678A
14                 CIF (companies): A12345678
15                 NIE (foreigners): X12345678A
16         according to the simple checksum algorithm.
17         Value can include any separator between number and letter (commonly used hyphen or space). Actually any strange character is ignored in whole value.
18         Less (or more) than 8 digits are allowed. It's not a mistake, old NIFs have 7 numbers, and 9 number codes could exist in the future.
19         Return value is normalized like patterns in previous examples (also changing letters to upper case).
20         """
21         def clean(self, value):
22                 super(ESNifField, self).clean(value)
23                 if value in EMPTY_VALUES:
24                         return ''
25                 checksum_list = 'TRWAGMYFPDXBNJZSQVHLCKE'
26                 normalized_value = ''
27                 for char in value:
28                         if char.isdigit() or char.upper() in checksum_list:
29                                 normalized_value += char.upper()
30                 if normalized_value[0] == 'X' and normalized_value[1:-1].isdigit() and normalized_value[-1] in checksum_list:
31                         nif_number, nif_letter = normalized_value[1:-1], normalized_value[-1]
32                 elif normalized_value[0] in checksum_list and normalized_value[1:].isdigit():
33                         nif_letter, nif_number = normalized_value[0], normalized_value[1:]
34                 elif normalized_value[:-1].isdigit() and normalized_value[-1] in checksum_list:
35                         nif_number, nif_letter = normalized_value[:-1], normalized_value[-1]
36                 else:
37                         print normalized_value
38                         raise ValidationError(_('Enter a CIF, NIF or NIE in the format Z99999999, 99999999Z or X99999999Z.'))
39
40                 if nif_letter == checksum_list[int(nif_number) % len(checksum_list)]:
41                         return normalized_value
42                 else:
43                         raise ValidationError(_('Invalid letter for CIF/NIF number'))