2
Hong Kong specific Form helpers
4
from __future__ import absolute_import, unicode_literals
8
from django.core.validators import EMPTY_VALUES
9
from django.forms import CharField
10
from django.forms import ValidationError
11
from django.utils.encoding import smart_text
12
from django.utils.translation import ugettext_lazy as _
15
hk_phone_digits_re = re.compile(r'^(?:852-?)?(\d{4})[-\.]?(\d{4})$')
16
hk_special_numbers = ('999', '992', '112')
17
hk_phone_prefixes = ('2', '3', '5', '6', '8', '9')
18
hk_formats = ['XXXX-XXXX', '852-XXXX-XXXX', '(+852) XXXX-XXXX',
19
'XXXX XXXX', 'XXXXXXXX']
23
class HKPhoneNumberField(CharField):
25
Validate Hong Kong phone number.
26
The input format can be either one of the followings:
27
'XXXX-XXXX', '852-XXXX-XXXX', '(+852) XXXX-XXXX',
28
'XXXX XXXX', or 'XXXXXXXX'.
29
The output format is 'XXXX-XXXX'.
31
Note: The phone number shall not start with 999, 992, or 112.
32
And, it should start with either 2, 3, 5, 6, 8, or 9.
34
Ref - http://en.wikipedia.org/wiki/Telephone_numbers_in_Hong_Kong
36
default_error_messages = {
37
'disguise': _('Phone number should not start with ' \
38
'one of the followings: %s.' % \
39
', '.join(hk_special_numbers)),
40
'invalid': _('Phone number must be in one of the following formats: '
41
'%s.' % ', '.join(hk_formats)),
42
'prefix': _('Phone number should start with ' \
43
'one of the followings: %s.' % \
44
', '.join(hk_phone_prefixes)),
47
def __init__(self, *args, **kwargs):
48
super(HKPhoneNumberField, self).__init__(*args, **kwargs)
50
def clean(self, value):
51
super(HKPhoneNumberField, self).clean(value)
53
if value in EMPTY_VALUES:
56
value = re.sub('(\(|\)|\s+|\+)', '', smart_text(value))
57
m = hk_phone_digits_re.search(value)
59
raise ValidationError(self.error_messages['invalid'])
61
value = '%s-%s' % (m.group(1), m.group(2))
62
for special in hk_special_numbers:
63
if value.startswith(special):
64
raise ValidationError(self.error_messages['disguise'])
66
prefix_found = map(lambda prefix: value.startswith(prefix),
68
if not any(prefix_found):
69
raise ValidationError(self.error_messages['prefix'])