Django

Code

Ticket #3946: ch-localflavor2.diff

File ch-localflavor2.diff, 8.7 kB (added by charly.wilhelm@gmail.com, 2 years ago)

Replacement with the suggestions of mtredinnick

  • django/contrib/localflavor/ch/ch_states.py

    old new  
     1# -*- coding: utf-8 -* 
     2from django.utils.translation import gettext_lazy as _ 
     3 
     4STATE_CHOICES = ( 
     5    ('AG', _('Aargau')), 
     6    ('AI', _('Appenzell Innerrhoden')), 
     7    ('AR', _('Appenzell Ausserrhoden')), 
     8    ('BS', _('Basel-Stadt')), 
     9    ('BL', _('Basel-Land')), 
     10    ('BE', _('Berne')), 
     11    ('FR', _('Fribourg')), 
     12    ('GE', _('Geneva')), 
     13    ('GL', _('Glarus')), 
     14    ('GR', _('Graubuenden')), 
     15    ('JU', _('Jura')), 
     16    ('LU', _('Lucerne')), 
     17    ('NE', _('Neuchatel')), 
     18    ('NW', _('Nidwalden')), 
     19    ('OW', _('Obwalden')), 
     20    ('SH', _('Schaffhausen')), 
     21    ('SZ', _('Schwyz')), 
     22    ('SO', _('Solothurn')), 
     23    ('SG', _('St. Gallen')), 
     24    ('TG', _('Thurgau')), 
     25    ('TI', _('Ticino')), 
     26    ('UR', _('Uri')), 
     27    ('VS', _('Valais')), 
     28    ('VD', _('Vaud')), 
     29    ('ZG', _('Zug')), 
     30    ('ZH', _('Zurich')) 
     31) 
  • django/contrib/localflavor/ch/forms.py

    old new  
     1""" 
     2Swiss-specific Form helpers 
     3""" 
     4 
     5from django.newforms import ValidationError 
     6from django.newforms.fields import Field, RegexField, Select, EMPTY_VALUES 
     7from django.utils.encoding import smart_unicode 
     8from django.utils.translation import gettext 
     9import re 
     10 
     11id_re = re.compile(r"^(?P<idnumber>\w{8})(?P<pos9>(\d{1}|<))(?P<checksum>\d{1})$") 
     12phone_digits_re = re.compile(r'^0([1-9]{1})\d{8}$') 
     13 
     14class CHZipCodeField(RegexField): 
     15    def __init__(self, *args, **kwargs): 
     16        super(CHZipCodeField, self).__init__(r'^\d{4}$', 
     17        max_length=None, min_length=None, 
     18        error_message=gettext('Enter a zip code in the format XXXX.'), 
     19        *args, **kwargs) 
     20 
     21class CHPhoneNumberField(Field): 
     22    """ 
     23    Validate local Swiss phone number (not international ones) 
     24    The correct format is '0XX XXX XX XX'. 
     25    '0XX.XXX.XX.XX' and '0XXXXXXXXX' validate but are corrected to 
     26    '0XX XXX XX XX'. 
     27    """ 
     28    def clean(self, value): 
     29        super(CHPhoneNumberField, self).clean(value) 
     30        if value in EMPTY_VALUES: 
     31            return u'' 
     32        value = re.sub('(\.|\s|/|-)', '', smart_unicode(value)) 
     33        m = phone_digits_re.search(value) 
     34        if m: 
     35            return u'%s %s %s %s' % (value[0:3], value[3:6], value[6:8], value[8:10]) 
     36        raise ValidationError('Phone numbers must be in 0XX XXX XX XX format.') 
     37     
     38class CHStateSelect(Select): 
     39    """ 
     40    A Select widget that uses a list of CH states as its choices. 
     41    """ 
     42    def __init__(self, attrs=None): 
     43        from ch_states import STATE_CHOICES # relative import 
     44        super(CHStateSelect, self).__init__(attrs, choices=STATE_CHOICES) 
     45 
     46class CHIdentityCardNumberField(Field): 
     47    """ 
     48    A Swiss identity card number. 
     49 
     50    Checks the following rules to determine whether the number is valid: 
     51 
     52        * Conforms to the X1234567<0 or 1234567890 format. 
     53        * Included checksums match calculated checksums 
     54 
     55    Algorithm is documented at http://adi.kousz.ch/artikel/IDCHE.htm 
     56    """ 
     57    
     58    def has_valid_checksum(self, number): 
     59        given_number, given_checksum = number[:-1], number[-1] 
     60        new_number = given_number 
     61        calculated_checksum = 0 
     62        fragment = "" 
     63        parameter = 7 
     64 
     65        first = str(number[:1]) 
     66        if first.isalpha(): 
     67            num = ord(first.upper()) - 65 
     68            if num < 0 or num > 8: 
     69                return False 
     70            new_number = str(num) + new_number[1:] 
     71            new_number = new_number[:8] + '0' 
     72 
     73        if not new_number.isdigit(): 
     74            return False 
     75         
     76        for i in range(len(new_number)): 
     77          fragment = int(new_number[i])*parameter 
     78          calculated_checksum += fragment 
     79 
     80          if parameter == 1: 
     81            parameter = 7 
     82          elif parameter == 3: 
     83            parameter = 1 
     84          elif parameter ==7: 
     85            parameter = 3 
     86 
     87        return str(calculated_checksum)[-1] == given_checksum 
     88 
     89    def clean(self, value): 
     90        super(CHIdentityCardNumberField, self).clean(value) 
     91        error_msg = gettext('Enter a valid Swiss identity or passport card number in X1234567<0 or 1234567890 format') 
     92        if value in EMPTY_VALUES: 
     93            return u'' 
     94         
     95        match = re.match(id_re, value) 
     96        if not match: 
     97            raise ValidationError(error_msg) 
     98 
     99        idnumber, pos9, checksum = match.groupdict()['idnumber'], match.groupdict()['pos9'], match.groupdict()['checksum'] 
     100 
     101        if idnumber == '00000000' or \ 
     102           idnumber == 'A0000000': 
     103            raise ValidationError(error_msg) 
     104 
     105        all_digits = "%s%s%s" % (idnumber, pos9, checksum) 
     106        if not self.has_valid_checksum(all_digits): 
     107            raise ValidationError(error_msg) 
     108 
     109        return u'%s%s%s' % (idnumber, pos9, checksum) 
  • tests/regressiontests/forms/localflavor.py

    old new  
    882882Traceback (most recent call last): 
    883883... 
    884884ValidationError: [u'Enter a valid German identity card number in XXXXXXXXXXX-XXXXXXX-XXXXXXX-X format.'] 
     885<<<<<<< .mine 
    885886 
     887# CHZipCodeField ############################################################ 
     888 
     889>>> from django.contrib.localflavor.ch.forms import CHZipCodeField 
     890>>> f = CHZipCodeField() 
     891>>> f.clean('800x') 
     892Traceback (most recent call last): 
     893... 
     894ValidationError: [u'Enter a zip code in the format XXXX.'] 
     895>>> f.clean('80 00') 
     896Traceback (most recent call last): 
     897... 
     898ValidationError: [u'Enter a zip code in the format XXXX.'] 
     899>>> f.clean('8000') 
     900u'8000' 
     901 
     902# CHPhoneNumberField ######################################################## 
     903 
     904>>> from django.contrib.localflavor.ch.forms import CHPhoneNumberField 
     905>>> f = CHPhoneNumberField() 
     906>>> f.clean('01234567890') 
     907Traceback (most recent call last): 
     908... 
     909ValidationError: [u'Phone numbers must be in 0XX XXX XX XX format.'] 
     910>>> f.clean('1234567890') 
     911Traceback (most recent call last): 
     912... 
     913ValidationError: [u'Phone numbers must be in 0XX XXX XX XX format.'] 
     914>>> f.clean('0123456789') 
     915u'012 345 67 89' 
     916 
     917# CHIdentityCardNumberField ################################################# 
     918 
     919>>> from django.contrib.localflavor.ch.forms import CHIdentityCardNumberField 
     920>>> f = CHIdentityCardNumberField() 
     921>>> f.clean('C1234567<0') 
     922u'C1234567<0' 
     923>>> f.clean('C1234567<1') 
     924Traceback (most recent call last): 
     925... 
     926ValidationError: [u'Enter a valid Swiss identity or passport card number in X1234567<0 or 1234567890 format'] 
     927>>> f.clean('2123456700') 
     928u'2123456700' 
     929>>> f.clean('2123456701') 
     930Traceback (most recent call last): 
     931... 
     932ValidationError: [u'Enter a valid Swiss identity or passport card number in X1234567<0 or 1234567890 format'] 
     933 
     934# CHStateSelect ############################################################# 
     935 
     936>>> from django.contrib.localflavor.ch.forms import CHStateSelect 
     937>>> w = CHStateSelect() 
     938>>> w.render('state', 'AG') 
     939u'<select name="state">\n<option value="AG" selected="selected">Aargau</option>\n<option value="AI">Appenzell Innerrhoden</option>\n<option value="AR">Appenzell Ausserrhoden</option>\n<option value="BS">Basel-Stadt</option>\n<option value="BL">Basel-Land</option>\n<option value="BE">Berne</option>\n<option value="FR">Fribourg</option>\n<option value="GE">Geneva</option>\n<option value="GL">Glarus</option>\n<option value="GR">Graubuenden</option>\n<option value="JU">Jura</option>\n<option value="LU">Lucerne</option>\n<option value="NE">Neuchatel</option>\n<option value="NW">Nidwalden</option>\n<option value="OW">Obwalden</option>\n<option value="SH">Schaffhausen</option>\n<option value="SZ">Schwyz</option>\n<option value="SO">Solothurn</option>\n<option value="SG">St. Gallen</option>\n<option value="TG">Thurgau</option>\n<option value="TI">Ticino</option>\n<option value="UR">Uri</option>\n<option value="VS">Valais</option>\n<option value="VD">Vaud</option>\n<option value="ZG">Zug</option>\n<option value="ZH">Zurich</option>\n</select>' 
     940======= 
     941 
    886942## AUPostCodeField ########################################################## 
    887943 
    888944A field that accepts a four digit Australian post code. 
     
    10121068<option value="VIC">Victoria</option> 
    10131069<option value="WA">Western Australia</option> 
    10141070</select> 
     1071>>>>>>> .r4955 
    10151072"""