python-stdnum-0.9/0000755000000000000000000000000012260536562014160 5ustar rootroot00000000000000python-stdnum-0.9/getiban.py0000755000000000000000000000547012260533041016141 0ustar rootroot00000000000000#!/usr/bin/env python # getiban.py - script to donwload and parse data from the IBAN registry # # Copyright (C) 2011, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """This script downloads data from SWIFT (the Society for Worldwide Interbank Financial Telecommunication which is the official IBAN registrar) to get the data needed to correctly parse and validate IBANs.""" import csv import urllib # The place where the current version of IBAN_Registry.txt can be downloaded. download_url = 'http://www.swift.com/dsp/resources/documents/IBAN_Registry.txt' def clean_row(row): """Clean up a read row from the CSV file.""" stripit = ' \t\n\r;:\'"' return dict( (k.strip(stripit).lower(), v.strip(stripit)) for k, v in row.items()) def get_country_codes(line): """Return the list of country codes this line has.""" # simplest case first if len(line['country code as defined in iso 3166']) == 2: return [line['country code as defined in iso 3166']] # fall back to parsing the IBAN structure return [x.strip()[:2] for x in line['iban structure'].split(',')] def parse(f): """Parse the specified file.""" print '# generated from IBAN_Registry.txt, downloaded from' print '# %s' % download_url for row in csv.DictReader(f, delimiter='\t', quotechar='"'): row = clean_row(row) bban = row['bban structure'] if not(bban) or bban.lower() == 'not in use': bban = row['iban structure'] for cc in get_country_codes(row): if bban.startswith(cc + '2!n'): bban = bban[5:] # print country line print '%s country="%s" bban="%s"' % ( cc, row['name of country'], bban) # TODO: some countries have a fixed check digit value # TODO: some countries have extra check digits # TODO: use "Bank identifier position within the BBAN" field # to add labels to the ranges (Bank identifier and Branch # Identifier) if __name__ == '__main__': #f = open('IBAN_Registry.txt', 'r') f = urllib.urlopen(download_url) parse(f) python-stdnum-0.9/setup.py0000755000000000000000000000404712260526703015676 0ustar rootroot00000000000000#!/usr/bin/env python # setup.py - python-stdnum installation script # # Copyright (C) 2010, 2011, 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """python-stdnum installation script.""" import os import sys from setuptools import setup, find_packages import stdnum # fix permissions for sdist if 'sdist' in sys.argv: os.system('chmod -R a+rX .') os.umask(int('022', 8)) setup(name='python-stdnum', version=stdnum.__version__, description='Python module to handle standardized numbers and codes', long_description=stdnum.__doc__, author='Arthur de Jong', author_email='arthur@arthurdejong.org', url='http://arthurdejong.org/python-stdnum/', license='LGPL', classifiers=[ 'Development Status :: 4 - Beta', 'Intended Audience :: Developers', 'Intended Audience :: System Administrators', 'License :: OSI Approved :: GNU Library or Lesser General Public License (LGPL)', 'Operating System :: OS Independent', 'Programming Language :: Python', 'Topic :: Software Development :: Libraries :: Python Modules', 'Topic :: Text Processing :: General', ], packages=find_packages(), package_data={'': ['*.dat']}, install_requires=['distribute'], extras_require={ 'VIES': ['suds'], }, ) python-stdnum-0.9/tests/0000755000000000000000000000000012260536562015322 5ustar rootroot00000000000000python-stdnum-0.9/tests/test_verhoeff.doctest0000644000000000000000000000366712154625050021561 0ustar rootroot00000000000000test_verhoeff.doctest - more detailed doctests for stdnum.verhoeff module Copyright (C) 2010, 2011, 2013 Arthur de Jong This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA This file contains more detailed doctests for the stdnum.verhoeff module. It tries to test more corner cases and detailed functionality that is not really useful as module documentation. >>> from stdnum import verhoeff These are normal variations that should just work. Calculating checksums: >>> verhoeff.checksum('654') 1 >>> verhoeff.checksum('1428570') 0 >>> verhoeff.checksum('398438246238642378648236487236482734') 3 The same numbers but now simply ask for validation: >>> verhoeff.validate('654') Traceback (most recent call last): ... InvalidChecksum: ... >>> verhoeff.validate('1428570') '1428570' >>> verhoeff.validate('398438246238642378648236487236482734') Traceback (most recent call last): ... InvalidChecksum: ... Adding a check digit to the numbers so they are all valid: >>> verhoeff.calc_check_digit('654') '8' >>> verhoeff.validate('6548') '6548' >>> verhoeff.calc_check_digit('1428570') '8' >>> verhoeff.validate('1428570') '1428570' >>> verhoeff.calc_check_digit('398438246238642378648236487236482734') '7' >>> verhoeff.validate('3984382462386423786482364872364827347') '3984382462386423786482364872364827347' python-stdnum-0.9/tests/test_luhn.doctest0000644000000000000000000000354612154625043020721 0ustar rootroot00000000000000test_luhn.doctest - more detailed doctests for stdnum.luhn module Copyright (C) 2010, 2011, 2013 Arthur de Jong This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA This file contains more detailed doctests for the stdnum.luhn module. It tries to test more corner cases and detailed functionality that is not really useful as module documentation. >>> from stdnum import luhn These are normal variations that should just work. Calculating checksums: >>> luhn.checksum('4992739871') 9 >>> luhn.checksum('490154203237518') 0 >>> luhn.checksum('abcdefe', alphabet='abcdef') 0 The same numbers but now simply ask for validation: >>> luhn.validate('4992739871') Traceback (most recent call last): ... InvalidChecksum: ... >>> luhn.validate('490154203237518') '490154203237518' >>> luhn.validate('abcdefe', alphabet='abcdef') 'abcdefe' Adding a check digit to the numbers so they are all valid: >>> luhn.calc_check_digit('4992739871') '6' >>> luhn.validate('49927398716') '49927398716' >>> luhn.calc_check_digit('142857') '2' >>> luhn.validate('1428572') '1428572' >>> luhn.calc_check_digit('398438246238642378648236487236482734') '7' >>> luhn.validate('3984382462386423786482364872364827347') '3984382462386423786482364872364827347' python-stdnum-0.9/tests/test_robustness.doctest0000644000000000000000000000244212154625047022160 0ustar rootroot00000000000000test_robustness.doctest - test is_valid() functions to not break Copyright (C) 2011, 2012 Arthur de Jong This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA This file contains some tests for modules in the stdnum package to check whether all provided is_valid() functions can handle clearly invalid junk. >>> testvalues = ( None, '*&^%$', '', 0, False, object(), 'Q', 'QQ', '3') >>> from stdnum.util import get_number_modules Go over each module and try every value. >>> badmodules = [] >>> for mod in get_number_modules(): ... results = [ x for x in testvalues if mod.is_valid(x) != False ] ... if results: ... print(mod.__name__, results) python-stdnum-0.9/tests/test_isan.doctest0000644000000000000000000000665712154625043020713 0ustar rootroot00000000000000test_isan.doctest - more detailed doctests for stdnum.isan module Copyright (C) 2010, 2012, 2013 Arthur de Jong This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA This file contains more detailed doctests for the stdnum.isan module. It tries to test more corner cases and detailed functionality that is not really useful as module documentation. >>> from stdnum import isan This is how numbers should be split (possible with and without episode number): >>> isan.split('000000018947000000000000') ('000000018947', '0000', '', '00000000', '') >>> isan.split('0000-0000-D07A-0090-Q-0000-0000-X') ('00000000D07A', '0090', 'Q', '00000000', 'X') >>> isan.split('000000018947000000000000') ('000000018947', '0000', '', '00000000', '') >>> isan.split('1881-66C7-3420-6541-Y') ('188166C73420', '6541', 'Y', '', '') >>> isan.split('1881-66C7-3420-6541') ('188166C73420', '6541', '', '', '') Compacting should also work: >>> isan.compact('000000018947000000000000') '000000018947000000000000' >>> isan.compact('0000-0000-D07A-0090-Q-0000-0000-X') '00000000D07A009000000000' >>> isan.compact('000000018947000000000000') '000000018947000000000000' >>> isan.compact('1881-66C7-3420-6541-Y') '188166C734206541' >>> isan.compact('1881-66C7-3420-6541') '188166C734206541' These should be valid numbers: >>> isan.validate('0000-0000-D07A-0090-Q-0000-0000-X') '00000000D07A0090Q00000000X' >>> isan.validate('1881-66C7-3420-6541-Y-9F3A-0245-O') '188166C734206541Y9F3A0245O' >>> isan.validate('0000-0000-D07A-0090-Q-0000-0000-X') '00000000D07A0090Q00000000X' >>> isan.validate('0000-0000-D07A-0090-Q') '00000000D07A0090Q' And these should be invalid: >>> isan.validate('00000000D07A0090-Z') Traceback (most recent call last): ... InvalidChecksum: ... >>> isan.validate('3abc6800-0041X1-20') Traceback (most recent call last): ... InvalidFormat: ... >>> isan.validate('3abc6800-0041') Traceback (most recent call last): ... InvalidLength: ... The format() function can add the check digit if needed. It should leave alone existing check digits (even invalid ones) and respect the presence or absence of a version number. >>> isan.format('00000000D07A0090') '0000-0000-D07A-0090-Q' >>> isan.format('1881-66C734206541-9F3A-0245') '1881-66C7-3420-6541-Y-9F3A-0245-O' >>> isan.format('1881-66C7-3420-6541-?-9F3A-0245-?', strip_check_digits=True, add_check_digits=True) '1881-66C7-3420-6541-Y-9F3A-0245-O' >>> isan.validate('1881-66C7-3420-6541-Y-9F3A-0245-O', strip_check_digits=True) '188166C7342065419F3A0245' >>> isan.validate('188166C7342065419F3A0245', add_check_digits=True) '188166C734206541Y9F3A0245O' A simple test for the to_binary() function. >>> import binascii >>> import sys >>> x = binascii.b2a_hex(isan.to_binary('0000-0000-D07A-0090-Q')) >>> if sys.version > '3': ... x = str(x, encoding='ascii') >>> x '00000000d07a0090' python-stdnum-0.9/tests/test_iban.doctest0000644000000000000000000001262712154625043020664 0ustar rootroot00000000000000test_iban.doctest - more detailed doctests for the stdnum.iban module Copyright (C) 2011 Arthur de Jong This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA This file contains more detailed doctests for the stdnum.iban module. It tries to test more corner cases and detailed functionality that is not really useful as module documentation. >>> from stdnum import iban These should all be valid numbers and are from the IBAN REGISTRY as sample numbers: >>> numbers = ''' ... AL47212110090000000235698741 ... AD1200012030200359100100 ... AT611904300234573201 ... BE68539007547034 ... BA391290079401028494 ... BG80BNBG96611020345678 ... HR1210010051863000160 ... CY17002001280000001200527600 ... CZ6508000000192000145399 ... CZ9455000000001011038930 ... DK5000400440116243 ... FO6264600001631634 ... GL8964710001000206 ... EE382200221020145685 ... FI2112345600000785 ... FI5542345670000081 ... FR1420041010050500013M02606 ... DE89370400440532013000 ... GE29NB0000000101904917 ... GI75NWBK000000007099453 ... GR1601101250000000012300695 ... HU42117730161111101800000000 ... IS140159260076545510730339 ... IE29AIBK93115212345678 ... IL620108000000099999999 ... IT60X0542811101000000123456 ... LV80BANK0000435195001 ... LB62099900000001001901229114 ... LI21088100002324013AA ... LT121000011101001000 ... LU280019400644750000 ... MK07250120000058984 ... MT84MALT011000012345MTLCAST001S ... MR1300020001010000123456753 ... MU17 BOMM0101101030300200000MUR ... MC1112739000700011111000h79 ... ME25505000012345678951 ... NL91ABNA0417164300 ... NO9386011117947 ... PL61109010140000071219812874 ... PT50000201231234567890154 ... RO49AAAA1B31007593840000 ... SM86U0322509800000000270100 ... SA0380000000608010167519 ... RS35260005601001611379 ... SK3112000000198742637541 ... SI56191000000123438 ... ES9121000418450200051332 ... SE4550000000058398257466 ... CH9300762011623852957 ... TN5910006035183598478831 ... TR330006100519786457841326 ... GB29NWBK60161331926819 ... AL47 2121 1009 0000 0002 3569 8741 ... AD12 0001 2030 2003 5910 0100 ... AT61 1904 3002 3457 3201 ... BE68 5390 0754 7034 ... BA39 1290 0794 0102 8494 ... BG80 BNBG 9661 1020 3456 78 ... HR12 1001 0051 8630 0016 0 ... CY17 0020 0128 0000 0012 0052 7600 ... CZ65 0800 0000 1920 0014 5399 ... CZ94 5500 0000 0010 1103 8930 ... DK50 0040 0440 1162 43 ... FO62 6460 0001 6316 34 ... GL89 6471 0001 0002 06 ... EE38 2200 2210 2014 5685 ... FI21 1234 5600 0007 85 ... FR14 2004 1010 0505 0001 3M02 606 ... DE89 3704 0044 0532 0130 00 ... GE29 NB00 0000 0101 9049 17 ... GI75 NWBK 0000 0000 7099 453 ... GR16 0110 1250 0000 0001 2300 695 ... HU42 1177 3016 1111 1018 0000 0000 ... IS14 0159 2600 7654 5510 7303 39 ... IE29 AIBK 9311 5212 3456 78 ... IL62 0108 0000 0009 9999 999 ... IT60 X054 2811 1010 0000 0123 456 ... LV80 BANK 0000 4351 9500 1 ... LB62 0999 0000 0001 0019 0122 9114 ... LI21 0881 0000 2324 013A A ... LT12 1000 0111 0100 1000 ... LU28 0019 4006 4475 0000 ... MK072 5012 0000 0589 84 ... MT84 MALT 0110 0001 2345 MTLC AST0 01S ... MR13 0002 0001 0100 0012 3456 753 ... MU17 BOMM 0101 1010 3030 0200 000M UR ... MC11 1273 9000 7000 1111 1000 h79 ... ME25 5050 0001 2345 6789 51 ... NL91 ABNA 0417 1643 00 ... NO93 8601 1117 947 ... PL61 1090 1014 0000 0712 1981 2874 ... PT50 0002 0123 1234 5678 9015 4 ... RO49 AAAA 1B31 0075 9384 0000 ... SM86 U032 2509 8000 0000 0270 100 ... SA03 8000 0000 6080 1016 7519 ... RS35 2600 0560 1001 6113 79 ... SK31 1200 0000 1987 4263 7541 ... SI56 1910 0000 0123 438 ... ES91 2100 0418 4502 0005 1332 ... SE45 5000 0000 0583 9825 7466 ... CH93 0076 2011 6238 5295 7 ... TN59 1000 6035 1835 9847 8831 ... TR33 0006 1005 1978 6457 8413 26 ... GB29 NWBK 6016 1331 9268 19 ... ''' >>> [ x for x in numbers.splitlines() if x and not iban.is_valid(x) ] [] These all have broken checksums or are mangled: >>> numbers = ''' ... AL48212110090000000235698741 ... AD1210012030200359100100 ... AT611804300234573201 ... BE68530907547034 ... BA391290709401028494 ... BG80BNBG99611020345678 ... HR1210010052863000160 ... CY17002001281000001200527600 ... CZ6508000000129000145399 ... CZ9455000000000101038930 ... DK5000400440116342 ... ''' >>> [ x for x in numbers.splitlines() if x and iban.is_valid(x) ] [] These are the wrong length but otherwise have valid checksums: >>> numbers = ''' ... AD48 0001 2030 2003 5910 01 ... AT93 1904 3002 3457 3201 99 ... BE36 5390 0754 7034 1234 ... BA30 1290 0794 0102 84 ... ''' >>> [ x for x in numbers.splitlines() if x and iban.is_valid(x) ] [] These are mostly valid except that they have alphabetic characters where they are not allowed or numbers where alphabetic characters are expected or have an unknown country code: >>> numbers = ''' ... BG93 BNBG 9661 1A20 3456 78 ... GI22 NW3K 0000 0000 7099 453 ... NL56 3003 0A17 1643 00 ... QQ93 1234 5678 ... ''' >>> [ x for x in numbers.splitlines() if x and iban.is_valid(x) ] [] python-stdnum-0.9/tests/test_bg_vat.doctest0000644000000000000000000000317312154625043021211 0ustar rootroot00000000000000test_bg_vat.doctest - more detailed doctests for stdnum.bg.vat module Copyright (C) 2012, 2013 Arthur de Jong This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA This file contains more detailed doctests for the stdnum.bg.vat module. It tries to cover more corner cases and detailed functionality that is not really useful as module documentation. >>> from stdnum.bg import vat Normal values that should just work. >>> vat.validate('103873594') # 9-digit legal entity '103873594' >>> vat.validate('131272009') # legal entity with fallback checksum '131272009' >>> vat.validate('7501020018') # physical person '7501020018' >>> vat.validate('8001010008') # physical person '8001010008' >>> vat.validate('8032056031') # physical person '8032056031' >>> vat.validate('7111042925') # foreigners '7111042925' >>> vat.validate('7153849522') # others '7153849522' Invalid checksum: >>> vat.validate('175074751') # invalid check digit Traceback (most recent call last): ... InvalidChecksum: ... python-stdnum-0.9/tests/test_eu_vat.doctest0000644000000000000000000003520412154625043021232 0ustar rootroot00000000000000test_eu_vat.doctest - more detailed doctests for the stdnum.eu.vat module Copyright (C) 2012, 2013 Arthur de Jong This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA This file contains more detailed doctests for the stdnum.eu.vat module. It tries to validate a number of VAT numbers that have been found online. >>> from stdnum.eu import vat >>> from stdnum.exceptions import * These have been found online and should all be valid numbers. >>> numbers = ''' ... ... ATU 142 43 102 ... ATU 15159209 ... ATU 28560205 ... ATU 34172105 ... ATU 40698107 ... ATU 46276408 ... ATU 49362201 ... ATU 54299806 ... ATU 54300000 ... ATU 56377717 ... ATU 57194903 ... ATU 64487479 ... ATU 64762368 ... ATU 64938009 ... ATU 65020906 ... ATU 65033803 ... ATU 65034704 ... ATU 65480455 ... ATU46080404 ... ATU61195628 ... ... BE (0)468.561.072 ... BE 0202.239.951 ... BE 0220.764.971 ... BE 0248.015.142 ... BE 0402 918 402 ... BE 0407.139.583 ... BE 0408 299 922 ... BE 0441.928.931 ... BE 0450 118 996 ... BE 0462423150 ... BE 0474 621 394 ... BE 0795 013 186 ... BE 0897290877 ... BE 444.503.092 ... BE 456.973.433 ... BE 464 401 356 ... BE413562567 ... BE697449992 ... ... BG 103873594 ... BG 124 551 319 ... BG 130 358 310 ... BG 131 272 009 ... BG 131202360 ... BG 147137471 ... BG 175074752 ... BG 175186242 ... BG 200182590 ... BG 200950556 ... BG130544585 ... Bg 200442771 ... ... CY 10246672X ... CY 10263870R ... CY 10274231F ... CY 10285193Z ... CY- 10277198H ... CY-10008489 A ... CY-10189098G ... CY-10258074Y ... CY-10259033P ... CY00632993 F ... ... CZ 25123891 ... CZ 25577581 ... CZ 26852357 ... CZ 61467839 ... CZ 640229/4448 ... CZ 640903926 ... CZ 6956220612 ... CZ 736028/5163 ... CZ 8058012314 ... CZ26780259 ... CZ48207926 ... CZ49620819 ... CZ6306150004 ... ... DE 118619592 ... DE 125014955 ... DE 129304291 ... DE 168347747 ... DE 181 207 708 ... DE 195131068 ... DE 204 760 908 ... DE 213 806 597 ... DE 221.304.969 ... DE 246 595 415 ... DE 811 363 057 ... DE 811125440 ... DE 811305931 ... DE 813 11 38 75 ... DE 813 184868 ... DE - 113866163 ... DE - 231969187 ... DE - 265265318 ... DE - 267297673 ... DE119263782 ... DE129390950 ... DE136308783 ... DE812847601 ... ... DK 10 50 32 80 ... DK 11 97 56 58 ... DK 12 14 48 22 ... DK 13 20 24 35 ... DK 13 31 04 59 ... DK 16 89 50 16 ... DK 25 18 63 11 ... DK 25 76 63 69 ... DK 25 86 35 26 ... DK 2566 2202 ... DK 26 09 77 89 ... DK 26 57 61 64 ... DK 28 01 76 34 ... DK 28107773 ... DK 29523215 ... DK 30 06 09 46 ... DK 32 27 15 02 ... DK 32329853 ... DK 65 07 04 13 ... DK 90 30 16 59 ... DK-20 04 52 72 ... DK-20 64 64 46 ... DK-27630308 ... DK-27926592 ... DK-28840926 ... DK-31882095 ... DK-33053266 ... DK10150817 ... DK10290813 ... DK26210895 ... DK36149213 ... DK: 21599336 ... ... EE 100 931 558 ... EE 100523487 ... EE 100572933 ... EE 100578209 ... EE 100594102 ... EE 100594403 ... EE 100832107 ... EE 100834066 ... EE 101031389 ... EE 101286639 ... EE 101288941 ... EE101256753 ... ... ES - Q0818001J ... ES 54362315K ... ES A-28184661 ... ES A-60631835 ... ES A-60997582 ... ES A08370314 ... ES A17028366 ... ES B-58378431 ... ES B64240914 ... ES B64717838 ... ES B79110482 ... ES B80975063 ... ES F13005293 ... ES J99216582 ... ES Q-2818015-F ... ES R9600075G ... ES U99216426 ... ES U99216632 ... ES V99218067 ... ES W4003922D ... ES X-5253868-R ... ES X5277343Q ... ES Y5277343F ... ES Z5277343K ... ES- A84409408 ... ES-A08074908 ... ES-B 60432291 ... ES-B18889204 ... ES-B55015432 ... ES-B64995111 ... ES-B96902531 ... ES-x-2482300w ... ESA78109592 ... Es-a58951310 ... ... EL 039868210 ... EL 044824428 ... EL 072130053 ... EL 082499478 ... EL 094012834 ... EL 094064321 ... EL 094068633 ... EL 094237076 ... EL 094263543 ... EL 095217179 ... EL 095304080 ... EL 099548630 ... EL 94051189 ... EL 998386804 ... EL 998408192 ... EL 998722134 ... EL 999038150 ... EL 999107669 ... EL 999533911 ... EL 999698730 ... EL 999715835 ... EL-082857563 ... EL094501040 ... EL098099809 ... EL: 094279805 ... El 800 179 925 ... ... FI 02459042 ... FI 0982651-1 ... FI 10320534 ... FI 18949388 ... FI 20194885 ... FI 20774740 ... FI 2094606-3 ... FI 24416318 ... FI- 01968312 ... FI- 22291259 ... FI-214 95 540 ... FI-22291240 ... FI-24163066 ... FI18261444 ... ... FR 04409414364 ... FR 09434086930 ... FR 114 248 728 36 ... FR 13 393 892 815 ... FR 163 041 877 01 ... FR 18 349 685 099 ... FR 19 552 008 443 ... FR 19552143273 ... FR 20 329 450 738 ... FR 21 448 834 911 ... FR 2143 2146 546 ... FR 22 326 565 603 ... FR 22 379 160 070 ... FR 26 495 205 213 ... FR 28337893168 ... FR 355 92065536 ... FR 36 380 610 451 ... FR 36502095094 ... FR 38 353427495 ... FR 41-343848552 ... FR 53418304010 ... FR 60391548955 ... FR 61 954 506 077 ... FR 63 334 214 293 ... FR 65 444 243 075 ... FR 68 378 838 692 ... FR 70492082151 ... FR 72 483 995 197 ... FR 734 836 491 66 ... FR 736 220 50 318 ... FR 74 397 888 330 ... FR 77 055 501 902 ... FR 77 384 627 170 ... FR 78528824428 ... FR 79 410 964 837 ... FR 83 404 833 048 ... FR 84 323 140 392 ... FR 86 394 303 796 ... FR 86 542 103 569 ... FR 88775649726 ... FR 94016950842 ... FR K 7399859412 ... FR01712030113 ... FR64333266765 ... FR82542065479 ... FR83404833048 ... FR86451397608 ... FR95483929956 ... Fr 40 303 265 045 ... Fr 96 631 620 572 ... fr 71383076817 ... ... GB 002 4257 28 ... GB 003232345 ... GB 100 1950 75 ... GB 100190874 ... GB 102675046 ... GB 232177091 ... GB 242338087388 ... GB 311 405 025 ... GB 362 5866 29 ... GB 417 2280 71 ... GB 436 0630 72 ... GB 495 2781 05 ... GB 507 5768 25 ... GB 521 6763 52 ... GB 586 367 295 ... GB 591 9373 01 ... GB 605 8678 15 ... GB 662 8564 06 ... GB 698 550 577 ... GB 733 4428 41 ... GB 770 381 235 ... GB 784 9117 89 ... GB 808 6365 12 ... GB 812 8333 44 ... GB 818243334 ... GB 823 531 352 ... GB 829 9594 59 ... GB 845788960 ... GB 879 7056 62 ... GB 881 3758 91 ... GB 913 3041 68 ... GB 933210951 ... GB 975 8664 50 ... GB 977 4872 51 ... GB 980780684 ... GB 997 7094 44 ... GB260311213 ... GB653599494 ... GB974053902 ... ... HU -12509403 ... HU 10672101 ... HU 10766172 ... HU 11444923 ... HU 12723650 ... HU 12840937 ... HU 13851909 ... HU 18206373 ... HU 23157653 ... HU 64241281 ... HU-10402434 ... HU-12892312 ... HU-14528114 ... HU11377304 ... HU12078503 ... HU13852467 ... ... IE 0005306C ... IE 4550159S ... IE 4693875V ... IE 4731823J ... IE 632 3420 C ... IE 6324720T ... IE 6339273F ... IE 635 430 5C ... IE 6388047V ... IE 6397893P ... IE 6433435F ... IE 6436390B ... IE 6791517I ... IE 8223200u ... IE 9502346O ... IE 9574173P ... IE 9679477V ... IE 9719156S ... IE 9741812E ... IE 9742129V ... IE-9696131F ... IE6599001W ... IE8D79739I ... IE9Y71814N ... ... IT - 01404480202 ... IT 0 0 6 1 8 2 8 0 4 9 9 ... IT 00 595 000 217 ... IT 00118439991 ... IT 00193180932 ... IT 00520800319 ... IT 00571320076 ... IT 00687120980 ... IT 01189820689 ... IT 01413270396 ... IT 01465210449 ... IT 01501180333 ... IT 01606120226 ... IT 01687870137 ... IT 01720020344 ... IT 01822890388 ... IT 02100550264 ... IT 02109480976 ... IT 02153481201 ... IT 02359210354 ... IT 02408660211 ... IT 02829410980 ... IT 03274440241 ... IT 03367280363 ... IT 04894530635 ... IT 05366960010 ... IT 05460820961 ... IT 05617370969 ... IT 06075960010 ... IT 06729900966 ... IT 06863340961 ... IT 09596821000 ... IT 12920760159 ... IT-01626160210 ... IT-03700020104 ... IT-03827740402 ... IT-09159800011 ... IT00743110157 ... IT02087050155 ... IT: 02331250163 ... ... LT 100001354118 ... LT 100001509912 ... LT 100001799517 ... LT 100001890913 ... LT 100001906711 ... LT 100001919017 ... LT 100002645517 ... LT 100002922012 ... LT 100003619917 ... LT 100005066013 ... LT 100005929611 ... LT 119511515 ... LT 235449811 ... LT 250266219 ... LT 258596610 ... LT 354991917 ... LT 616414610 ... LT 757118413 ... LT-100000979812 ... LT100001251914 ... LT100002894215 ... LT100004801610 ... LT290068995116 ... ... LU 10059929 ... LU 10590281 ... LU 109 676 28 ... LU 11082217 ... LU 13178262 ... LU 150 274 42 ... LU 1871 0830 ... LU 19184853 ... LU 19406747 ... LU 19979983 ... LU 20981643 ... LU 21989666 ... LU 22 22 12 68 ... LU 22690342 ... LU 22991225 ... LU.248.70.640 ... LU: 20993674 ... LU: 2294 4200 ... Lu 19980500 ... ... LV 4000 3521 600 ... LV 40003189718 ... LV 40003282138 ... LV 40003449366 ... LV 40003655379 ... LV 40003718068 ... LV 40003754957 ... LV 40003777428 ... LV 40003939038 ... LV 40008000102 ... LV 40103077610 ... LV 40103157009 ... LV 40103179665 ... LV 40103264016 ... LV 43603009384 ... LV 44103040262 ... LV 5000 399 3021 ... LV 50003087101 ... LV 90000528023 ... LV-40003241337 ... LV-40003467376 ... LV-42103016370 ... LV-42103048183 ... ... MT 1039-6417 ... MT 1167-9112 ... MT 1465 8213 ... MT 1613-4207 ... MT 17025737 ... MT 18740407 ... MT 1894 0705 ... MT 1966 1023 ... MT 19784818 ... MT 2029 1423 ... MT 20630321 ... ... NL 001241 643 B01 ... NL 009122746 B01 ... NL 806753742B01 ... NL 820605876B01 ... NL 8225.69.759 b01 ... NL-812421267 B01 ... NL-8197.38.116.B.01 ... NL.0094.10.806.B.01 ... NL.8143.26.584.B.01 ... NL.8186.43.778.B.01 ... NL001309675B01 ... NL001545668B01 ... NL003376734B77 ... NL00449544B01 ... NL006375054B01 ... NL006866049B01 ... NL007394913B01 ... NL009093503B01 ... NL019077312B01 ... NL066593931B01 ... NL068357370B01 ... NL117621729B01 ... NL167647672B01 ... NL4495445B01 ... NL68357370B01 ... NL802003217B01 ... NL808373894B01 ... NL811705262B01 ... NL813411786B01 ... ... PL 5211754253 ... PL 5262987091 ... PL 584-030-44-72 ... PL 5840154038 ... PL 5840304472 ... PL 5860224115 ... PL 6330005110 ... PL 6661913137 ... PL 687-16-26-585 ... PL 777 26 68 285 ... PL 7780104605 ... PL 7881154591 ... PL 9562197426 ... PL-7532365958 ... PL-951-157-77-68 ... PL5261025421 ... PL6772135826 ... ... PT 500 019 720 ... PT 500135.495 ... PT 501 507 930 ... PT 501 519 246 ... PT 501 964 843 ... PT 502448911 ... PT 502971142 ... PT 504141066 ... PT 506 030 636 ... PT 506835669 ... PT 507 223 730 ... PT 507 757 505 ... PT 507 859 146 ... PT 507297687 ... PT 508 081 327 ... PT 509 250 505 ... PT 509284930 ... PT-505 856 468 ... PT503038083 ... ... RO 11358544 ... RO 13837330 ... RO 14840784 ... RO 1630615123457 ... RO 16621241 ... RO 17832344 ... RO 1822964 ... RO 18341035 ... RO 185 472 90 ... RO 18779508 ... RO 20950021 ... RO 21356044 ... RO 21996566 ... RO 241 30 20 ... RO 24736200 ... RO 3087444 ... RO 4003786 ... RO 4019740 ... RO 4257679 ... RO 573768 ... RO 6010151 ... RO 6322498 ... RO 6655328 ... RO-23867797 ... RO-27849238 ... RO16241790 ... Ro 15071875 ... ... SE 202 100-5000 01 ... SE 390 806 051 401 ... SE 55 62 00-0777 01 ... SE 55 67 59 32 48 01 ... SE 556.383.740.901 ... SE 556058115801 ... SE 556126249301 ... SE 556433592401 ... SE 556700 3552 01 ... SE 556708202801 ... SE 556728341001 ... SE 556848115301 ... SE 720 522 241 201 ... SE-502053602401 ... SE-556 644 662 001 ... SE-556 792 355 101 ... SE-5562245190-01 ... SE-556271210801 ... SE-556666-4438-01 ... SE556043606401 ... Se 556250398601 ... ... SI 26808498 ... SI 29664373 ... SI 3609 7152 ... SI 48673820 ... SI 50223054 ... SI 56633360 ... SI 56951442 ... SI 68297530 ... SI 70310815 ... SI 73567906 ... SI 85390518 ... SI 92351069 ... SI-83815201 ... SI-89036999 ... ... SK 1078449064 ... SK 202 274 96 19 ... SK 2020 237 945 ... SK 2020257679 ... SK 2021 6858 20 ... SK 2021853504 ... SK 2021998528 ... SK 2022193459 ... SK2022193459 ... ... ''' >>> [x for x in numbers.splitlines() if x and not vat.is_valid(x)] [] The following numbers are wrong in one way or another. First we need a function to be able to determine the kind of error. >>> def caught(number, exception): ... try: ... vat.validate(number) ... return False ... except exception: ... return True ... These numbers should be mostly valid except that they have been mangled so their check digit is wrong. >>> numbers = ''' ... ... ATU 143 43 102 ... ATU 15169209 ... ATU46080904 ... ATU61191628 ... ... BE 0406.139.583 ... BE 0793 013 186 ... BE 456.973.432 ... BE697449982 ... ... BG 1037735942 ... BG 131 172 009 ... BG 147147471 ... BG 200940556 ... ... CY 10246672F ... CY-10009489 A ... CY-10257074Y ... CY00632893 F ... ... CZ 25557481 ... CZ 48207726 ... CZ 640913926 ... CZ 8058018314 ... ... DE 125014855 ... DE 246 495 415 ... DE 813 91 38 75 ... DE - 266297673 ... ... DK 11 96 56 58 ... DK 2565 2202 ... DK-27996592 ... DK10159817 ... ... EE 100 941 558 ... EE 100525487 ... EE 101586639 ... EE101256754 ... ... ES 54362415K ... ES K-2814015-F ... ES-x-2322300w ... Es-a48951310 ... ... EL 094013834 ... EL 094068733 ... EL094501140 ... EL: 094269805 ... ... FR 04409414264 ... FR 21 326 565 603 ... FR K 7399859312 ... FR L 7399859412 ... ... IE 4731823H ... IE 632 3421 C ... IE 5339273F ... IE8D79729I ... ... LV 40003189715 ... LV 90000528022 ... LV-10103241337 ... LV-42103048181 ... ... SK 1078449164 ... SK 302 274 96 19 ... SK 2030 237 945 ... SK 2020457679 ... ... ''' >>> [x for x in numbers.splitlines() if x and not caught(x, InvalidChecksum)] [] These numbers should be mostly valid except that they have some formatting flaws. >>> numbers = ''' ... ... AT1 142 43 102 ... ATU 1515B209 ... ... BE 02A2.239.951 ... BE 0220,764.971 ... ... BG 10X8735941 ... ... CY-102590Z3P ... ... DE 246X595 415 ... DE 011125440 ... ... IE 4550C59S ... IE 069385V8 ... ... NL 001241643801 ... NL 009122746B00 ... NL B06753742B01 ... NL 82X569759b01 ... ... SK A078449064 ... SK 012 274 96 19 ... SK 2010 237 945 ... ... ''' >>> [x for x in numbers.splitlines() if x and not caught(x, InvalidFormat)] [] These numbers should be mostly valid except that they have some component that contains an invalid or unknown value. >>> numbers = ''' ... ... CY-12259033P ... ... CZ 95123891 ... ... IT 00687129980 ... ... LT 100001354 ... LT 100001509922 ... ... QQ 124567 ... ... ''' >>> [x for x in numbers.splitlines() if x and not caught(x, InvalidComponent)] [] >>> vat.compact('QQ 124567') Traceback (most recent call last): ... InvalidComponent: ... These numbers should be mostly valid except that they have the wrong length. >>> numbers = ''' ... ... ATU 151592092 ... ... CY-1225903322 ... ... ES B-583784312 ... ... NL006866304B021 ... ... SE 55643359201 ... SE 5567003255201 ... ... ''' >>> [x for x in numbers.splitlines() if x and not caught(x, InvalidLength)] [] python-stdnum-0.9/tests/test_fi_hetu.doctest0000644000000000000000000000435712154625043021377 0ustar rootroot00000000000000test_fi_hetu.doctest - more detailed doctests for stdnum.fi.hetu module Copyright (C) 2011 Jussi Judin Copyright (C) 2013 Arthur de Jong This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA This file contains more detailed doctests for the stdnum.fi.hetu. It tries to cover more corner cases and detailed functionality that is not really useful as module documentation. >>> from stdnum.fi import hetu >>> from stdnum.exceptions import * Normal values that should just work. >>> hetu.validate('131052-308T') '131052-308T' >>> hetu.validate('131052+308T') '131052+308T' >>> hetu.validate('131052A308T') '131052A308T' >>> hetu.validate('131052a308t') '131052A308T' Invalid checksum: >>> hetu.validate('131052-308U') Traceback (most recent call last): ... InvalidChecksum: ... Invalid century indicator: >>> hetu.validate('131052/308T') Traceback (most recent call last): ... InvalidFormat: ... >>> hetu.validate('131052T308T') Traceback (most recent call last): ... InvalidFormat: ... Invalid birth date: >>> hetu.validate('310252-308Y') Traceback (most recent call last): ... InvalidComponent: ... >>> hetu.validate('130052-308R') Traceback (most recent call last): ... InvalidComponent: ... Leaving out the first zero is wrong: >>> hetu.validate('10101-0101') Traceback (most recent call last): ... InvalidFormat: ... Invalid individual number: (for historical reasons individual IDs start from 002) >>> hetu.validate('131052-000V') Traceback (most recent call last): ... InvalidComponent: ... compact() and format() don't do much special: >>> hetu.compact('131052a308t') '131052A308T' python-stdnum-0.9/tests/test_iso7064.doctest0000644000000000000000000000377612154625043021073 0ustar rootroot00000000000000test_doctest - more detailed doctests for the stdnum.iso7064 package Copyright (C) 2010, 2011, 2013 Arthur de Jong This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA This file contains more detailed doctests for the stdnum.iso7064 package. It tries to test more corner cases and detailed functionality that is not really useful as module documentation. >>> from stdnum.iso7064 import mod_11_10, mod_11_2, mod_37_2, mod_37_36, mod_97_10 These are normal variations of Mod 11, 10 that should just work. >>> mod_11_10.validate('12323') '12323' >>> mod_11_10.validate('546794') '546794' >>> mod_11_10.calc_check_digit('0794') '5' >>> mod_11_10.validate('07945') '07945' >>> mod_11_10.calc_check_digit('00200667308') '5' >>> mod_11_10.validate('002006673085') '002006673085' >>> mod_11_10.validate('002006673084') Traceback (most recent call last): ... InvalidChecksum: ... >>> mod_11_10.calc_check_digit('00200667309') '3' >>> mod_11_10.calc_check_digit('00200667310') '8' >>> mod_11_10.calc_check_digit('00200667311') '6' >>> mod_11_10.calc_check_digit('00200667312') '4' These normal tests of Mod 11, 2 should just work. >>> mod_11_2.calc_check_digit('0794') '0' >>> mod_11_2.validate('07940') '07940' >>> mod_11_2.calc_check_digit('079') 'X' >>> mod_11_2.validate('079X') '079X' These normal tests of Mod 37, 2 should just work >>> mod_37_2.calc_check_digit('G123498654321') 'H' python-stdnum-0.9/tests/test_isbn.doctest0000644000000000000000000000554012237246032020701 0ustar rootroot00000000000000test_isbn.doctest - more detailed doctests for stdnum.isbn module Copyright (C) 2010, 2011, 2013 Arthur de Jong This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA This file contains more detailed doctests for the stdnum.isbn module. It tries to test more corner cases and detailed functionality that is not really useful as module documentation. >>> from stdnum import isbn Tests for mangling and incorect check digits. >>> isbn.validate('08515x-629-2') # added X in the middle Traceback (most recent call last): ... InvalidFormat: ... >>> isbn.validate('85152-629-1') # incorrect check digit Traceback (most recent call last): ... InvalidChecksum: ... >>> isbn.validate('978-902453827X') # ISBN13 with X check digit Traceback (most recent call last): ... InvalidFormat: ... >>> isbn.validate('978-902453827') # invalid length Traceback (most recent call last): ... InvalidLength: ... See if ISBN10 to 13 conversion works. >>> isbn.to_isbn13('978-9024538270') # ISBN13 should stay ISBN13 '978-9024538270' >>> isbn.to_isbn13('1 85798218 5') '978 1 85798218 3' >>> isbn.to_isbn13('1857982185') '9781857982183' >>> isbn.to_isbn13('1-85798-218-5') '978-1-85798-218-3' >>> isbn.validate(isbn.to_isbn13('1 85798218 5')) '9781857982183' >>> isbn.compact('1 85798218 5', convert=True) '9781857982183' >>> isbn.validate('1 85798218 5', convert=True) '9781857982183' See if ISBN13 to 10 conversion works. >>> isbn.to_isbn10('1-85798-218-5') # ISBN10 should stay ISBN10 '1-85798-218-5' >>> isbn.to_isbn10('978 1 85798218 3') '1 85798218 5' >>> isbn.to_isbn10('9781857982183') '1857982185' >>> isbn.to_isbn10('978-1-85798-218-3') '1-85798-218-5' >>> isbn.to_isbn10('979-20-1234567-8') # incorrect check digit Traceback (most recent call last): ... InvalidFormat: ... >>> isbn.to_isbn10('9791843123391') Traceback (most recent call last): ... InvalidFormat: ... Regrouping tests. >>> isbn.split('9024538270') # normal ISBN10 ('', '90', '245', '3827', '0') >>> isbn.split('9999678270') # ISBN10, unknown publisher in group ('', '99996', '', '7827', '0') >>> isbn.split('979-20-1234567-8') ('979', '', '', '201234567', '8') >>> isbn.split('5413170121522') # valid checkdigit, unknown prefix ('', '', '', '541317012152', '2') python-stdnum-0.9/tests/test_imei.doctest0000644000000000000000000000425712154625043020676 0ustar rootroot00000000000000test_imei.doctest - more detailed doctests for stdnum.imei module Copyright (C) 2010, 2013 Arthur de Jong This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA This file contains more detailed doctests for the stdnum.imei module. It tries to test more corner cases and detailed functionality that is not really useful as module documentation. >>> from stdnum import imei Should be valid numbers: >>> imei.validate('49-015420-323751') '49015420323751' >>> imei.validate('35-209900-176148-1') '352099001761481' >>> imei.validate('35-209900-176148-23') '3520990017614823' >>> imei.validate('350077-52-323751-3') '350077523237513' >>> imei.validate('354178036859789') '354178036859789' These are normal variations that should just work. Getting the type: >>> imei.imei_type('35686800-004141-20') 'IMEISV' >>> imei.imei_type('35-417803-685978-9') 'IMEI' >>> imei.imei_type('35-417803-685978-2') is None # invalid check digit True >>> imei.imei_type('3568680000414120') 'IMEISV' The format() function can add the check digit if needed. It should leave alone existing check digits (even invalid ones) and only add them to the 14 digit format. >>> imei.format('354178036859789') '35-417803-685978-9' >>> imei.format('35417803685978') '35-417803-685978' >>> imei.format('354178036859786', add_check_digit=True) '35-417803-685978-6' >>> imei.format('35417803685978', add_check_digit=True) '35-417803-685978-9' >>> imei.format('35686800-004141', add_check_digit=True) '35-686800-004141-8' >>> imei.format('35686800-004141-20', add_check_digit=True) '35-686800-004141-20' python-stdnum-0.9/tests/test_meid.doctest0000644000000000000000000001252312154625043020664 0ustar rootroot00000000000000test_meid.doctest - more detailed doctests for stdnum.meid module Copyright (C) 2010, 2011, 2013 Arthur de Jong This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA This file contains more detailed doctests for the stdnum.meid module. It tries to test more corner cases and detailed functionality that is not really useful as module documentation. >>> from stdnum import meid IMEI numbers without the software version (but optionally with a check digit) should be valid numbers: >>> meid.validate('49-015420-323751') '49015420323751' >>> meid.validate('35-209900-176148-1') '35209900176148' >>> meid.validate('35-209900-176148-2') Traceback (most recent call last): ... InvalidChecksum: ... MEIDs can be represented as HEX strings (with and without check digit): >>> meid.validate('AF 01 23 45 0A BC DE') 'AF0123450ABCDE' >>> meid.validate('AF 01 23 45 0A BC DE C') 'AF0123450ABCDE' >>> meid.validate('AF 01 23 45 0A BC DE D') Traceback (most recent call last): ... InvalidChecksum: ... Also, MEIDs can be represented in decimal format (with and without check digit): >>> meid.validate('29360 87365 0070 3710') 'AF0123450ABCDE' >>> meid.validate('29360 87365 0070 3710 0') 'AF0123450ABCDE' >>> meid.validate('29360 87365 0070 3710 1') Traceback (most recent call last): ... InvalidChecksum: ... The validate() method should be fairly robust against invalid junk passed: >>> meid.validate('29360 ABCDE 0070 3710') Traceback (most recent call last): ... InvalidFormat: ... >>> meid.validate('GF 01 23 45 0A BC DE') Traceback (most recent call last): ... InvalidFormat: ... The compact method should convert to HEX if needed and can optionally leave the check digit intact. >>> meid.compact('49-015420-323751') '49015420323751' >>> meid.compact('35-209900-176148-2') '35209900176148' >>> meid.compact('35-209900-176148-2', strip_check_digit=False) '352099001761482' >>> meid.compact('af 01 23 45 0a bc de') 'AF0123450ABCDE' >>> meid.compact('AF 01 23 45 0A BC DE C') 'AF0123450ABCDE' >>> meid.compact('AF 01 23 45 0A BC DE C', strip_check_digit=False) 'AF0123450ABCDEC' >>> meid.compact('29360 87365 0070 3710') 'AF0123450ABCDE' >>> meid.compact('29360 87365 0070 3710 0') 'AF0123450ABCDE' >>> meid.compact('29360 87365 0070 3710 0', strip_check_digit=False) 'AF0123450ABCDEC' The format() function can add the check digit if needed. It should leave alone existing check digits (even invalid ones). >>> meid.format('35-209900-176148-2') '35 20 99 00 17 61 48 2' >>> meid.format('35-209900-176148') '35 20 99 00 17 61 48' >>> meid.format('35-209900-176148', add_check_digit=True) '35 20 99 00 17 61 48 1' >>> meid.format('af0123450abcDE') 'AF 01 23 45 0A BC DE' >>> meid.format('af0123450abcDEC', add_check_digit=True) 'AF 01 23 45 0A BC DE C' The format() function can also convert to decimal, recalculating the check digit if needed (conversion will silently correct incorrect check digits): >>> meid.format('35-209900-176148', format='dec') '08913 28768 0153 2232' >>> meid.format('35-209900-176148', format='dec', add_check_digit=True) '08913 28768 0153 2232 3' >>> meid.format('35-209900-176148-9', format='dec') '08913 28768 0153 2232 3' >>> meid.format('af0123450abcDE', format='dec') '29360 87365 0070 3710' >>> meid.format('af0123450abcDE', format='dec', add_check_digit=True) '29360 87365 0070 3710 0' >>> meid.format('af0123450abcDEC', format='dec') '29360 87365 0070 3710 0' >>> meid.format('293608736500703710', format='dec') '29360 87365 0070 3710' >>> meid.format('293608736500703710', format='dec', add_check_digit=True) '29360 87365 0070 3710 0' >>> meid.format('2936087365007037106', format='dec') '29360 87365 0070 3710 6' The format() function can also convert to hex, recalculating the check digit if needed (conversion will silently correct incorrect check digits): >>> meid.format('35-209900-176148', format='hex') '35 20 99 00 17 61 48' >>> meid.format('35-209900-176148', format='hex', add_check_digit=True) '35 20 99 00 17 61 48 1' >>> meid.format('35-209900-176148-9', format='hex') '35 20 99 00 17 61 48 9' >>> meid.format('af0123450abcDE', format='hex') 'AF 01 23 45 0A BC DE' >>> meid.format('af0123450abcDE', format='hex', add_check_digit=True) 'AF 01 23 45 0A BC DE C' >>> meid.format('af0123450abcDEF', format='hex') 'AF 01 23 45 0A BC DE F' >>> meid.format('293608736500703710', format='hex') 'AF 01 23 45 0A BC DE' >>> meid.format('293608736500703710', format='hex', add_check_digit=True) 'AF 01 23 45 0A BC DE C' >>> meid.format('2936087365007037106', format='hex') 'AF 01 23 45 0A BC DE C' The conversion function should work regardless of the check digit and whether decimal or hex representation is used. >>> meid.to_pseudo_esn('AF 01 23 45 0A BC DE C') '8016B128' >>> meid.to_pseudo_esn('29360 87365 0070 3710') '8016B128' python-stdnum-0.9/tests/test_ismn.doctest0000644000000000000000000000446112154625043020716 0ustar rootroot00000000000000test_ismn.doctest - more detailed doctests for stdnum.ismn module Copyright (C) 2010, 2011, 2012, 2013 Arthur de Jong This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA This file contains more detailed doctests for the stdnum.ismn module. It tries to test more corner cases and detailed functionality that is not really useful as module documentation. >>> from stdnum import ismn These are normal variations that should just work. >>> ismn.validate('979-0-3217-6543-6') '9790321765436' >>> ismn.validate('979-0-3217-6544-3') '9790321765443' >>> ismn.validate('9790321765450') '9790321765450' >>> ismn.validate('M-3217-6546-7') 'M321765467' >>> ismn.validate('M321765474') 'M321765474' >>> ismn.validate('979-0-260000438') '9790260000438' Tests for mangling and incorect check digits. >>> ismn.validate('979-0-3217-6543-x') Traceback (most recent call last): ... InvalidFormat: ... >>> ismn.validate('M-3217-6546-8') Traceback (most recent call last): ... InvalidChecksum: ... >>> ismn.validate('979M321765450') Traceback (most recent call last): ... InvalidFormat: ... >>> ismn.validate('Z-3217-6546-8') Traceback (most recent call last): ... InvalidFormat: ... See if 10 to 13 digit conversion works. >>> ismn.to_ismn13('979-0-32176544-3') # ismn13 should stay ismn13 '979-0-32176544-3' >>> ismn.to_ismn13('M-32176546-7') '979-0-32176546-7' >>> ismn.to_ismn13('M 3217 65504') '979 0 3217 65504' Test the ismn_type() function >>> ismn.ismn_type('M-3217-6546-7') 'ISMN10' >>> ismn.ismn_type('BAD') >>> ismn.ismn_type('9790321765450') 'ISMN13' Regrouping tests. >>> ismn.format('M-3217-6546-7') '979-0-3217-6546-7' >>> ismn.format('9790321765450') '979-0-3217-6545-0' python-stdnum-0.9/tests/test_my_nric.doctest0000644000000000000000000000614112154632227021407 0ustar rootroot00000000000000test_my_nric.doctest - more detailed doctests for stdnum.my.nric module Copyright (C) 2013 Arthur de Jong This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA This file contains more detailed doctests for the stdnum.my.nric. It tries to cover more corner cases and detailed functionality that is not really useful as module documentation. >>> from stdnum.my import nric >>> from stdnum.exceptions import * Normal values that should just work. >>> nric.validate('770305-02-1234') '770305021234' >>> nric.validate('890131-06-1224') '890131061224' >>> nric.validate('810909785542') '810909785542' >>> nric.validate('880229875542') '880229875542' Get the birth date: >>> nric.get_birth_date('770305-02-1234') datetime.date(1977, 3, 5) >>> nric.get_birth_date('890131-06-1224') datetime.date(1989, 1, 31) >>> nric.get_birth_date('810909785542') datetime.date(1981, 9, 9) >>> nric.get_birth_date('880229875542') datetime.date(1988, 2, 29) Get the birth place: >>> str(nric.get_birth_place('770305-02-1234')['state']) 'Kedah' >>> str(nric.get_birth_place('890131-06-1224')['state']) 'Pahang' >>> str(nric.get_birth_place('810909785542')['country']) 'Sri Lanka' >>> str(nric.get_birth_place('880229875542')['countries']) 'Britain, Ireland' Formatting: >>> nric.format('770305-02-1234') '770305-02-1234' >>> nric.format('890131-06-1224') '890131-06-1224' >>> nric.format('810909785542') '810909-78-5542' >>> nric.format('880229875542') '880229-87-5542' Invalid date: >>> nric.validate('771305-02-1234') Traceback (most recent call last): ... InvalidComponent: ... >>> nric.validate('890132-06-1224') Traceback (most recent call last): ... InvalidComponent: ... >>> nric.validate('870229875542') Traceback (most recent call last): ... InvalidComponent: ... Invalid birth place: >>> nric.validate('770305-00-1234') Traceback (most recent call last): ... InvalidComponent: ... >>> nric.validate('890131-17-1224') Traceback (most recent call last): ... InvalidComponent: ... >>> nric.validate('810909805542') Traceback (most recent call last): ... InvalidComponent: ... >>> nric.validate('880229995542') Traceback (most recent call last): ... InvalidComponent: ... Just invalid numbers: >>> nric.validate('770305-00') Traceback (most recent call last): ... InvalidLength: ... >>> nric.validate('890A31-17-1224') Traceback (most recent call last): ... InvalidFormat: ... >>> nric.get_birth_place('8109098') Traceback (most recent call last): ... InvalidComponent: ... python-stdnum-0.9/tests/test_ean.doctest0000644000000000000000000000260012154625043020504 0ustar rootroot00000000000000test_ean.doctest - more detailed doctests for the stdnum.ean module Copyright (C) 2013 Arthur de Jong This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA This file contains more detailed doctests for the stdnum.ean module. It tries to test more corner cases and detailed functionality that is not really useful as module documentation. >>> from stdnum import ean These numbers have broken checksums or are mangled: >>> ean.validate('7501031311309') '7501031311309' >>> ean.validate('75010313113') Traceback (most recent call last): ... InvalidLength: ... >>> ean.validate('750103AAAA309') Traceback (most recent call last): ... InvalidFormat: ... >>> ean.validate('7501031311308') Traceback (most recent call last): ... InvalidChecksum: ... python-stdnum-0.9/tests/test_gb_vat.doctest0000644000000000000000000000620612260400322021176 0ustar rootroot00000000000000test_gb_vat.doctest - more detailed doctests for stdnum.gb.vat module Copyright (C) 2012, 2013 Arthur de Jong This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA This file contains more detailed doctests for the stdnum.gb.vat. It tries to cover more corner cases and detailed functionality that is not really useful as module documentation. >>> from stdnum.gb import vat Normal values that should just work. >>> vat.validate('980780684') # standard number '980780684' >>> vat.validate('100190874') # standard number restarting '100190874' >>> vat.validate('242338087388') # branch trader '242338087388' >>> vat.validate('GD100') # government department 'GD100' >>> vat.validate('HA501') # health authority 'HA501' >>> vat.validate('GD888810003') # government department for EU 'GD888810003' >>> vat.validate('HA888856782') # health authority for EU 'HA888856782' Invalid long numbers: >>> vat.validate('802311781') # invalid check digit Traceback (most recent call last): ... InvalidChecksum: ... >>> vat.validate('9807806842') # too long for standard number Traceback (most recent call last): ... InvalidLength: ... >>> vat.validate('9807806B4') # invalid digit Traceback (most recent call last): ... InvalidFormat: ... >>> vat.validate('GD8888567B2') # invalid digit for EU health authority Traceback (most recent call last): ... InvalidFormat: ... >>> vat.validate('001234567') # invalid checksum Traceback (most recent call last): ... InvalidChecksum: ... Some variations on the short format: >>> vat.validate('ZZ100') # unknown code Traceback (most recent call last): ... InvalidComponent: ... >>> vat.validate('GD600') # government department with high number Traceback (most recent call last): ... InvalidComponent: ... >>> vat.validate('HA201') # health authority with low number Traceback (most recent call last): ... InvalidComponent: ... Some variations on the EU format: >>> vat.validate('GD888860018') # government department with high number Traceback (most recent call last): ... InvalidComponent: ... >>> vat.validate('HA888820107') # health authority with low number Traceback (most recent call last): ... InvalidComponent: ... >>> vat.validate('HA888856700') # health authority with invalid checksum Traceback (most recent call last): ... InvalidChecksum: ... Formatting tests: >>> vat.format('980780684') # standard number '980 7806 84' >>> vat.format('HA501') # health authority 'HA501' >>> vat.format('242338087388') # branch trader '242 3380 87 388' python-stdnum-0.9/getmybp.py0000755000000000000000000000566712154632227016217 0ustar rootroot00000000000000#!/usr/bin/env python # getmybp.py - script to donwnload data from Malaysian government site # # Copyright (C) 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA from collections import defaultdict import re import urllib import BeautifulSoup # URLs that are downloaded state_list_url = 'http://www.jpn.gov.my/en/informasi/states-code' country_list_url = 'http://www.jpn.gov.my/en/informasi/country-code' spaces_re = re.compile('\s+', re.UNICODE) def clean(s): """Cleans up the string removing unneeded stuff from it.""" return spaces_re.sub(' ', s.replace(u'\u0096', '')).strip().encode('utf-8') def parse(f): """Parse the specified file.""" soup = BeautifulSoup.BeautifulSoup(f, convertEntities='html') # find all table rows for tr in soup.find('div', id='content').findAll('tr'): # find the rows with four columns of text tds = [ clean(''.join(x.string for x in td.findAll(text=True))) for td in tr.findAll('td') ] if len(tds) >= 2 and tds[0] and tds[1]: yield tds[0], tds[1] if len(tds) >= 4 and tds[2] and tds[3]: yield tds[2], tds[3] if __name__ == '__main__': results = defaultdict(lambda : defaultdict(list)) # read the states #f = open('/tmp/states.html', 'r') f = urllib.urlopen(state_list_url) for state, bps in parse(f): for bp in bps.split(','): results[bp.strip()]['state'] = state results[bp.strip()]['countries'].append('Malaysia') # read the countries #f = open('/tmp/countries.html', 'r') f = urllib.urlopen(country_list_url) for country, bp in parse(f): results[bp]['countries'].append(country) # print the results print '# generated from National Registration Department of Malaysia, downloaded from' print '# %s' % state_list_url print '# %s' % country_list_url print for bp in sorted(results.iterkeys()): res = bp row = results[bp] if 'state' in row: res += ' state="%s"' % row['state'] countries = row['countries'] if len(countries) == 1: res += ' country="%s"' % countries[0] if len(countries) > 0: res += ' countries="%s"' % (', '.join(countries)) print res python-stdnum-0.9/NEWS0000644000000000000000000001450012260533041014644 0ustar rootroot00000000000000changes from 0.8.1 to 0.9 ------------------------- * add modules for the following number formats: - Brin number (Dutch number for schools) - Postcode (Dutch postal code) - ATIN (U.S. Adoption Taxpayer Identification Number) - EIN (U.S. Employer Identification Number) - ITIN (U.S. Individual Taxpayer Identification Number) - PTIN (U.S. Preparer Tax Identification Number) - TIN (U.S. Taxpayer Identification Number) * try to replace Unicode characters with similar-looking ASCII characters * update getimsi script (thanks eneq123) * update getiban script * add proxy support to the stdnum.eu.vat.check_vies() function (thanks Cédric Krier) * support newer United Kingdom VAT numbers changes from 0.8 to 0.8.1 ------------------------- * include some files that were missing from the source tarball changes from 0.7 to 0.8 ----------------------- * add modules for the following number formats: - NRIC No. (Malaysian National Registration Identity Card Number) * all modules now provide a validate() function that throws an exception that contains more information on the failure reason * documentation improvements * remove add_check_digit parameter from GRid's format() function * improvements to the tests * re-add Python3 support (now tested with Python 2.7, 3.2 and 3.3) changes from 0.6 to 0.7 ----------------------- * add modules for the following number formats: - Onderwijsnummer (Dutch school number) - BTW-nummer (Omzetbelastingnummer, the Dutch VAT number) - HETU (Finnish personal identity code) as provided by Jussi Judin (#5) - RČ (Rodné číslo, the Czech and Slovak birth numbers) - SIREN (a French company identification number) - FPA, ΦΠΑ (Foros Prostithemenis Aksias, the Greek VAT number) - Ust ID Nr. (Umsatzsteur Identifikationnummer, the German VAT number) - BTW, TVA, NWSt (Belgian VAT number) - DNI (Documento nacional de identidad, Spanish personal identity codes) - NIE (Número de Identificación de Extranjeros, Spanish foreigner number) - CIF (Certificado de Identificación Fiscal, Spanish company tax number) - NIF (Número de Identificación Fiscal, Spanish VAT number) - PVN (Pievienotās vērtības nodokļa, Latvian VAT number) - CVR (Momsregistreringsnummer, Danish VAT number) - TVA (taxe sur la valeur ajoutée, Luxembourgian VAT number) - CNP (Cod Numeric Personal, Romanian Numerical Personal Code) - CF (Cod de înregistrare în scopuri de TVA, Romanian VAT number) - Partita IVA (Italian VAT number) - Αριθμός Εγγραφής Φ.Π.Α. (Cypriot VAT number) - UID (Umsatzsteuer-Identifikationsnummer, Austrian VAT number) - NIF (Número de identificação fiscal, Portuguese VAT number) - IČ DPH (IČ pre daň z pridanej hodnoty, Slovak VAT number) - ALV nro (Arvonlisäveronumero, Finnish VAT number) - DIČ (Daňové identifikační číslo, Czech VAT number) - ANUM (Közösségi adószám, Hungarian VAT number) - VAT (Irish VAT number) - KMKR (Käibemaksukohuslase, Estonian VAT number) - PVM (Pridėtinės vertės mokestis mokėtojo kodas, Lithuanian VAT number) - n° TVA (taxe sur la valeur ajoutée, French VAT number) - VAT (Maltese VAT number) - NIP (Numer Identyfikacji Podatkowej, Polish VAT number) - ID za DDV (Davčna številka, Slovenian VAT number) - VAT (Moms, Mervärdesskatt, Swedish VAT number) - VAT (United Kingdom (and Isle of Man) VAT registration number) - EGN (ЕГН, Единен граждански номер, Bulgarian personal identity codes) - PNF (ЛНЧ, Личен номер на чужденец, Bulgarian number of a foreigner) - VAT (Идентификационен номер по ДДС, Bulgarian VAT number) - VAT (European Union VAT number) - OIB (Osobni identifikacijski broj, Croatian identification number) - PPS No (Personal Public Service Number, Irish personal number) - CPR (personnummer, the Danish citizen number) * additional tests for robustness and use introspection to test all modules * some code refactoring with the introduction of an internal utility module * improvements to the docstring documentation * generate API documentation using Sphinx changes from 0.5 to 0.6 ----------------------- * fix a problem with handling an ISBN13 with a valid check digit but with an unknown bookland prefix * add an IMSI (International Mobile Subscriber Identity) module * implement a conversion function from ISBN13 to ISBN10 * implement an ismn.ismn_type() function * implement an imei.split() function that splits the number into a TAC, serial number and checksum or software version * source code layout changes to better follow PEP8 changes from 0.4 to 0.5 ----------------------- * add modules for the following number formats: - EAN (International Article Number) * refactoring to use the EAN check digit code for ISBN and ISMN checks * implement a conversion function from ISSN to EAN * support Python3 with the same codebase * Python 2.5 compatibility improvement changes from 0.3 to 0.4 ----------------------- * add modules for the following number formats: - CPF (Cadastro de Pessoas Físicas, the Brazillian national identification number) - IBAN (International Bank Account Number) - ISIL (International Standard Identifier for Libraries and Related Organizations) - SSN (U.S. Social Security Number) * implement an internal module to store and handle hierarchically organised data structures efficiently * regional-specific numbers are now in ISO 3166 packages (the BSN module is now in stdnum.nl.bsn) * ISBN module functions now have a convert flag to convert to ISBN-13 on the fly changes from 0.2 to 0.3 ----------------------- * add modules for the following number formats: - ISMN (International Standard Music Number) - ISAN (International Standard Audiovisual Number) - IMEI (International Mobile Equipment Identity) - MEID (Mobile Equipment Identifier) - GRid (Global Release Identifier) * add modules for handling the following check digit algorithms: - the Verhoeff algorithm - the Luhn and Luhn mod N algorithms - some algorithms described in ISO/IEC 7064: Mod 11, 2, Mod 37, 2, Mod 97, 10, Mod 11, 10 and Mod 37, 36 * added more unit tests changes from 0.1 to 0.2 ----------------------- * rename validate() function to is_valid() for all modules * handle wrong types passed to is_valid() more gracefully * add more tests and fix some minor bugs python-stdnum-0.9/ChangeLog0000644000000000000000000014472512260533753015746 0ustar rootroot000000000000002013-12-31 Arthur de Jong * [5c1765e] stdnum/iban.dat, stdnum/isbn.dat: Update database files 2013-12-31 Arthur de Jong * [4217c35] stdnum/isan.py, stdnum/meid.py, stdnum/util.py: Add pragma: no cover for Python 3 Some statements are not covered in Python 3 tests. 2013-12-31 Arthur de Jong * [6c49ca8] getiban.py: Update getiban script This switches to use the csv module to support multi-line column values. This also handles some problems in the BBAN structure column that would contain an IBAN structure. 2013-12-31 Arthur de Jong * [0ee74e5] ChangeLog: Generate Changelog with different formatter git log --date=short --name-only \ --format="%x0c%ad %aN <%aE>%n%n%x09* [%h]%x00%s%n%x00%+b%x00" | \ awk 'BEGIN { RS="\f"; FS="\0" } { if ($1) { gsub(/\n*$/, "", $4); gsub(/^\n*/, "", $4); gsub(/\n/, ", ", $4); gsub(/\ngit-svn-id.*/, "", $3); gsub(/\n/, "\n\t ", $3); print $1 " " $4 ": "; print "\t " $2 $3 }}' | \ fmt --width=78 -c > ChangeLog 2013-12-30 Cédric Krier * [a148835] stdnum/gb/vat.py, tests/test_gb_vat.doctest: Add some new VAT numbers for GB Add support for restarting from November 2009 using 9755. Add support for EU format of health authorities See: https://github.com/arthurdejong/python-stdnum/pull/4 2013-12-12 eneq123 * [4609a22] getimsi.py, stdnum/imsi.dat: Update parsing in getimsi script This updates the regexes and includes seom optimizations. See: https://github.com/arthurdejong/python-stdnum/issues/1 2013-12-30 Cédric Krier * [9ec3cb0] stdnum/eu/vat.py: Add support for proxy 2013-12-04 Arthur de Jong * [7f30979] getimsi.py, stdnum/imsi.dat: Update getimsi script This updates the script due to the Wikipedia article change and removes the code for getting the data from ITU for now. See: https://github.com/arthurdejong/python-stdnum/issues/1 2013-11-09 Arthur de Jong * [b0c47d5] stdnum/nl/__init__.py, stdnum/nl/postcode.py: Add a Dutch postal code module The Dutch postal code (postcode) consists of four digits followed by two characters and together with the house number should uniquely identify any address. Addresses trac ticket #7. 2013-11-09 Arthur de Jong * [73d05b0] stdnum/nl/brin.py: Add a Dutch Brin number module The Brin (Basis Registratie Instellingen) is a number to identify schools and related institutions. Addresses trac ticket #6. 2013-11-09 Arthur de Jong * [73330a1] stdnum/nl/onderwijsnummer.py: Clarify onderwijsnummer description 2013-11-09 Arthur de Jong * [188d3ea] : Add various United States Tax number modules This adds modules for the Individual Taxpayer Identification Number (ITIN), the Employer Identification Number (EIN), Adoption Taxpayer Identification Number (ATIN) and Preparer Tax Identification Number (PTIN) that together with the Social Security Number (SSN) are valid Taxpayer Identification Numbers (TIN) 2013-10-12 Arthur de Jong * [9530635] stdnum/us/tin.py: Add a United States TIN module The Taxpayer Identification Number is used used for tax purposes in the United States. This module uses the SSN, ITIN, EIN, PTIN and ATIN modules to determine validitiy of the TIN. 2013-10-11 Arthur de Jong * [316e3f2] stdnum/us/ptin.py: Add a United States PTIN module A Preparer Tax Identification Number (PTIN) is United States identification number for tax return preparers. It is an eight-digit number prefixed with a capital P. 2013-10-11 Arthur de Jong * [47ea6ea] stdnum/us/atin.py: Add a United States ATIN module An Adoption Taxpayer Identification Number (ATIN) is a temporary nine-digit number issued by the United States IRS for a child for whom the adopting parents cannot obtain a Social Security Number. 2013-10-11 Arthur de Jong * [b1c9ba5] stdnum/us/ein.dat, stdnum/us/ein.py: Add a United States EIN module The Employer Identification Number (EIN), also known as Federal Employer Identification Number (FEIN), is used to identify a business entity in the United States. It is issued to anyone that has to pay withholding taxes on employees. 2013-10-11 Arthur de Jong * [19039f7] stdnum/us/itin.py: Add a United States ITIN module The ITIN (Individual Taxpayer Identification Number) is issued by the United States IRS to individuals who are required to have a taxpayer identification number but who are not eligible to obtain a Social Security Number. 2013-10-11 Arthur de Jong * [70b974b] stdnum/meid.py: Remove unused import 2013-11-08 Arthur de Jong * [f122c88] stdnum/util.py: Try to replace Unicode characters with ASCII This changes the stdnum.util.clean() method that is used by all modules to replace alternative Unicode dashes, dots, etc. by their ASCII equivalent so the numbers will be automatically converted and validated. Inspiration for this change came from https://github.com/JNRowe/pyisbn/pull/6 2013-06-14 Arthur de Jong * [c042f02] ChangeLog, NEWS, stdnum/__init__.py: Get files ready for 0.8.1 release 2013-06-14 Arthur de Jong * [31e5e81] MANIFEST.in, setup.py: Ensure that all used files are included in the sdist 2013-06-09 Arthur de Jong * [7fa9822] ChangeLog, NEWS, README, docs/index.rst, getnumlist.py, setup.py, stdnum/__init__.py: Get files ready for 0.8 release 2013-06-09 Arthur de Jong * [9597010] stdnum/iban.dat, stdnum/imsi.dat, stdnum/isbn.dat, stdnum/isil.dat: Update database files We manually tweak the Finland IBAN entry. We should probably change the parsing so that it uses the IBAN structure instead of the BBAN structure. 2013-06-09 Arthur de Jong * [19cbb3c] stdnum/my/nric.py: Fix NRIC module description 2013-06-08 Arthur de Jong * [46a7996] getmybp.py, stdnum/my/__init__.py, stdnum/my/bp.dat, stdnum/my/nric.py, tests/test_my_nric.doctest: Add a Malaysian NRIC No. module NRIC No. (National Registration Identity Card Number) is the unique identifier for issued to Malaysian citizens and permanent residents. 2013-06-08 Arthur de Jong * [999f2c3] : Provide a validate() function in all modules This provides an additional means of doing number validation that allows applications calling this library to get more information about why the validation failed and present more informative messages to the user. This introduces a collection of exceptions which will be raised by the validate() function in each module. All modules have been updated to provide this new function. 2013-05-22 Arthur de Jong * [cb69921] README, docs/index.rst, docs/stdnum.exceptions.rst: Document the validate() function and exceptions 2013-05-18 Arthur de Jong * [e00744c] stdnum/util.py: Use validate() in stdnum.util 2013-05-17 Arthur de Jong * [3d3a97d] stdnum/us/ssn.py: Implement validate() for U.S. Social Security Number 2013-05-17 Arthur de Jong * [4bfce3f] stdnum/eu/vat.py, tests/test_eu_vat.doctest: Implement validate() for European VAT numbers 2013-05-17 Arthur de Jong * [1aaf902] stdnum/sk/dph.py, stdnum/sk/rc.py: Implement validate() for Slovak numbers 2013-05-17 Arthur de Jong * [8982d1e] stdnum/si/ddv.py: Implement validate() for Slovenian VAT numbers 2013-05-17 Arthur de Jong * [522a599] stdnum/se/vat.py: Implement validate() for Swedish VAT numbers 2013-05-17 Arthur de Jong * [8e7d807] stdnum/pt/nif.py: Implement validate() for Portuguese VAT numbers 2013-05-17 Arthur de Jong * [7e865db] stdnum/pl/nip.py: Implement validate() for Polish numbers 2013-05-17 Arthur de Jong * [96c5080] stdnum/mt/vat.py: Implement validate() for Maltese numbers 2013-05-17 Arthur de Jong * [2ff4950] stdnum/lv/pvn.py: Implement validate() for Latvian numbers 2013-05-17 Arthur de Jong * [9845b0a] stdnum/lu/tva.py: Implement validate() for Luxembourgian numbers 2013-05-17 Arthur de Jong * [04cfb84] stdnum/lt/pvm.py: Implement validate() for Lithuanian numbers 2013-05-17 Arthur de Jong * [b1d5a72] stdnum/it/iva.py: Implement validate() for Italian numbers 2013-05-17 Arthur de Jong * [083993b] stdnum/ie/pps.py, stdnum/ie/vat.py: Implement validate() for Irish numbers 2013-05-17 Arthur de Jong * [301ba25] stdnum/hu/anum.py: Implement validate() for Hungarian numbers 2013-05-17 Arthur de Jong * [31f2684] stdnum/hr/oib.py: Implement validate() for Croatian numbers 2013-05-17 Arthur de Jong * [1932f69] stdnum/gr/vat.py: Implement validate() for Greek numbers 2013-05-17 Arthur de Jong * [10710dc] stdnum/gb/vat.py, tests/test_gb_vat.doctest: Implement validate() for United Kingdom numbers 2013-05-17 Arthur de Jong * [4753c09] stdnum/fi/alv.py, stdnum/fi/hetu.py, tests/test_fi_hetu.doctest: Implement validate() for Finnish numbers 2013-05-17 Arthur de Jong * [2259cbb] stdnum/es/cif.py, stdnum/es/dni.py, stdnum/es/nie.py, stdnum/es/nif.py: Implement validate() for Spanish numbers 2013-05-17 Arthur de Jong * [07c66e1] stdnum/ee/kmkr.py: Implement validate() for Estonian numbers 2013-05-17 Arthur de Jong * [8caecc5] stdnum/dk/cpr.py, stdnum/dk/cvr.py: Implement validate() for Danish numbers 2013-05-17 Arthur de Jong * [360480b] stdnum/de/vat.py: Implement validate() for German numbers 2013-05-17 Arthur de Jong * [fce6196] stdnum/cy/vat.py: Implement validate() for Cypriot numbers 2013-05-17 Arthur de Jong * [14e382f] stdnum/cz/dic.py, stdnum/cz/rc.py: Implement validate() for Czech numbers 2013-05-17 Arthur de Jong * [54ce2d7] stdnum/br/cpf.py: Implement validate() for Brazillian numbers 2013-05-17 Arthur de Jong * [6080907] stdnum/bg/egn.py, stdnum/bg/pnf.py, stdnum/bg/vat.py, tests/test_bg_vat.doctest: Implement validate() for Bulgarian numbers 2013-05-17 Arthur de Jong * [33ce4e9] stdnum/be/vat.py: Implement validate() for Belgian numbers 2013-05-17 Arthur de Jong * [66d6259] stdnum/at/uid.py: Implement validate() for Austrian numbers 2013-05-11 Arthur de Jong * [05547a4] stdnum/ro/cf.py, stdnum/ro/cnp.py: Implement validate() for Romanian numbers 2013-05-17 Arthur de Jong * [fc1432c] stdnum/fr/siren.py, stdnum/fr/tva.py: Implement validate() for French numbers 2013-05-05 Arthur de Jong * [62cafb4] stdnum/nl/bsn.py, stdnum/nl/btw.py, stdnum/nl/onderwijsnummer.py: Implement validate() for Dutch numbers 2013-05-04 Arthur de Jong * [cf88e23] stdnum/meid.py, tests/test_meid.doctest: Implement validate() for MEID 2013-05-04 Arthur de Jong * [c6f41f6] stdnum/issn.py: Implement validate() for ISSN 2013-05-04 Arthur de Jong * [21f07b3] stdnum/ismn.py, tests/test_ismn.doctest: Implement validate() for ISMN 2013-05-04 Arthur de Jong * [c07609f] stdnum/isil.py: Implement validate() for ISIL 2013-05-04 Arthur de Jong * [a18f1ac] stdnum/isan.py, tests/test_isan.doctest: Implement validate() for ISAN 2013-05-01 Arthur de Jong * [3ac8164] stdnum/iban.py: Implement validate() for IBAN 2013-05-03 Arthur de Jong * [12bd684] stdnum/grid.py: Implement validate() for GRid numbers 2013-05-04 Arthur de Jong * [9cee495] stdnum/imsi.py: Implement validate() for IMSI 2013-05-04 Arthur de Jong * [6e4bb71] stdnum/imei.py, tests/test_imei.doctest: Implement validate() for IMEI numbers 2013-05-04 Arthur de Jong * [efa2550] stdnum/iso7064/mod_11_10.py, stdnum/iso7064/mod_11_2.py, stdnum/iso7064/mod_37_2.py, stdnum/iso7064/mod_37_36.py, stdnum/iso7064/mod_97_10.py, tests/test_iso7064.doctest: Implement validate() for ISO 7064 algorithms 2013-05-03 Arthur de Jong * [5c9090b] stdnum/verhoeff.py, tests/test_verhoeff.doctest: Implement validate() for the Verhoeff checksum 2013-05-03 Arthur de Jong * [9ad5139] stdnum/luhn.py, tests/test_luhn.doctest: Implement validate() for the Luhn algorithms 2013-05-03 Arthur de Jong * [9580046] stdnum/isbn.py, tests/test_isbn.doctest: Implement validate() for ISBN 2013-05-03 Arthur de Jong * [fa1864f] stdnum/ean.py, tests/test_ean.doctest: Implement validate() for EAN 2013-06-07 Arthur de Jong * [8b9ef8f] stdnum/util.py: Raise a proper exception if cleaning fails 2013-06-07 Arthur de Jong * [1ac5437] setup.cfg, stdnum/exceptions.py: Provide a module with validation exceptions This introduces a new module for switching the validation scheme. Instead of using the is_valid() function that returns a boolean a validate() function either returns the sanitised number or raises an exception that should indicate the kind of validation failure. This should make it easier for applications calling this library to present more informative messages to the user. 2013-06-07 Arthur de Jong * [99586c9] stdnum/__init__.py, stdnum/de/vat.py, stdnum/nl/bsn.py, stdnum/util.py: Revert generating stdnum docstring dynamically Generating the docstring dynamically results in all stdnum modules being imported for every import from any stdnum module which is a performance hit. So we switch back to a manually generated list, using: from stdnum.util import get_module_list print '\n'.join(get_module_list()) This also shortens a few short descriptions to attempt to fit things on one line. 2013-06-07 Arthur de Jong * [a655e82] docs/conf.py, docs/index.rst: Documentation consistency improvements 2013-06-07 Arthur de Jong * [37a2afd] tests/test_iso7064.doctest: The robustness test were moved to the general tests 2013-06-07 Arthur de Jong * [90b7c4a] stdnum/numdb.py: Remove empty line 2013-06-07 Arthur de Jong * [bcb0a0b] stdnum/grid.py: GRid's format() function shouldn't have add_check_digit parameter 2013-04-26 Arthur de Jong * [2d956eb] stdnum/util.py: Use a cleaner way to get all stdnum modules This mechanism should work from Python 2.6 up to and including Python 3.3. 2013-04-26 Arthur de Jong * [30c832f] stdnum/numdb.py: Fix doctest to not be dependant on dict ordering 2013-04-26 Arthur de Jong * [51a55be] .gitignore: Add a .gitignore file 2012-09-22 Arthur de Jong * [3f6d52a] stdnum/__init__.py, stdnum/util.py: generate part of the stdnum docstring based on introspection of the modules 2012-06-16 Arthur de Jong * [af7e837] : set svn:ignore properly 2012-02-26 Arthur de Jong * [8f2e44c] stdnum/bg/egn.py, stdnum/cz/rc.py, stdnum/dk/cpr.py, stdnum/fi/hetu.py, stdnum/isan.py, stdnum/lv/pvn.py, stdnum/meid.py, stdnum/ro/cnp.py, tests/test_isan.doctest, tests/test_ismn.doctest, tests/test_robustness.doctest: re-add Python3 support 2012-02-26 Arthur de Jong * [3325052] ChangeLog, NEWS, stdnum/__init__.py: get files ready for 0.7 release 2012-02-26 Arthur de Jong * [a3ba206] stdnum/iban.dat, stdnum/imsi.dat, stdnum/isbn.dat, stdnum/isil.dat: update data files 2012-02-26 Arthur de Jong * [c240eff] getnumlist.py: also generate a list of modules for use in the Spinx documentation 2012-02-26 Arthur de Jong * [54b0f47] README, getnumlist.py, stdnum/__init__.py: use a script to generate the list of number formats in stdnum 2012-02-26 Arthur de Jong * [dada6a4] stdnum/eu/vat.py, stdnum/gb/vat.py, stdnum/gr/vat.py, stdnum/grid.py, stdnum/hr/oib.py, stdnum/hu/anum.py, stdnum/iban.py, stdnum/ie/pps.py, stdnum/ie/vat.py, stdnum/imei.py, stdnum/isan.py, stdnum/iso7064/__init__.py, stdnum/iso7064/mod_11_10.py, stdnum/iso7064/mod_11_2.py, stdnum/iso7064/mod_37_2.py, stdnum/iso7064/mod_37_36.py, stdnum/iso7064/mod_97_10.py, stdnum/lt/pvm.py, stdnum/luhn.py, stdnum/meid.py, stdnum/verhoeff.py: some more documentation improvements 2012-02-26 Arthur de Jong * [13218a0] setup.py: make script executable 2012-02-26 Arthur de Jong * [c2f0ea2] stdnum/fr/siren.py: add a to_vta() function to the stdnum.fr.siren module 2012-02-26 Arthur de Jong * [902a656] stdnum/__init__.py, stdnum/at/uid.py, stdnum/be/vat.py, stdnum/bg/egn.py, stdnum/bg/pnf.py, stdnum/bg/vat.py, stdnum/br/cpf.py, stdnum/cy/vat.py, stdnum/cz/dic.py, stdnum/cz/rc.py, stdnum/de/vat.py, stdnum/dk/cpr.py, stdnum/dk/cvr.py, stdnum/ean.py, stdnum/ee/kmkr.py, stdnum/es/cif.py, stdnum/es/dni.py, stdnum/es/nie.py, stdnum/es/nif.py, stdnum/eu/vat.py, stdnum/fi/alv.py, stdnum/fi/hetu.py, stdnum/fr/siren.py, stdnum/fr/tva.py, stdnum/gb/vat.py, stdnum/gr/vat.py, stdnum/grid.py, stdnum/hr/oib.py, stdnum/hu/anum.py, stdnum/iban.py, stdnum/ie/pps.py, stdnum/ie/vat.py, stdnum/imei.py, stdnum/imsi.py, stdnum/isan.py, stdnum/isbn.py, stdnum/isil.py, stdnum/ismn.py, stdnum/iso7064/__init__.py, stdnum/iso7064/mod_11_10.py, stdnum/iso7064/mod_11_2.py, stdnum/iso7064/mod_37_2.py, stdnum/iso7064/mod_37_36.py, stdnum/iso7064/mod_97_10.py, stdnum/issn.py, stdnum/it/iva.py, stdnum/lt/pvm.py, stdnum/lu/tva.py, stdnum/luhn.py, stdnum/lv/pvn.py, stdnum/meid.py, stdnum/mt/vat.py, stdnum/nl/bsn.py, stdnum/nl/btw.py, stdnum/nl/onderwijsnummer.py, stdnum/numdb.py, stdnum/pl/nip.py, stdnum/pt/nif.py, stdnum/ro/cf.py, stdnum/ro/cnp.py, stdnum/se/vat.py, stdnum/si/ddv.py, stdnum/sk/dph.py, stdnum/sk/rc.py, stdnum/us/ssn.py, stdnum/util.py, stdnum/verhoeff.py: ensure that the module docstrings are in a somewhat more usable format 2012-02-25 Arthur de Jong * [907e410] setup.py: add the optional dependency on suds for the stdnum.eu.vat.check_vies() function 2012-02-24 Arthur de Jong * [ae9268b] stdnum/cz/rc.py: make the get_birth_date() function publically available 2012-02-24 Arthur de Jong * [4dfc8d7] docs/_templates/autosummary/module.rst, docs/conf.py, docs/index.rst, docs/stdnum.at.uid.rst, docs/stdnum.be.vat.rst, docs/stdnum.bg.egn.rst, docs/stdnum.bg.pnf.rst, docs/stdnum.bg.vat.rst, docs/stdnum.br.cpf.rst, docs/stdnum.cy.vat.rst, docs/stdnum.cz.dic.rst, docs/stdnum.cz.rc.rst, docs/stdnum.de.vat.rst, docs/stdnum.dk.cpr.rst, docs/stdnum.dk.cvr.rst, docs/stdnum.ean.rst, docs/stdnum.ee.kmkr.rst, docs/stdnum.es.cif.rst, docs/stdnum.es.dni.rst, docs/stdnum.es.nie.rst, docs/stdnum.es.nif.rst, docs/stdnum.eu.vat.rst, docs/stdnum.fi.alv.rst, docs/stdnum.fi.hetu.rst, docs/stdnum.fr.siren.rst, docs/stdnum.fr.tva.rst, docs/stdnum.gb.vat.rst, docs/stdnum.gr.vat.rst, docs/stdnum.grid.rst, docs/stdnum.hr.oib.rst, docs/stdnum.hu.anum.rst, docs/stdnum.iban.rst, docs/stdnum.ie.pps.rst, docs/stdnum.ie.vat.rst, docs/stdnum.imei.rst, docs/stdnum.imsi.rst, docs/stdnum.isan.rst, docs/stdnum.isbn.rst, docs/stdnum.isil.rst, docs/stdnum.ismn.rst, docs/stdnum.iso7064.rst, docs/stdnum.issn.rst, docs/stdnum.it.iva.rst, docs/stdnum.lt.pvm.rst, docs/stdnum.lu.tva.rst, docs/stdnum.luhn.rst, docs/stdnum.lv.pvn.rst, docs/stdnum.meid.rst, docs/stdnum.mt.vat.rst, docs/stdnum.nl.bsn.rst, docs/stdnum.nl.btw.rst, docs/stdnum.nl.onderwijsnummer.rst, docs/stdnum.pl.nip.rst, docs/stdnum.pt.nif.rst, docs/stdnum.ro.cf.rst, docs/stdnum.ro.cnp.rst, docs/stdnum.se.vat.rst, docs/stdnum.si.ddv.rst, docs/stdnum.sk.dph.rst, docs/stdnum.sk.rc.rst, docs/stdnum.us.ssn.rst, docs/stdnum.verhoeff.rst, setup.cfg: generate documentation using Sphinx 2012-02-23 Arthur de Jong * [093b1a1] README, stdnum/__init__.py, stdnum/dk/cpr.py: add a CPR (personnummer, the Danish citizen number) module 2012-02-23 Arthur de Jong * [89e4d78] README, stdnum/__init__.py, stdnum/ie/pps.py: add a PPS No (Personal Public Service Number, Irish personal number) module 2012-02-22 Arthur de Jong * [3a9c407] README, stdnum/__init__.py, stdnum/hr/__init__.py, stdnum/hr/oib.py: add an OIB (Osobni identifikacijski broj, Croatian personal identification number) module 2012-02-20 Arthur de Jong * [680b7d1] numdb-test.dat, stdnum/numdb.py, test.dat: rename numdb test file 2012-02-20 Arthur de Jong * [68f62bf] stdnum/eu/vat.py: add a stdnum.eu.vat.check_vies() function to do an on-line check of the VAT number 2012-02-19 Arthur de Jong * [e640e3b] stdnum/iban.py, stdnum/numdb.py: add "pragma: no cover" statements to code that isn't expected to be covered 2012-02-19 Arthur de Jong * [b561d59] README, stdnum/__init__.py, stdnum/eu/__init__.py, stdnum/eu/vat.py, tests/test_eu_vat.doctest: add a VAT (European Union VAT number) module 2012-02-19 Arthur de Jong * [61af19d] README, stdnum/__init__.py: make number description consistent 2012-02-19 Arthur de Jong * [eeb5c61] stdnum/at/__init__.py, stdnum/cz/__init__.py, stdnum/dk/__init__.py, stdnum/ee/__init__.py, stdnum/es/__init__.py, stdnum/fi/__init__.py, stdnum/fr/__init__.py, stdnum/hu/__init__.py, stdnum/it/__init__.py, stdnum/lt/__init__.py, stdnum/lu/__init__.py, stdnum/lv/__init__.py, stdnum/nl/__init__.py, stdnum/pl/__init__.py, stdnum/pt/__init__.py, stdnum/ro/__init__.py, stdnum/si/__init__.py, stdnum/sk/__init__.py: for all countries, provide vat as an alias for the local vat identifier 2012-02-19 Arthur de Jong * [6755b94] stdnum/at/__init__.py, stdnum/be/__init__.py, stdnum/bg/__init__.py, stdnum/br/__init__.py, stdnum/cy/__init__.py, stdnum/cz/__init__.py, stdnum/de/__init__.py, stdnum/dk/__init__.py, stdnum/ee/__init__.py, stdnum/es/__init__.py, stdnum/fi/__init__.py, stdnum/fr/__init__.py, stdnum/gb/__init__.py, stdnum/gr/__init__.py, stdnum/hu/__init__.py, stdnum/ie/__init__.py, stdnum/it/__init__.py, stdnum/lt/__init__.py, stdnum/lu/__init__.py, stdnum/lv/__init__.py, stdnum/mt/__init__.py, stdnum/nl/__init__.py, stdnum/pl/__init__.py, stdnum/pt/__init__.py, stdnum/ro/__init__.py, stdnum/se/__init__.py, stdnum/si/__init__.py, stdnum/sk/__init__.py, stdnum/us/__init__.py: give all packages a description 2012-02-19 Arthur de Jong * [6d74fe9] stdnum/nl/vat.py: remove stdnum.nl.vat alias module 2012-02-19 Arthur de Jong * [528901d] stdnum/util.py, tests/test_robustness.doctest: use introspection to find number modules and test them 2012-02-18 Arthur de Jong * [2d80a24] README, stdnum/__init__.py, stdnum/bg/vat.py, tests/test_bg_vat.doctest, tests/test_robustness.doctest: add a VAT (Идентификационен номер по ДДС, Bulgarian VAT numbers) module 2012-02-18 Arthur de Jong * [1384488] README, stdnum/__init__.py, stdnum/bg/pnf.py, tests/test_robustness.doctest: add a PNF (ЛНЧ, Личен номер на чужденец, Bulgarian personal number of a foreigner) module 2012-02-18 Arthur de Jong * [a24e98e] README, stdnum/__init__.py, stdnum/bg/__init__.py, stdnum/bg/egn.py, tests/test_robustness.doctest: add an EGN (ЕГН, Единен граждански номер, Bulgarian personal identity codes) module 2012-02-18 Arthur de Jong * [4ac3fe7] tests/test_robustness.doctest: explicitly test for False 2012-02-18 Arthur de Jong * [0c78d90] stdnum/lt/pvm.py: explicitly return False if no rule matches 2012-02-18 Arthur de Jong * [cddb5f9] README, stdnum/__init__.py, stdnum/gb/__init__.py, stdnum/gb/vat.py, tests/test_gb_vat.doctest, tests/test_robustness.doctest: add a VAT (United Kingdom (and Isle of Man) VAT registration number) module 2012-02-18 Arthur de Jong * [6c436ec] tests/test_fi_hetu.doctest: fix typo 2012-02-18 Arthur de Jong * [aa39c92] README, stdnum/__init__.py, stdnum/se/__init__.py, stdnum/se/vat.py, tests/test_robustness.doctest: add a VAT (Moms, Mervärdesskatt, Swedish VAT number) module 2012-02-18 Arthur de Jong * [3a7a91c] README, stdnum/__init__.py, stdnum/si/__init__.py, stdnum/si/ddv.py, tests/test_robustness.doctest: add a ID za DDV (Davčna številka, Slovenian VAT number) module 2012-02-18 Arthur de Jong * [ebbd1af] README, stdnum/__init__.py, stdnum/pl/__init__.py, stdnum/pl/nip.py, tests/test_robustness.doctest: add a NIP (Numer Identyfikacji Podatkowej, Polish VAT number) module 2012-02-18 Arthur de Jong * [c75f072] README, stdnum/__init__.py, stdnum/mt/__init__.py, stdnum/mt/vat.py, tests/test_robustness.doctest: add a VAT (Maltese VAT number) module 2012-02-17 Arthur de Jong * [0922f3c] stdnum/it/iva.py: strip a few more separators 2012-02-17 Arthur de Jong * [b708920] README, stdnum/__init__.py, stdnum/fr/tva.py, tests/test_robustness.doctest: add a TVA (Numéro d'identification à la taxe sur la valeur ajoutée, French VAT number) module 2012-02-17 Arthur de Jong * [dc8e9a3] README, stdnum/__init__.py, stdnum/lt/__init__.py, stdnum/lt/pvm.py, tests/test_robustness.doctest: add a PVM (Pridėtinės vertės mokestis mokėtojo kodas, Lithuanian VAT number) module 2012-02-17 Arthur de Jong * [20296ef] README, stdnum/__init__.py, stdnum/ee/__init__.py, stdnum/ee/kmkr.py, tests/test_robustness.doctest: add a KMKR (Käibemaksukohuslase, Estonian VAT number) module 2012-02-17 Arthur de Jong * [2100c28] README, stdnum/__init__.py, stdnum/ie/__init__.py, stdnum/ie/vat.py, tests/test_robustness.doctest: add a VAT (Irish VAT number) module 2012-02-17 Arthur de Jong * [d2f1348] README, stdnum/__init__.py, stdnum/hu/__init__.py, stdnum/hu/anum.py, tests/test_robustness.doctest: add an ANUM (Közösségi adószám, Hungarian VAT number) module 2012-02-17 Arthur de Jong * [d803443] README, stdnum/__init__.py, stdnum/cz/dic.py, tests/test_robustness.doctest: add a DIČ (Daňové identifikační číslo, Czech VAT number) module 2012-02-17 Arthur de Jong * [0d2e4cc] README, stdnum/__init__.py, stdnum/fi/alv.py, tests/test_robustness.doctest: add an ALV nro (Arvonlisäveronumero, Finnish VAT number) module 2012-02-17 Arthur de Jong * [03eccc4] README, stdnum/__init__.py, stdnum/sk/dph.py, tests/test_robustness.doctest: add IČ DPH (Identifikačné číslo pre daň z pridanej hodnoty, Slovak VAT number) module 2012-02-16 Arthur de Jong * [389c306] README, stdnum/__init__.py, stdnum/pt/__init__.py, stdnum/pt/nif.py, tests/test_robustness.doctest: add a NIF (Número de identificação fiscal, Portuguese VAT number) module 2012-02-13 Arthur de Jong * [cdc7f96] README, stdnum/__init__.py, stdnum/at/__init__.py, stdnum/at/uid.py, tests/test_robustness.doctest: add a UID (Umsatzsteuer-Identifikationsnummer, Austrian VAT number) module 2012-02-13 Arthur de Jong * [e0bb4e8] README, stdnum/__init__.py, stdnum/cy/__init__.py, stdnum/cy/vat.py, tests/test_robustness.doctest: add a Αριθμός Εγγραφής Φ.Π.Α. (Cypriot VAT number) module 2012-02-12 Arthur de Jong * [402a0d5] stdnum/es/cif.py, stdnum/it/iva.py, stdnum/util.py: use the luhn module where possible 2012-02-12 Arthur de Jong * [1c2b4c3] tests/test_robustness.doctest: fix typo in header 2012-02-12 Arthur de Jong * [09ef54d] README, stdnum/__init__.py, stdnum/it/__init__.py, stdnum/it/iva.py, tests/test_robustness.doctest: add a Partita IVA (Italian VAT number) module 2012-02-12 Arthur de Jong * [ffc824b] README, stdnum/__init__.py, stdnum/ro/cf.py, tests/test_robustness.doctest: add a CF (Cod de înregistrare în scopuri de TVA, Romanian VAT number) module 2012-02-12 Arthur de Jong * [9d65f6a] README, stdnum/__init__.py, stdnum/ro/__init__.py, stdnum/ro/cnp.py, tests/test_robustness.doctest: add a CNP (Cod Numeric Personal, Romanian Numerical Personal Code) module 2012-02-12 Arthur de Jong * [60533cd] stdnum/gr/vat.py: also strip : as seen in some numbers 2012-02-11 Arthur de Jong * [74c4c71] README, stdnum/__init__.py, stdnum/lu/__init__.py, stdnum/lu/tva.py, tests/test_robustness.doctest: add a TVA (Numéro d'identification à la taxe sur la valeur ajoutée, Luxembourgian VAT number) module 2012-02-11 Arthur de Jong * [74f4e2a] README, stdnum/__init__.py, stdnum/dk/__init__.py, stdnum/dk/cvr.py, tests/test_robustness.doctest: add a CVR (Momsregistreringsnummer, Danish VAT number) module 2012-02-11 Arthur de Jong * [3c64f1e] stdnum/be/vat.py: add missing test 2012-02-11 Arthur de Jong * [b8c3ba6] stdnum/be/vat.py: clean up numbers starting with (0) 2012-02-11 Arthur de Jong * [8a10861] README, stdnum/__init__.py, stdnum/lv/__init__.py, stdnum/lv/pvn.py, tests/test_robustness.doctest: add a PVN (Pievienotās vērtības nodokļa, Latvian VAT number) module 2012-02-11 Arthur de Jong * [a3610a3] README, stdnum/__init__.py, stdnum/es/nif.py, tests/test_robustness.doctest: add a NIF (Número de Identificación Fiscal, Spanish VAT number) module 2012-02-11 Arthur de Jong * [aa90c4f] README, stdnum/__init__.py, stdnum/es/cif.py, tests/test_robustness.doctest: add a CIF (Certificado de Identificación Fiscal, Spanish tax identification number) module 2012-02-11 Arthur de Jong * [a574e6c] stdnum/util.py: implement a digitsum() function to find the sub of all digits in a number 2012-02-11 Arthur de Jong * [84d1ee7] stdnum/es/nie.py: fix description and remove unnecessary import 2012-02-10 Arthur de Jong * [fa2d398] README, stdnum/__init__.py, stdnum/es/nie.py, tests/test_robustness.doctest: add a NIE (Número de Identificación de Extranjeros, Spanish identification number for foreigners) module 2012-02-10 Arthur de Jong * [fe3210f] README, stdnum/__init__.py, stdnum/es/__init__.py, stdnum/es/dni.py, tests/test_robustness.doctest: add a DNI (Documento nacional de identidad, Spanish personal identity codes) module 2012-02-10 Arthur de Jong * [4439f47] README, stdnum/__init__.py, stdnum/be/__init__.py, stdnum/be/vat.py, tests/test_robustness.doctest: add a BTW, TVA, NWSt (Belgian VAT number) module 2012-02-10 Arthur de Jong * [1ab602c] README, stdnum/__init__.py, stdnum/sk/__init__.py, stdnum/sk/rc.py: also make the stdnum.cz.rc module available as stdnum.sk.rc 2012-02-10 Arthur de Jong * [e9e5861] stdnum/nl/vat.py: also make the stdnum.nl.btw module available as stdnum.nl.vat 2012-02-10 Arthur de Jong * [c795b3c] stdnum/nl/btw.py: fix number in test and ensure that number is not all zeroes 2012-02-10 Arthur de Jong * [2bb9231] stdnum/cz/rc.py: add some info to description 2012-02-10 Arthur de Jong * [1aeeaf4] README, stdnum/__init__.py, stdnum/de/__init__.py, stdnum/de/vat.py, tests/test_robustness.doctest: add an Ust ID Nr. (Umsatzsteur Identifikationnummer, the German VAT number) module 2012-02-10 Arthur de Jong * [473b3ca] README, stdnum/__init__.py, stdnum/gr/__init__.py, stdnum/gr/vat.py, tests/test_robustness.doctest: add a FPA, ΦΠΑ (Foros Prostithemenis Aksias, the Greek VAT number) module 2012-02-05 Arthur de Jong * [9f1d47b] README, stdnum/__init__.py, stdnum/fr/__init__.py, stdnum/fr/siren.py, tests/test_robustness.doctest: add a SIREN (Système d'Identification du Répertoire des Entreprises, a French company identification number) module 2012-02-05 Arthur de Jong * [575fc75] README, stdnum/__init__.py, stdnum/cz/__init__.py, stdnum/cz/rc.py, tests/test_robustness.doctest: add a RČ (Rodné číslo, the Czech birth numbers) module 2012-02-04 Arthur de Jong * [41dd815] stdnum/br/cpf.py, stdnum/ean.py, stdnum/grid.py, stdnum/iban.py, stdnum/imei.py, stdnum/imsi.py, stdnum/isan.py, stdnum/isbn.py, stdnum/ismn.py, stdnum/issn.py, stdnum/meid.py, stdnum/nl/bsn.py, stdnum/nl/btw.py, stdnum/nl/onderwijsnummer.py, stdnum/us/ssn.py, stdnum/util.py: implement a stdnum.util module for holding utility functions (for now clean()) 2012-02-04 Arthur de Jong * [54cc207] tests/test_robustness.doctest: some extra rubustness checks 2012-02-04 Arthur de Jong * [b43817c] stdnum/nl/bsn.py, stdnum/nl/onderwijsnummer.py: rename calc_checksum() to checksum() for consistency 2012-02-04 Arthur de Jong * [548f129] stdnum/iso7064/mod_37_36.py: use integer division 2012-02-02 Arthur de Jong * [9efde4f] README, stdnum/__init__.py, stdnum/nl/btw.py, tests/test_robustness.doctest: add a BTW (the Dutch VAT number) module 2012-02-02 Arthur de Jong * [086e509] README, stdnum/__init__.py, stdnum/nl/bsn.py, stdnum/nl/onderwijsnummer.py, tests/test_robustness.doctest: add an onderwijsnummer (Dutch school number) module 2011-12-31 Arthur de Jong * [587c538] setup.py: revert switching to distutils part of r93, keep restructuring part 2011-12-31 Arthur de Jong * [6756d79] setup.cfg, setup.py: switch to distutils 2011-11-07 Arthur de Jong * [e6020b9] README, stdnum/__init__.py, stdnum/fi/__init__.py, stdnum/fi/hetu.py, tests/test_fi_hetu.doctest, tests/test_robustness.doctest: add a HETU (Finnish personal identity code) module as provided by Jussi Judin (#5) 2011-09-30 Arthur de Jong * [77ac8d4] setup.py: fix version number use (fix r86) 2011-09-30 Arthur de Jong * [6cdfb6b] ChangeLog, NEWS, stdnum/__init__.py: get files ready for 0.6 release 2011-09-30 Arthur de Jong * [1451b47] stdnum/imsi.dat, stdnum/isbn.dat, stdnum/isil.dat: update data files 2011-09-30 Arthur de Jong * [6ec6c7e] setup.py, stdnum/__init__.py: move the version number definition to the stdnum package 2011-09-25 Arthur de Jong * [ae2013d] stdnum/ismn.py: implement an ismn_type() function 2011-09-23 Arthur de Jong * [14b97f9] : ignore __pycache__ directories 2011-09-23 Arthur de Jong * [cbd114e] README, getimsi.py, stdnum/__init__.py, stdnum/imsi.dat, stdnum/imsi.py, tests/test_robustness.doctest: add an IMSI (International Mobile Subscriber Identity) module 2011-09-23 Arthur de Jong * [68c98f0] stdnum/imei.py: implement an imei.split() function that splits the number into a TAC, serial number and checksum or software version 2011-09-23 Arthur de Jong * [e6cd768] getiban.py: remove unneeded import 2011-09-20 Arthur de Jong * [4e8d7e4] stdnum/isbn.py, tests/test_isbn.doctest: implement a conversion function from ISBN13 to ISBN10 2011-09-20 Arthur de Jong * [d6f9ba2] tests/test_imei.doctest, tests/test_isan.doctest, tests/test_isbn.doctest, tests/test_ismn.doctest: fix space before inline comments 2011-09-20 Arthur de Jong * [c4ad099] stdnum/isbn.py, tests/test_isbn.doctest: fix a problem with an ISBN13 with a valid check digit but with an unknown bookland prefix 2011-09-04 Arthur de Jong * [1c7c198] setup.py: fix homepage URL 2011-08-19 Arthur de Jong * [881e8a6] getiban.py, getisbn.py, getisil.py, setup.py, stdnum/br/cpf.py, stdnum/ean.py, stdnum/grid.py, stdnum/iban.py, stdnum/imei.py, stdnum/isan.py, stdnum/isbn.py, stdnum/isil.py, stdnum/ismn.py, stdnum/iso7064/mod_11_10.py, stdnum/iso7064/mod_11_2.py, stdnum/iso7064/mod_37_2.py, stdnum/iso7064/mod_37_36.py, stdnum/iso7064/mod_97_10.py, stdnum/issn.py, stdnum/luhn.py, stdnum/meid.py, stdnum/nl/bsn.py, stdnum/numdb.py, stdnum/us/ssn.py, stdnum/verhoeff.py: make source code layout follow PEP8 more 2011-07-09 Arthur de Jong * [8dbcedd] ChangeLog, NEWS, setup.py: get files ready for 0.5 release 2011-07-09 Arthur de Jong * [596c7a1] stdnum/iban.dat, stdnum/isbn.dat, stdnum/isil.dat: update data files 2011-06-20 Arthur de Jong * [63b2b0a] stdnum/issn.py: implement a conversion function from ISSN to EAN 2011-06-20 Arthur de Jong * [d101acf] stdnum/isbn.py, stdnum/ismn.py: use the ean module for calculating the check digit 2011-06-20 Arthur de Jong * [f5747bc] README, stdnum/__init__.py, stdnum/ean.py, tests/test_robustness.doctest: add an EAN (International Article Number) module 2011-03-06 Arthur de Jong * [1b904ba] setup.py, stdnum/numdb.py: also support Python3 with the same codebase (see #3) 2011-03-06 Arthur de Jong * [a45079f] setup.py: ensure that data files are always included 2011-03-02 Arthur de Jong * [c17920a] stdnum/verhoeff.py: Python 2.5 compatibility improvement 2011-02-06 Arthur de Jong * [e6ba399] ChangeLog, NEWS, setup.py: get files ready for 0.4 release 2011-02-06 Arthur de Jong * [060dfce] stdnum/isbn.dat: include an updated version 2011-02-06 Arthur de Jong * [8806d2a] README, stdnum/__init__.py, stdnum/us/__init__.py, stdnum/us/ssn.py, tests/test_robustness.doctest: add an SSN (U.S. Social Security Number) module 2011-02-05 Arthur de Jong * [c260626] README, stdnum/__init__.py: add ISIL to the documentation 2011-02-05 Arthur de Jong * [e517903] getisil.py, stdnum/isil.dat, stdnum/isil.py, tests/test_robustness.doctest: add an ISIL (International Standard Identifier for Libraries and Related Organizations) module 2011-02-05 Arthur de Jong * [96f4f7c] stdnum/numdb.py: allow most kind of characters in number ranges 2011-02-05 Arthur de Jong * [33611d1] stdnum/iban.py: move more validation into try/except (specifically the _convert() call) 2011-02-05 Arthur de Jong * [62aa496] tests/test_br_cpf.doctest, tests/test_iban.doctest, tests/test_imei.doctest, tests/test_isan.doctest, tests/test_isbn.doctest, tests/test_ismn.doctest, tests/test_issn.doctest, tests/test_luhn.doctest, tests/test_meid.doctest, tests/test_nl_bsn.doctest, tests/test_robustness.doctest, tests/test_verhoeff.doctest: move all robustness tests into one test file 2011-02-05 Arthur de Jong * [9081e90] tests/test_iso7064.doctest: fix imports of iso7064.mod_*_* modules 2011-02-05 Arthur de Jong * [e5678ca] stdnum/isbn.py: fix typo in r53 2011-02-05 Arthur de Jong * [ea737ff] stdnum/__init__.py: add encoding header 2011-01-31 Arthur de Jong * [cc7a6d8] README, stdnum/__init__.py: get README and package docstring in sync 2011-01-21 Arthur de Jong * [6724e50] stdnum/isbn.py, tests/test_isbn.doctest: add a convert parameter to most isbn functions to automatically convert to ISBN-13 2011-01-17 Arthur de Jong * [411874e] README: add note about CPF and update copyright year 2011-01-16 Arthur de Jong * [db2238c] README, getiban.py, stdnum/iban.dat, stdnum/iban.py, tests/test_iban.doctest: add an IBAN (International Bank Account Number) module 2011-01-16 Arthur de Jong * [2b4aff6] setup.py, stdnum/numdb.py: revert r49 because it wasn't needed after all 2011-01-16 Arthur de Jong * [0bf31c9] setup.py, stdnum/numdb.py: introduce a full parameter that can be used to only return the part that is in the database 2011-01-16 Arthur de Jong * [4fe17ba] stdnum/grid.py, stdnum/isan.py: fix import of iso7064 modules 2011-01-16 Arthur de Jong * [c1f03c2] stdnum/numdb.py, test.dat: add test for partial match 2011-01-15 Arthur de Jong * [81a99d3] tests/test_nl_bsn.doctest: fix comments to refer to the new path of the module 2011-01-15 Arthur de Jong * [fda67ac] stdnum/br/__init__.py, stdnum/br/cpf.py, tests/test_br_cpf.doctest: add a CPF (Cadastro de Pessoas Físicas) module 2011-01-15 Arthur de Jong * [8d3a92c] stdnum/bsn.py, stdnum/nl/__init__.py, stdnum/nl/bsn.py, tests/test_bsn.doctest, tests/test_nl_bsn.doctest: move bsn module inside nl package 2010-11-26 Arthur de Jong * [6ed480c] setup.py, stdnum/__init__.py: move general description to package __init__.py file 2010-11-24 Arthur de Jong * [124c16d] getisbn.py, stdnum/isbn.dat, stdnum/isbn.py, stdnum/isbn/__init__.py, stdnum/isbn/ranges.py, stdnum/numdb.py, test.dat, tests/test_isbn.doctest: implement a new numdb module to hold information on hierarchically organised numbers and switch the isbn module to use this format instead 2010-09-11 Arthur de Jong * [72a0b96] ChangeLog, NEWS, README, setup.py: get files ready for 0.3 release 2010-09-05 Arthur de Jong * [cd844b5] setup.py: have sdist target create a tarball with reasonable permissions 2010-08-29 Arthur de Jong * [2e64eb8] stdnum/bsn.py, stdnum/isan.py, stdnum/iso7064/mod_37_2.py, stdnum/iso7064/mod_37_36.py, stdnum/meid.py, stdnum/verhoeff.py, tests/test_bsn.doctest, tests/test_ismn.doctest: spelling check 2010-08-28 Arthur de Jong * [2a7afff] README, stdnum/grid.py: add a GRid (Global Release Identifier) module 2010-08-27 Arthur de Jong * [9970652] README, stdnum/isan.py, tests/test_isan.doctest: add ISAN (International Standard Audiovisual Number) module 2010-08-27 Arthur de Jong * [fda9552] README, stdnum/iso7064/__init__.py, stdnum/iso7064/mod_11_10.py, stdnum/iso7064/mod_11_2.py, stdnum/iso7064/mod_37_2.py, stdnum/iso7064/mod_37_36.py, stdnum/iso7064/mod_97_10.py, tests/test_iso7064.doctest: implement some ISO/IEC 7064 check digit schemes 2010-08-26 Arthur de Jong * [4017d83] stdnum/isbn/__init__.py, stdnum/ismn.py, stdnum/issn.py, stdnum/verhoeff.py: switch to using enumerate() for looping over numbers where needed 2010-08-21 Arthur de Jong * [8bdb6ef] README, stdnum/ismn.py, tests/test_ismn.doctest: add an ISMN (International Standard Music Number) module 2010-08-21 Arthur de Jong * [97d5280] tests/test_isbn.doctest: simplify ranges tests a bit 2010-08-21 Arthur de Jong * [f3b025b] stdnum/isbn/ranges.py: update ranges from newly downloaded file 2010-08-20 Arthur de Jong * [8748830] README, stdnum/meid.py, tests/test_meid.doctest: add a MEID (Mobile Equipment Identifier) module 2010-08-20 Arthur de Jong * [f125f3e] setup.cfg, tests/test_isbn.doctest, tests/test_issn.doctest: write some more tests (some of which are a bit of a hack) to get coverage to 100% 2010-08-20 Arthur de Jong * [d622d92] stdnum/imei.py, tests/test_imei.doctest: add an add_check_digit option to the format() function to add a check digit if needed and possible 2010-08-20 Arthur de Jong * [a74a6f7] stdnum/luhn.py: make checksum calculation a little more readable 2010-08-20 Arthur de Jong * [6bb04af] README, stdnum/imei.py, tests/test_imei.doctest: add an IMEI (International Mobile Equipment Identity) module 2010-08-20 Arthur de Jong * [ca08995] README, stdnum/luhn.py, tests/test_luhn.doctest: add functions for handling the Luhn and Luhn mod N algorithms 2010-08-20 Arthur de Jong * [7e800c3] stdnum/issn.py: fix typo 2010-08-20 Arthur de Jong * [571dc83] README, stdnum/verhoeff.py, tests/test_verhoeff.doctest: add functions for handling the Verhoeff algorithm 2010-08-16 Arthur de Jong * [9ffa9fd] ChangeLog, NEWS, setup.py: get files ready for 0.2 release 2010-08-16 Arthur de Jong * [19b7d2d] debian/changelog, debian/compat, debian/control, debian/copyright, debian/docs, debian/rules, debian/source/format, debian/watch: debian package configuration is now available at http://svn.debian.org/viewsvn/python-modules/packages/python-stdnum/trunk/ 2010-08-14 Arthur de Jong * [85e9e3b] setup.cfg, tests/test_bsn.doctest, tests/test_isbn.doctest: add more doctests that are not part of the module documentation 2010-07-27 Arthur de Jong * [c536356] README, stdnum/bsn.py, stdnum/isbn/__init__.py, stdnum/issn.py: rename validate() function to is_valid() 2010-07-27 Arthur de Jong * [85a5fc8] stdnum/isbn/ranges.py: fix typo in output() function 2010-07-27 Arthur de Jong * [1071603] stdnum/isbn/ranges.py: fix range detection to handle lookup errors more gracefully 2010-07-27 Arthur de Jong * [a86c4cc] stdnum/bsn.py, stdnum/isbn/__init__.py, stdnum/issn.py: handle wrong types passed to validate() more gracefully 2010-07-26 Arthur de Jong * [9495116] debian/changelog, debian/source/format, debian/watch: make release 0.1-1 2010-07-25 Arthur de Jong * [55a97d4] ChangeLog: get files ready for 0.1 release 2010-07-25 Arthur de Jong * [1e02d5a] debian/changelog, debian/compat, debian/control, debian/copyright, debian/docs, debian/rules, debian/source/format: add Debian packaging 2010-07-25 Arthur de Jong * [14bd2fe] COPYING, ChangeLog, MANIFEST.in, NEWS: include some more files in the source distribution 2010-07-25 Arthur de Jong * [9940cf3] setup.cfg: use nose for testing and ignore generated files and directories 2010-07-25 Arthur de Jong * [967f2ae] setup.py: add a setup.py script for use of setuptools 2010-07-25 Arthur de Jong * [ca5f850] README: add documentation to the README 2010-07-25 Arthur de Jong * [40aff16] stdnum/bsn.py, stdnum/isbn/__init__.py, stdnum/isbn/ranges.py, stdnum/issn.py: spelling check an extra doctest and a simplification 2010-07-23 Arthur de Jong * [6eabbc3] stdnum/bsn.py: add BSN (Burgerservicenummer, the Ducth national identification number) module 2010-07-23 Arthur de Jong * [92e18aa] stdnum/issn.py: add an ISSN (International Standard Serial Number) module 2010-07-23 Arthur de Jong * [31ce783] stdnum/isbn/__init__.py: fix example and fix ISBN13 conversion 2010-07-23 Arthur de Jong * [4b8c10e] stdnum/isbn/__init__.py: get rid of remainders of old code that used exceptions 2010-07-23 Arthur de Jong * [7d2f15a] README, stdnum/__init__.py, stdnum/isbn/__init__.py, stdnum/isbn/ranges.py: make a initial repository layout with an implementation of the isbn module python-stdnum-0.9/getisil.py0000755000000000000000000000475511623301675016205 0ustar rootroot00000000000000#!/usr/bin/env python # getisil.py - script to donwload ISIL agencies # # Copyright (C) 2011 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """This script downloads a web page from the ISIL Registration Authority and screen-scrapes the national and non-national ISIL agencies and code prefixes.""" import urllib import BeautifulSoup import re spaces_re = re.compile('\s+', re.UNICODE) # the web page that holds information on the ISIL authorities download_url = 'http://biblstandard.dk/isil/' def clean(s): """Cleans up the string removing unneeded stuff from it.""" return spaces_re.sub(' ', s.replace(u'\u0096', '')).strip().encode('utf-8') def parse(f): """Parse the specified file.""" print '# generated from ISIL Registration Authority, downloaded from' print '# %s' % download_url soup = BeautifulSoup.BeautifulSoup(f, convertEntities='html') # find all table rows for tr in soup.findAll('tr'): # find the rows with four columns of text tds = tr.findAll('td', attrs={'class': 'text'}, recursive=False) if len(tds) == 4: props = {} cc = clean(tds[0].string) if tds[1].string: props['country'] = clean(tds[1].contents[0]) ra_a = tds[2].find('a') if ra_a: props['ra'] = clean(ra_a.string) props['ra_url'] = clean(ra_a['href']) elif tds[2].string: props['ra'] = clean(tds[2].string) # we could also get the search urls from tds[3].findAll('a') print '%s$ %s' % ( cc, ' '.join(['%s="%s"' % (x, y) for x, y in props.iteritems()])) if __name__ == '__main__': #f = open('isil.html', 'r') f = urllib.urlopen(download_url) parse(f) python-stdnum-0.9/numdb-test.dat0000644000000000000000000000024511720301355016723 0ustar rootroot00000000000000# this is a comment line 0-8 prop1="foo" 100-999 prop2="bar" 200,300-399 prop3="baz" 6 prop1="boo" 90-99 prop1="booz" 00-89 prop2="foo" 900-999 prop2="fooz" python-stdnum-0.9/getimsi.py0000755000000000000000000001732512260533041016173 0ustar rootroot00000000000000#!/usr/bin/env python # getismsi.py - script to donwload data from Wikipedia to build the database # # Copyright (C) 2011, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA from collections import defaultdict import re import urllib # URLs that are downloaded mcc_list_url = 'https://en.wikipedia.org/w/index.php?title=Mobile_country_code&action=raw' cleanup_replacements = { 'Anguilla (United Kingdom)': 'Anguilla', 'Argentina|Argentine Republic': 'Argentina', 'Aruba (Kingdom of the Netherlands|Netherlands)': 'Aruba', 'Azerbaijan|Azerbaijani Republic': 'Azerbaijan', 'Bermuda (United Kingdom)': 'Bermuda', 'British Virgin Islands (United Kingdom)': 'British Virgin Islands', 'Brunei|Brunei Darussalam': 'Brunei', 'Cayman Islands': 'Cayman Islands (United Kingdom)', 'Cayman Islands (United Kingdom)': 'Cayman Islands (United Kingdom)', 'Czech Rep.': 'Czech Republic', 'Democratic People\'s Republic of Korea|Korea, North': 'North Korea', 'Denmark (Kingdom of Denmark)': 'Denmark', 'Faroe Islands (Kingdom of Denmark)': 'Faroe Islands (Denmark)', 'French Polynesia (France)': 'French Polynesia', 'Gabon|Gabonese Republic': 'Gabon', 'Georgia (country)|Georgia': 'Georgia', 'Gibraltar': 'Gibraltar (United Kingdom)', 'Gibraltar (United Kingdom)': 'Gibraltar (United Kingdom)', 'Greenland (Kingdom of Denmark)': 'Greenland (Denmark)', 'Guadeloupe': 'Guadeloupe (France)', 'Hong Kong (People\'s Republic of China|PRC)': 'Hong Kong (China)', 'Hong Kong (Special Administrative Region of People\'s Republic of China)': 'Hong Kong (China)', 'Korea (Rep. of)': 'South Korea', 'Kyrgyz Republic': 'Kyrgyzstan', 'Lao People\'s Democratic Republic|Laos': 'Laos', 'Macau (People\'s Republic of China)': 'Macau (China)', 'Macau (People\'s Republic of China|PRC)': 'Macau (China)', 'Martinique': 'Martinique (France)', 'Moldova (Republic of)': 'Moldova', 'Montenegro (Republic of)': 'Montenegro', 'Netherlands (Kingdom of the Netherlands)': 'Netherlands', 'Palestinian Authority': 'Palestinian territories', 'Palestinian territories|Palestine': 'Palestinian territories', 'People\'s Republic of China|China': 'China', 'Puerto Rico (United States)': 'Puerto Rico', 'Republic of Ireland|Ireland': 'Ireland', 'Republic of Korea|Korea, South': 'South Korea', 'Russian Federation': 'Russian Federation', 'Rwanda|Rwandese Republic': 'Rwanda', 'Serbia (Republic of)': 'Serbia', 'Somali Democratic Republic|Somalia': 'Somalia', 'Syrian Arab Republic': 'Syria', 'Syrian Arab Republic|Syria': 'Syria', 'Turks and Caicos Islands (United Kingdom)': 'Turks and Caicos Islands', 'United States': 'United States of America', 'United States Virgin Islands (United States)': 'United States Virgin Islands', 'Venezuela (Bolivarian Republic of)': 'Venezuela', 'Vietnam|Viet Nam': 'Vietnam', } remove_ref_re = re.compile(r'.*?') remove_comment_re = re.compile(r'{{.*?}}') remove_href_re = re.compile(ur'(?i)\b((?:https?://|www\d{0,3}[.]|[a-z0-9.\-]+' + ur'[.][a-z]{2,4}/)(?:[^\s()<>]+|\(([^\s()<>]+|' + ur'(\([^\s()<>]+\)))*\))+(?:\(([^\s()<>]+|' + ur'(\([^\s()<>]+\)))*\)|[^\s`!()\[\]{};:\'".,<>' + ur'?\xab\xbb\u201c\u201d\u2018\u2019]))') def cleanup_value(val): """Remove unneeded markup from the value.""" # remove uninteresting things from value val = remove_comment_re.sub('', val) val = remove_ref_re.sub('', val) val = remove_href_re.sub('', val) val = val.replace('[', '').replace(']', '').replace('\'\'', '').strip() val = val.split('|')[-1] # replace value val = val.replace('Unknown', '') val = val.replace('United Kingdom|UK', 'United Kingdom') val = val.replace('United States|US', 'United States') val = val.replace('New Zealand|NZ', 'New Zealand').strip() return cleanup_replacements.get(val, val) def update_mncs(data, mcc, mnc, **kwargs): """Merge provided mnc information with the data that is already stored in mccs.""" data[mcc][mnc].update(dict((k, cleanup_value(v)) for k, v in kwargs.items() if v)) def get_mncs_from_wikipedia(data): """Update the collection of Mobile Country Codes from Wikipedia. This parses a Wikipedia page to extract the MCC and MNC, the first part of any IMSI, and stores the results.""" mnc_country_re = re.compile(r'^[=]{2,4}\s+(?P.*?)(\s+-\s+(?P[^\s]{2}))?\s+[=]{2,4}$') mnc_line_re = re.compile(r'^\|\s*(?P[0-9]+)' + r'\s*\\\\\s*(?P[0-9]+)' + r'(\s*\\\\\s*(?P[^\\]*)' + r'(\s*\\\\\s*(?P[^\\]*)' + r'(\s*\\\\\s*(?P[^\\]*)' + r'(\s*\\\\\s*(?P[^\\]*)' + r'(\s*\\\\\s*(?P[^\\]*)' + r')?)?)?)?)?') f = urllib.urlopen(mcc_list_url) country = cc = '' for line in f.readlines(): line = line.strip() match = mnc_country_re.match(line) if match: country = match.group('country') cc = (match.group('cc') or '').lower() if '||' not in line: continue line = line.replace('||', '\\\\') match = mnc_line_re.match(line) if match: mnc_list = str2range(match.group('mnc')) for mnc in mnc_list: update_mncs(data, match.group('mcc'), mnc, country=country, cc=cc, brand=match.group('brand'), operator=match.group('operator'), status=match.group('status'), bands=match.group('bands')) def str2range(x): result = [] for part in x.split(','): if '-' in part: a, b = part.split('-') f = '%0' + str(len(b)) + 'd' a, b = int(a), int(b) for i in range(a, b + 1): result.append(f % (i)) else: a = part result.append(part) return result if __name__ == '__main__': # download/parse the information data = defaultdict(lambda: defaultdict(dict)) get_mncs_from_wikipedia(data) # print header print '# generated from various sources' print '# %s' % mcc_list_url # build an ordered list of mccs mcc_list = list(data.keys()) mcc_list.sort() # go over mccs for mcc in mcc_list: print '%s' % mcc # build an ordered list of mncs mnc_list = data[mcc].keys() mnc_list.sort() for mnc in mnc_list: info = data[mcc][mnc] infokeys = info.keys() infokeys.sort() print ' %s%s' % (mnc, ''.join([' %s="%s"' % (k, info[k]) for k in infokeys])) # try to get the length of mnc's try: l = len(mnc_list[0]) print ' %s-%s' % (l * '0', l * '9') except IndexError: pass # ignore python-stdnum-0.9/README0000644000000000000000000001437212260533233015037 0ustar rootroot00000000000000python-stdnum ============= A Python module to parse, validate and reformat standard numbers and codes in different formats. Available formats ----------------- Currently this package supports the following formats: * UID (Umsatzsteuer-Identifikationsnummer, Austrian VAT number) * BTW, TVA, NWSt (Belgian VAT number) * EGN (ЕГН, Единен граждански номер, Bulgarian personal identity codes) * PNF (ЛНЧ, Личен номер на чужденец, Bulgarian number of a foreigner) * VAT (Идентификационен номер по ДДС, Bulgarian VAT number) * CPF (Cadastro de Pessoas Físicas, Brazillian national identifier) * Αριθμός Εγγραφής Φ.Π.Α. (Cypriot VAT number) * DIČ (Daňové identifikační číslo, Czech VAT number) * RČ (Rodné číslo, the Czech birth number) * Ust ID Nr. (Umsatzsteur Identifikationnummer, German VAT number) * CPR (personnummer, the Danish citizen number) * CVR (Momsregistreringsnummer, Danish VAT number) * EAN (International Article Number) * KMKR (Käibemaksukohuslase, Estonian VAT number) * CIF (Certificado de Identificación Fiscal, Spanish company tax number) * DNI (Documento nacional de identidad, Spanish personal identity codes) * NIE (Número de Identificación de Extranjeros, Spanish foreigner number) * NIF (Número de Identificación Fiscal, Spanish VAT number) * VAT (European Union VAT number) * ALV nro (Arvonlisäveronumero, Finnish VAT number) * HETU (Henkilötunnus, Finnish personal identity code) * SIREN (a French company identification number) * n° TVA (taxe sur la valeur ajoutée, French VAT number) * VAT (United Kingdom (and Isle of Man) VAT registration number) * FPA, ΦΠΑ (Foros Prostithemenis Aksias, the Greek VAT number) * GRid (Global Release Identifier) * OIB (Osobni identifikacijski broj, Croatian identification number) * ANUM (Közösségi adószám, Hungarian VAT number) * IBAN (International Bank Account Number) * PPS No (Personal Public Service Number, Irish personal number) * VAT (Irish VAT number) * IMEI (International Mobile Equipment Identity) * IMSI (International Mobile Subscriber Identity) * ISAN (International Standard Audiovisual Number) * ISBN (International Standard Book Number) * ISIL (International Standard Identifier for Libraries) * ISMN (International Standard Music Number) * ISSN (International Standard Serial Number) * Partita IVA (Italian VAT number) * PVM (Pridėtinės vertės mokestis mokėtojo kodas, Lithuanian VAT number) * TVA (taxe sur la valeur ajoutée, Luxembourgian VAT number) * PVN (Pievienotās vērtības nodokļa, Latvian VAT number) * MEID (Mobile Equipment Identifier) * VAT (Maltese VAT number) * NRIC No. (Malaysian National Registration Identity Card Number) * Brin number (Dutch number for schools) * BSN (Burgerservicenummer, Dutch national identification number) * BTW-nummer (Omzetbelastingnummer, the Dutch VAT number) * Onderwijsnummer (Dutch student school number) * Postcode (Dutch postal code) * NIP (Numer Identyfikacji Podatkowej, Polish VAT number) * NIF (Número de identificação fiscal, Portuguese VAT number) * CF (Cod de înregistrare în scopuri de TVA, Romanian VAT number) * CNP (Cod Numeric Personal, Romanian Numerical Personal Code) * VAT (Moms, Mervärdesskatt, Swedish VAT number) * ID za DDV (Davčna številka, Slovenian VAT number) * IČ DPH (IČ pre daň z pridanej hodnoty, Slovak VAT number) * RČ (Rodné číslo, the Slovak birth number) * ATIN (U.S. Adoption Taxpayer Identification Number) * EIN (U.S. Employer Identification Number) * ITIN (U.S. Individual Taxpayer Identification Number) * PTIN (U.S. Preparer Tax Identification Number) * SSN (U.S. Social Security Number) * TIN (U.S. Taxpayer Identification Number) Furthermore a number of generic check digit algorithms are available: * the Verhoeff algorithm * the Luhn and Luhn mod N algorithms * some algorithms described in ISO/IEC 7064: Mod 11, 2, Mod 37, 2, Mod 97, 10, Mod 11, 10 and Mod 37, 36 Basically any number or code that has some validation mechanism available or some common formatting is eligible for inclusion into this library. These modules generally do not provide background information on the meaning and use of the specified numbers, only parsing and handling functions. Interface --------- Most of these modules implement the following functions: validate() - validate the correctness of the passed number and return a compact representation of the number invalid numbers are rejected with one of the exceptions from the stdnum.exceptions module compact() - return a compact representation of the number or code this function generally does not do validation but may raise exceptions for wildly incorrect numbers format() - return a formatted version of the number in the preferred format this function generally expects to be passed a valid number or code Apart from the above, the module may add extra parsing, validation or conversion functions. Requirements ------------ The modules should not require any external Python modules and should be pure Python. The modules are developed and tested with Python 2.6 but may also work with older versions of Python. Copyright --------- Copyright (C) 2010, 2011, 2012, 2013 Arthur de Jong This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA Feedback and bug reports ------------------------ If you have any questions regarding python-stdnum, would like to report a bug or request addition of a format please send an email to Patches and code contributions are more than welcome. python-stdnum-0.9/getisbn.py0000755000000000000000000000760311623305314016165 0ustar rootroot00000000000000#!/usr/bin/env python # getisbn.py - script to get ISBN prefix data # # Copyright (C) 2010, 2011 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """This script downloads XML data from the International ISBN Agency website and provides a compact form of all group prefixes, and registrant ranges for those prefixes suitable for the numdb module. This data is needed to correctly split ISBNs into an EAN.UCC prefix, a group prefix, a registrant, an item number and a check-digit.""" import xml.sax import urllib # The place where the current version of RangeMessage.xml can be downloaded. download_url = 'http://www.isbn-international.org/agency?rmxml=1' def _wrap(text): """Generator that returns lines of text that are no longer than max_len.""" while text: i = len(text) if i > 73: i = text.rindex(',', 20, 73) yield text[:i] text = text[i + 1:] class RangeHandler(xml.sax.ContentHandler): def __init__(self): self._gather = None self._prefix = None self._agency = None self._range = None self._length = None self._ranges = [] self._last = None self._topranges = {} def startElement(self, name, attrs): if name in ('MessageSerialNumber', 'MessageDate', 'Prefix', 'Agency', 'Range', 'Length'): self._gather = '' def characters(self, content): if self._gather is not None: self._gather += content def endElement(self, name): if name == 'MessageSerialNumber': print '# file serial %s' % self._gather.strip() elif name == 'MessageDate': print '# file date %s' % self._gather.strip() elif name == 'Prefix': self._prefix = self._gather.strip() elif name == 'Agency': self._agency = self._gather.strip() elif name == 'Range': self._range = self._gather.strip() elif name == 'Length': self._length = int(self._gather.strip()) elif name == 'Rule' and self._length: self._ranges.append(tuple(x[:self._length] for x in self._range.split('-'))) elif name == 'Rules': if '-' in self._prefix: p, a = self._prefix.split('-') if p != self._last: print p self._last = p for line in _wrap(','.join(r[0] + '-' + r[1] for r in self._topranges[p])): print ' %s' % line print ' %s agency="%s"' % (a, self._agency) for line in _wrap(','.join(r[0] + '-' + r[1] for r in self._ranges)): print ' %s' % line else: self._topranges[self._prefix] = self._ranges self._ranges = [] self._gather = None if __name__ == '__main__': print '# generated from RangeMessage.xml, downloaded from' print '# %s' % download_url parser = xml.sax.make_parser() parser.setContentHandler(RangeHandler()) parser.parse(urllib.urlopen(download_url)) #parser.parse('RangeMessage.xml') python-stdnum-0.9/MANIFEST.in0000644000000000000000000000017612204002711015700 0ustar rootroot00000000000000include README NEWS ChangeLog COPYING numdb-test.dat *.py recursive-include tests *.doctest recursive-include docs *.rst *.py python-stdnum-0.9/getnumlist.py0000755000000000000000000000410712204002711016710 0ustar rootroot00000000000000#!/usr/bin/env python # getnumlist.py - script to get a list of number formats in stdnum # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """This script uses introspection to present a list of number formats suitable to be included in the README and stdnum package description.""" import pydoc from stdnum import util # these are excluded algortihms = ('stdnum.verhoeff', 'stdnum.luhn', 'stdnum.iso7064') def get_number_modules(): """Provides the number modules that are not algorithms.""" for module in util.get_number_modules(): if module.__name__ not in algortihms and \ not module.__name__.startswith('stdnum.iso7064'): yield module if __name__ == '__main__': print 'For README:' print '' for module in get_number_modules(): print ' * %s' % util.get_module_name(module) print '' print 'For stdnum/__init__.py:' print '' for module in get_number_modules(): print ' * %s: %s' % ( module.__name__.replace('stdnum.', ''), util.get_module_name(module), ) print '' print 'For docs/index.rst:' print '' for module in get_number_modules(): print ' %s' % module.__name__.replace('stdnum.', '') print '' print 'For index.xml:' print '' for module in get_number_modules(): print '
  • %s
  • ' % util.get_module_name(module) python-stdnum-0.9/PKG-INFO0000644000000000000000000001377312260536562015270 0ustar rootroot00000000000000Metadata-Version: 1.1 Name: python-stdnum Version: 0.9 Summary: Python module to handle standardized numbers and codes Home-page: http://arthurdejong.org/python-stdnum/ Author: Arthur de Jong Author-email: arthur@arthurdejong.org License: LGPL Description: Parse, validate and reformat standard numbers and codes. This library offers functions for parsing, validating and reformatting standard numbers and codes in various formats. Currently this package supports the following formats: * at.uid: UID (Umsatzsteuer-Identifikationsnummer, Austrian VAT number) * be.vat: BTW, TVA, NWSt (Belgian VAT number) * bg.egn: EGN (ЕГН, Единен граждански номер, Bulgarian personal identity codes) * bg.pnf: PNF (ЛНЧ, Личен номер на чужденец, Bulgarian number of a foreigner) * bg.vat: VAT (Идентификационен номер по ДДС, Bulgarian VAT number) * br.cpf: CPF (Cadastro de Pessoas Físicas, Brazillian national identifier) * cy.vat: Αριθμός Εγγραφής Φ.Π.Α. (Cypriot VAT number) * cz.dic: DIČ (Daňové identifikační číslo, Czech VAT number) * cz.rc: RČ (Rodné číslo, the Czech birth number) * de.vat: Ust ID Nr. (Umsatzsteur Identifikationnummer, German VAT number) * dk.cpr: CPR (personnummer, the Danish citizen number) * dk.cvr: CVR (Momsregistreringsnummer, Danish VAT number) * ean: EAN (International Article Number) * ee.kmkr: KMKR (Käibemaksukohuslase, Estonian VAT number) * es.cif: CIF (Certificado de Identificación Fiscal, Spanish company tax number) * es.dni: DNI (Documento nacional de identidad, Spanish personal identity codes) * es.nie: NIE (Número de Identificación de Extranjeros, Spanish foreigner number) * es.nif: NIF (Número de Identificación Fiscal, Spanish VAT number) * eu.vat: VAT (European Union VAT number) * fi.alv: ALV nro (Arvonlisäveronumero, Finnish VAT number) * fi.hetu: HETU (Henkilötunnus, Finnish personal identity code) * fr.siren: SIREN (a French company identification number) * fr.tva: n° TVA (taxe sur la valeur ajoutée, French VAT number) * gb.vat: VAT (United Kingdom (and Isle of Man) VAT registration number) * gr.vat: FPA, ΦΠΑ (Foros Prostithemenis Aksias, the Greek VAT number) * grid: GRid (Global Release Identifier) * hr.oib: OIB (Osobni identifikacijski broj, Croatian identification number) * hu.anum: ANUM (Közösségi adószám, Hungarian VAT number) * iban: IBAN (International Bank Account Number) * ie.pps: PPS No (Personal Public Service Number, Irish personal number) * ie.vat: VAT (Irish VAT number) * imei: IMEI (International Mobile Equipment Identity) * imsi: IMSI (International Mobile Subscriber Identity) * isan: ISAN (International Standard Audiovisual Number) * isbn: ISBN (International Standard Book Number) * isil: ISIL (International Standard Identifier for Libraries) * ismn: ISMN (International Standard Music Number) * issn: ISSN (International Standard Serial Number) * it.iva: Partita IVA (Italian VAT number) * lt.pvm: PVM (Pridėtinės vertės mokestis mokėtojo kodas, Lithuanian VAT number) * lu.tva: TVA (taxe sur la valeur ajoutée, Luxembourgian VAT number) * lv.pvn: PVN (Pievienotās vērtības nodokļa, Latvian VAT number) * meid: MEID (Mobile Equipment Identifier) * mt.vat: VAT (Maltese VAT number) * my.nric: NRIC No. (Malaysian National Registration Identity Card Number) * nl.brin: Brin number (Dutch number for schools) * nl.bsn: BSN (Burgerservicenummer, Dutch national identification number) * nl.btw: BTW-nummer (Omzetbelastingnummer, the Dutch VAT number) * nl.onderwijsnummer: Onderwijsnummer (Dutch student school number) * nl.postcode: Postcode (Dutch postal code) * pl.nip: NIP (Numer Identyfikacji Podatkowej, Polish VAT number) * pt.nif: NIF (Número de identificação fiscal, Portuguese VAT number) * ro.cf: CF (Cod de înregistrare în scopuri de TVA, Romanian VAT number) * ro.cnp: CNP (Cod Numeric Personal, Romanian Numerical Personal Code) * se.vat: VAT (Moms, Mervärdesskatt, Swedish VAT number) * si.ddv: ID za DDV (Davčna številka, Slovenian VAT number) * sk.dph: IČ DPH (IČ pre daň z pridanej hodnoty, Slovak VAT number) * sk.rc: RČ (Rodné číslo, the Slovak birth number) * us.atin: ATIN (U.S. Adoption Taxpayer Identification Number) * us.ein: EIN (U.S. Employer Identification Number) * us.itin: ITIN (U.S. Individual Taxpayer Identification Number) * us.ptin: PTIN (U.S. Preparer Tax Identification Number) * us.ssn: SSN (U.S. Social Security Number) * us.tin: TIN (U.S. Taxpayer Identification Number) Furthermore a number of generic check digit algorithms are available: * iso7064.mod_11_10: The ISO 7064 Mod 11, 10 algorithm * iso7064.mod_11_2: The ISO 7064 Mod 11, 2 algorithm * iso7064.mod_37_2: The ISO 7064 Mod 37, 2 algorithm * iso7064.mod_37_36: The ISO 7064 Mod 37, 36 algorithm * iso7064.mod_97_10: The ISO 7064 Mod 97, 10 algorithm * luhn: The Luhn and Luhn mod N algorithms * verhoeff: The Verhoeff algorithm Platform: UNKNOWN Classifier: Development Status :: 4 - Beta Classifier: Intended Audience :: Developers Classifier: Intended Audience :: System Administrators Classifier: License :: OSI Approved :: GNU Library or Lesser General Public License (LGPL) Classifier: Operating System :: OS Independent Classifier: Programming Language :: Python Classifier: Topic :: Software Development :: Libraries :: Python Modules Classifier: Topic :: Text Processing :: General python-stdnum-0.9/docs/0000755000000000000000000000000012260536561015107 5ustar rootroot00000000000000python-stdnum-0.9/docs/stdnum.eu.vat.rst0000644000000000000000000000011011721773163020346 0ustar rootroot00000000000000stdnum.eu.vat ============= .. automodule:: stdnum.eu.vat :members: python-stdnum-0.9/docs/stdnum.es.dni.rst0000644000000000000000000000011011721773163020324 0ustar rootroot00000000000000stdnum.es.dni ============= .. automodule:: stdnum.es.dni :members: python-stdnum-0.9/docs/stdnum.us.ptin.rst0000644000000000000000000000011312260533041020533 0ustar rootroot00000000000000stdnum.us.ptin ============== .. automodule:: stdnum.us.ptin :members: python-stdnum-0.9/docs/stdnum.ie.pps.rst0000644000000000000000000000011011721773163020342 0ustar rootroot00000000000000stdnum.ie.pps ============= .. automodule:: stdnum.ie.pps :members: python-stdnum-0.9/docs/stdnum.isan.rst0000644000000000000000000000010211721773163020077 0ustar rootroot00000000000000stdnum.isan =========== .. automodule:: stdnum.isan :members: python-stdnum-0.9/docs/stdnum.meid.rst0000644000000000000000000000010211721773163020063 0ustar rootroot00000000000000stdnum.meid =========== .. automodule:: stdnum.meid :members: python-stdnum-0.9/docs/stdnum.lu.tva.rst0000644000000000000000000000011011721773163020355 0ustar rootroot00000000000000stdnum.lu.tva ============= .. automodule:: stdnum.lu.tva :members: python-stdnum-0.9/docs/stdnum.mt.vat.rst0000644000000000000000000000011011721773163020355 0ustar rootroot00000000000000stdnum.mt.vat ============= .. automodule:: stdnum.mt.vat :members: python-stdnum-0.9/docs/stdnum.ee.kmkr.rst0000644000000000000000000000011311721773163020503 0ustar rootroot00000000000000stdnum.ee.kmkr ============== .. automodule:: stdnum.ee.kmkr :members: python-stdnum-0.9/docs/stdnum.issn.rst0000644000000000000000000000010211721773163020121 0ustar rootroot00000000000000stdnum.issn =========== .. automodule:: stdnum.issn :members: python-stdnum-0.9/docs/stdnum.fr.tva.rst0000644000000000000000000000011011721773163020344 0ustar rootroot00000000000000stdnum.fr.tva ============= .. automodule:: stdnum.fr.tva :members: python-stdnum-0.9/docs/stdnum.sk.dph.rst0000644000000000000000000000011011721773163020333 0ustar rootroot00000000000000stdnum.sk.dph ============= .. automodule:: stdnum.sk.dph :members: python-stdnum-0.9/docs/stdnum.fi.hetu.rst0000644000000000000000000000011311721773163020511 0ustar rootroot00000000000000stdnum.fi.hetu ============== .. automodule:: stdnum.fi.hetu :members: python-stdnum-0.9/docs/stdnum.cz.rc.rst0000644000000000000000000000010511721773163020167 0ustar rootroot00000000000000stdnum.cz.rc ============ .. automodule:: stdnum.cz.rc :members: python-stdnum-0.9/docs/stdnum.de.vat.rst0000644000000000000000000000011011721773163020325 0ustar rootroot00000000000000stdnum.de.vat ============= .. automodule:: stdnum.de.vat :members: python-stdnum-0.9/docs/stdnum.lt.pvm.rst0000644000000000000000000000011011721773163020364 0ustar rootroot00000000000000stdnum.lt.pvm ============= .. automodule:: stdnum.lt.pvm :members: python-stdnum-0.9/docs/conf.py0000644000000000000000000001422212154447010016377 0ustar rootroot00000000000000# -*- coding: utf-8 -*- # # python-stdnum documentation build configuration file, created by # sphinx-quickstart # # This file is execfile()d with the current directory set to its containing dir. # # Note that not all possible configuration values are present in this # autogenerated file. # # All configuration values have a default; values that are commented out # serve to show the default. import sys, os import stdnum # If extensions (or modules to document with autodoc) are in another directory, # add these directories to sys.path here. If the directory is relative to the # documentation root, use os.path.abspath to make it absolute, like shown here. #sys.path.insert(0, os.path.abspath('..')) # -- General configuration ----------------------------------------------------- # If your documentation needs a minimal Sphinx version, state it here. #needs_sphinx = '1.0' # Add any Sphinx extension module names here, as strings. They can be extensions # coming with Sphinx (named 'sphinx.ext.*') or your custom ones. extensions = [ 'sphinx.ext.autodoc', 'sphinx.ext.doctest', 'sphinx.ext.todo', 'sphinx.ext.coverage', 'sphinx.ext.autosummary' ] # Add any paths that contain templates here, relative to this directory. templates_path = ['_templates'] # The suffix of source filenames. source_suffix = '.rst' # The encoding of source files. source_encoding = 'utf-8' # The master toctree document. master_doc = 'index' # General information about the project. project = u'python-stdnum' copyright = u'2013, Arthur de Jong' # The version info for the project you're documenting, acts as replacement for # |version| and |release|, also used in various other places throughout the # built documents. # # The short X.Y version. version = stdnum.__version__ # The full version, including alpha/beta/rc tags. release = version # The language for content autogenerated by Sphinx. Refer to documentation # for a list of supported languages. #language = None # There are two options for replacing |today|: either, you set today to some # non-false value, then it is used: #today = '' # Else, today_fmt is used as the format for a strftime call. #today_fmt = '%B %d, %Y' # List of patterns, relative to source directory, that match files and # directories to ignore when looking for source files. exclude_patterns = ['_*', '.svn'] # The reST default role (used for this markup: `text`) to use for all documents. #default_role = None # If true, '()' will be appended to :func: etc. cross-reference text. #add_function_parentheses = True # If true, the current module name will be prepended to all description # unit titles (such as .. function::). #add_module_names = True # If true, sectionauthor and moduleauthor directives will be shown in the # output. They are ignored by default. #show_authors = False # The name of the Pygments (syntax highlighting) style to use. pygments_style = 'sphinx' # A list of ignored prefixes for module index sorting. modindex_common_prefix = ['stdnum.', ] # Automatically generate stub pages for autosummary entries. autosummary_generate = True # -- Options for HTML output --------------------------------------------------- # The theme to use for HTML and HTML Help pages. See the documentation for # a list of builtin themes. html_theme = 'default' # Theme options are theme-specific and customize the look and feel of a theme # further. For a list of options available for each theme, see the # documentation. #html_theme_options = {} # Add any paths that contain custom themes here, relative to this directory. #html_theme_path = [] # The name for this set of Sphinx documents. If None, it defaults to # " v documentation". #html_title = None # A shorter title for the navigation bar. Default is the same as html_title. #html_short_title = None # The name of an image file (relative to this directory) to place at the top # of the sidebar. #html_logo = None # The name of an image file (within the static path) to use as favicon of the # docs. This file should be a Windows icon file (.ico) being 16x16 or 32x32 # pixels large. #html_favicon = None # Add any paths that contain custom static files (such as style sheets) here, # relative to this directory. They are copied after the builtin static files, # so a file named "default.css" will overwrite the builtin "default.css". #html_static_path = ['_static'] # If not '', a 'Last updated on:' timestamp is inserted at every page bottom, # using the given strftime format. html_last_updated_fmt = '%b %d, %Y' # If true, SmartyPants will be used to convert quotes and dashes to # typographically correct entities. #html_use_smartypants = True # Custom sidebar templates, maps document names to template names. #html_sidebars = {} # Additional templates that should be rendered to pages, maps page names to # template names. #html_additional_pages = {} # If false, no module index is generated. #html_domain_indices = True # If false, no index is generated. #html_use_index = True # If true, the index is split into individual pages for each letter. #html_split_index = False # If true, links to the reST sources are added to the pages. html_show_sourcelink = False # If true, "Created using Sphinx" is shown in the HTML footer. Default is True. #html_show_sphinx = True # If true, "(C) Copyright ..." is shown in the HTML footer. Default is True. #html_show_copyright = True # If true, an OpenSearch description file will be output, and all pages will # contain a tag referring to it. The value of this option must be the # base URL from which the finished HTML is served. #html_use_opensearch = '' # This is the file name suffix for HTML files (e.g. ".xhtml"). #html_file_suffix = None # Suffix for generated links to HTML files. #html_link_suffix = '' # Output file base name for HTML help builder. htmlhelp_basename = 'python-stdnumdoc' # -- Options for manual page output -------------------------------------------- # One entry per manual page. List of tuples # (source start file, name, description, authors, manual section). man_pages = [ ('index', 'python-stdnum', u'python-stdnum Documentation', [u'Arthur de Jong'], 1) ] # If true, show URL addresses after external links. #man_show_urls = False python-stdnum-0.9/docs/_templates/0000755000000000000000000000000012260536561017244 5ustar rootroot00000000000000python-stdnum-0.9/docs/_templates/autosummary/0000755000000000000000000000000012260536561021632 5ustar rootroot00000000000000python-stdnum-0.9/docs/_templates/autosummary/module.rst0000644000000000000000000000011411721773163023647 0ustar rootroot00000000000000{{ fullname }} {{ underline }} .. automodule:: {{ fullname }} :members: python-stdnum-0.9/docs/stdnum.us.tin.rst0000644000000000000000000000011012260533041020350 0ustar rootroot00000000000000stdnum.us.tin ============= .. automodule:: stdnum.us.tin :members: python-stdnum-0.9/docs/stdnum.ro.cnp.rst0000644000000000000000000000011011721773163020343 0ustar rootroot00000000000000stdnum.ro.cnp ============= .. automodule:: stdnum.ro.cnp :members: python-stdnum-0.9/docs/stdnum.ean.rst0000644000000000000000000000007711721773163017723 0ustar rootroot00000000000000stdnum.ean ========== .. automodule:: stdnum.ean :members: python-stdnum-0.9/docs/stdnum.si.ddv.rst0000644000000000000000000000011011721773163020333 0ustar rootroot00000000000000stdnum.si.ddv ============= .. automodule:: stdnum.si.ddv :members: python-stdnum-0.9/docs/stdnum.sk.rc.rst0000644000000000000000000000010511721773163020170 0ustar rootroot00000000000000stdnum.sk.rc ============ .. automodule:: stdnum.sk.rc :members: python-stdnum-0.9/docs/stdnum.imei.rst0000644000000000000000000000010211721773163020070 0ustar rootroot00000000000000stdnum.imei =========== .. automodule:: stdnum.imei :members: python-stdnum-0.9/docs/stdnum.exceptions.rst0000644000000000000000000000143212154624370021331 0ustar rootroot00000000000000stdnum.exceptions ================= .. automodule:: stdnum.exceptions :show-inheritance: :member-order: bysource :members: The exceptions are organised hierarchically in the following structure: :: ValidationError +-- InvalidFormat | +-- InvalidLength +-- InvalidChecksum +-- InvalidComponent It is possible to change the exception messages by setting the `message` class property. This allows localisation and application-specific error messages. >>> raise InvalidFormat() Traceback (most recent call last): ... InvalidChecksum: The number has an invalid format. >>> InvalidFormat.message = 'UNKNOWN' >>> raise InvalidFormat() Traceback (most recent call last): ... InvalidChecksum: UNKNOWN python-stdnum-0.9/docs/stdnum.dk.cvr.rst0000644000000000000000000000011011721773163020333 0ustar rootroot00000000000000stdnum.dk.cvr ============= .. automodule:: stdnum.dk.cvr :members: python-stdnum-0.9/docs/stdnum.it.iva.rst0000644000000000000000000000011011721773163020336 0ustar rootroot00000000000000stdnum.it.iva ============= .. automodule:: stdnum.it.iva :members: python-stdnum-0.9/docs/stdnum.es.cif.rst0000644000000000000000000000011011721773163020313 0ustar rootroot00000000000000stdnum.es.cif ============= .. automodule:: stdnum.es.cif :members: python-stdnum-0.9/docs/stdnum.gb.vat.rst0000644000000000000000000000011011721773163020325 0ustar rootroot00000000000000stdnum.gb.vat ============= .. automodule:: stdnum.gb.vat :members: python-stdnum-0.9/docs/stdnum.isil.rst0000644000000000000000000000010211721773163020105 0ustar rootroot00000000000000stdnum.isil =========== .. automodule:: stdnum.isil :members: python-stdnum-0.9/docs/stdnum.cz.dic.rst0000644000000000000000000000011011721773163020316 0ustar rootroot00000000000000stdnum.cz.dic ============= .. automodule:: stdnum.cz.dic :members: python-stdnum-0.9/docs/stdnum.imsi.rst0000644000000000000000000000010211721773163020106 0ustar rootroot00000000000000stdnum.imsi =========== .. automodule:: stdnum.imsi :members: python-stdnum-0.9/docs/stdnum.us.atin.rst0000644000000000000000000000011312260533041020514 0ustar rootroot00000000000000stdnum.us.atin ============== .. automodule:: stdnum.us.atin :members: python-stdnum-0.9/docs/stdnum.bg.egn.rst0000644000000000000000000000011011721773163020304 0ustar rootroot00000000000000stdnum.bg.egn ============= .. automodule:: stdnum.bg.egn :members: python-stdnum-0.9/docs/stdnum.grid.rst0000644000000000000000000000010211721773163020072 0ustar rootroot00000000000000stdnum.grid =========== .. automodule:: stdnum.grid :members: python-stdnum-0.9/docs/stdnum.dk.cpr.rst0000644000000000000000000000011011721773163020325 0ustar rootroot00000000000000stdnum.dk.cpr ============= .. automodule:: stdnum.dk.cpr :members: python-stdnum-0.9/docs/stdnum.br.cpf.rst0000644000000000000000000000011011721773163020316 0ustar rootroot00000000000000stdnum.br.cpf ============= .. automodule:: stdnum.br.cpf :members: python-stdnum-0.9/docs/stdnum.se.vat.rst0000644000000000000000000000011011721773163020344 0ustar rootroot00000000000000stdnum.se.vat ============= .. automodule:: stdnum.se.vat :members: python-stdnum-0.9/docs/stdnum.iban.rst0000644000000000000000000000010211721773163020056 0ustar rootroot00000000000000stdnum.iban =========== .. automodule:: stdnum.iban :members: python-stdnum-0.9/docs/index.rst0000644000000000000000000000542512260533270016750 0ustar rootroot00000000000000.. module:: stdnum python-stdnum ============= A Python module to parse, validate and reformat standard numbers and codes in different formats. It contains a large collection of number formats. Basically any number or code that has some validation mechanism available or some common formatting is eligible for inclusion in this library. http://arthurdejong.org/python-stdnum/ Common Interface ---------------- Most of the number format modules implement the following functions: .. function:: validate(number) Validate the number and return a compact, consistent representation of the number or code. If the validation fails, :mod:`an exception <.exceptions>` is raised that indicates the type of error. .. function:: is_valid(number) Return either True or False depending on whether the passed number is in any supported and valid form and passes all embedded checks of the number. This function should never raise an exception. .. function:: compact(number) Return a compact representation of the number or code. This function generally does not do validation but may raise exceptions for wildly invalid numbers. .. function:: format(number) Return a formatted version of the number in the preferred format. This function generally expects to be passed a valid number or code and may raise exceptions for invalid numbers. The check digit modules generally also provide the following functions: .. function:: checksum(number) Calculate the checksum over the provided number. This is generally a number that can be used to determine whether the provided number is valid. It depends on the algorithm which checksum is considered valid. .. function:: calc_check_digit(number) Calculate the check digit that should be added to the number to make it valid. Apart from the above, the modules may add extra parsing, validation or conversion functions. Helper modules -------------- .. autosummary:: :toctree: exceptions Generic check digit algorithms ------------------------------ .. autosummary:: :toctree: iso7064 luhn verhoeff Available formats ----------------- .. autosummary:: :toctree: at.uid be.vat bg.egn bg.pnf bg.vat br.cpf cy.vat cz.dic cz.rc de.vat dk.cpr dk.cvr ean ee.kmkr es.cif es.dni es.nie es.nif eu.vat fi.alv fi.hetu fr.siren fr.tva gb.vat gr.vat grid hr.oib hu.anum iban ie.pps ie.vat imei imsi isan isbn isil ismn issn it.iva lt.pvm lu.tva lv.pvn meid mt.vat my.nric nl.brin nl.bsn nl.btw nl.onderwijsnummer nl.postcode pl.nip pt.nif ro.cf ro.cnp se.vat si.ddv sk.dph sk.rc us.atin us.ein us.itin us.ptin us.ssn us.tin python-stdnum-0.9/docs/stdnum.iso7064.rst0000644000000000000000000000123111721773163020264 0ustar rootroot00000000000000stdnum.iso7064 ============== .. automodule:: stdnum.iso7064 :members: Mod 11, 10 ---------- :mod:`stdnum.iso7064.mod_11_10` .. automodule:: stdnum.iso7064.mod_11_10 :members: Mod 11, 2 --------- :mod:`stdnum.iso7064.mod_11_2` .. automodule:: stdnum.iso7064.mod_11_2 :members: Mod 37, 2 (Mod x, 2) -------------------- :mod:`stdnum.iso7064.mod_37_2` .. automodule:: stdnum.iso7064.mod_37_2 :members: Mod 37, 36 (Mod x+1, x) ----------------------- :mod:`stdnum.iso7064.mod_37_36` .. automodule:: stdnum.iso7064.mod_37_36 :members: Mod 97, 10 ---------- :mod:`stdnum.iso7064.mod_97_10` .. automodule:: stdnum.iso7064.mod_97_10 :members: python-stdnum-0.9/docs/stdnum.my.nric.rst0000644000000000000000000000011312260533041020512 0ustar rootroot00000000000000stdnum.my.nric ============== .. automodule:: stdnum.my.nric :members: python-stdnum-0.9/docs/stdnum.gr.vat.rst0000644000000000000000000000011011721773163020345 0ustar rootroot00000000000000stdnum.gr.vat ============= .. automodule:: stdnum.gr.vat :members: python-stdnum-0.9/docs/stdnum.fi.alv.rst0000644000000000000000000000011011721773163020323 0ustar rootroot00000000000000stdnum.fi.alv ============= .. automodule:: stdnum.fi.alv :members: python-stdnum-0.9/docs/stdnum.bg.vat.rst0000644000000000000000000000011011721773163020325 0ustar rootroot00000000000000stdnum.bg.vat ============= .. automodule:: stdnum.bg.vat :members: python-stdnum-0.9/docs/stdnum.lv.pvn.rst0000644000000000000000000000011011721773163020367 0ustar rootroot00000000000000stdnum.lv.pvn ============= .. automodule:: stdnum.lv.pvn :members: python-stdnum-0.9/docs/stdnum.es.nie.rst0000644000000000000000000000011011721773163020325 0ustar rootroot00000000000000stdnum.es.nie ============= .. automodule:: stdnum.es.nie :members: python-stdnum-0.9/docs/stdnum.hu.anum.rst0000644000000000000000000000011311721773163020522 0ustar rootroot00000000000000stdnum.hu.anum ============== .. automodule:: stdnum.hu.anum :members: python-stdnum-0.9/docs/stdnum.es.nif.rst0000644000000000000000000000011011721773163020326 0ustar rootroot00000000000000stdnum.es.nif ============= .. automodule:: stdnum.es.nif :members: python-stdnum-0.9/docs/stdnum.pl.nip.rst0000644000000000000000000000011011721773163020344 0ustar rootroot00000000000000stdnum.pl.nip ============= .. automodule:: stdnum.pl.nip :members: python-stdnum-0.9/docs/stdnum.cy.vat.rst0000644000000000000000000000011011721773163020350 0ustar rootroot00000000000000stdnum.cy.vat ============= .. automodule:: stdnum.cy.vat :members: python-stdnum-0.9/docs/stdnum.nl.brin.rst0000644000000000000000000000011312260533041020475 0ustar rootroot00000000000000stdnum.nl.brin ============== .. automodule:: stdnum.nl.brin :members: python-stdnum-0.9/docs/stdnum.nl.btw.rst0000644000000000000000000000011011721773163020350 0ustar rootroot00000000000000stdnum.nl.btw ============= .. automodule:: stdnum.nl.btw :members: python-stdnum-0.9/docs/stdnum.us.ein.rst0000644000000000000000000000011012260533041020331 0ustar rootroot00000000000000stdnum.us.ein ============= .. automodule:: stdnum.us.ein :members: python-stdnum-0.9/docs/stdnum.nl.postcode.rst0000644000000000000000000000012712260533041021370 0ustar rootroot00000000000000stdnum.nl.postcode ================== .. automodule:: stdnum.nl.postcode :members: python-stdnum-0.9/docs/stdnum.us.itin.rst0000644000000000000000000000011312260533041020524 0ustar rootroot00000000000000stdnum.us.itin ============== .. automodule:: stdnum.us.itin :members: python-stdnum-0.9/docs/stdnum.isbn.rst0000644000000000000000000000010211721773163020100 0ustar rootroot00000000000000stdnum.isbn =========== .. automodule:: stdnum.isbn :members: python-stdnum-0.9/docs/stdnum.us.ssn.rst0000644000000000000000000000011011721773163020375 0ustar rootroot00000000000000stdnum.us.ssn ============= .. automodule:: stdnum.us.ssn :members: python-stdnum-0.9/docs/stdnum.nl.onderwijsnummer.rst0000644000000000000000000000015411721773163023014 0ustar rootroot00000000000000stdnum.nl.onderwijsnummer ========================= .. automodule:: stdnum.nl.onderwijsnummer :members: python-stdnum-0.9/docs/stdnum.pt.nif.rst0000644000000000000000000000011011721773163020342 0ustar rootroot00000000000000stdnum.pt.nif ============= .. automodule:: stdnum.pt.nif :members: python-stdnum-0.9/docs/stdnum.ro.cf.rst0000644000000000000000000000010511721773163020157 0ustar rootroot00000000000000stdnum.ro.cf ============ .. automodule:: stdnum.ro.cf :members: python-stdnum-0.9/docs/stdnum.be.vat.rst0000644000000000000000000000011011721773163020323 0ustar rootroot00000000000000stdnum.be.vat ============= .. automodule:: stdnum.be.vat :members: python-stdnum-0.9/docs/stdnum.fr.siren.rst0000644000000000000000000000011611721773163020700 0ustar rootroot00000000000000stdnum.fr.siren =============== .. automodule:: stdnum.fr.siren :members: python-stdnum-0.9/docs/stdnum.ie.vat.rst0000644000000000000000000000011011721773163020332 0ustar rootroot00000000000000stdnum.ie.vat ============= .. automodule:: stdnum.ie.vat :members: python-stdnum-0.9/docs/stdnum.ismn.rst0000644000000000000000000000010211721773163020113 0ustar rootroot00000000000000stdnum.ismn =========== .. automodule:: stdnum.ismn :members: python-stdnum-0.9/docs/stdnum.bg.pnf.rst0000644000000000000000000000011011721773163020316 0ustar rootroot00000000000000stdnum.bg.pnf ============= .. automodule:: stdnum.bg.pnf :members: python-stdnum-0.9/docs/stdnum.nl.bsn.rst0000644000000000000000000000011011721773163020336 0ustar rootroot00000000000000stdnum.nl.bsn ============= .. automodule:: stdnum.nl.bsn :members: python-stdnum-0.9/docs/stdnum.hr.oib.rst0000644000000000000000000000011011721773163020325 0ustar rootroot00000000000000stdnum.hr.oib ============= .. automodule:: stdnum.hr.oib :members: python-stdnum-0.9/docs/stdnum.verhoeff.rst0000644000000000000000000000011611721773163020756 0ustar rootroot00000000000000stdnum.verhoeff =============== .. automodule:: stdnum.verhoeff :members: python-stdnum-0.9/docs/stdnum.at.uid.rst0000644000000000000000000000011011721773163020330 0ustar rootroot00000000000000stdnum.at.uid ============= .. automodule:: stdnum.at.uid :members: python-stdnum-0.9/docs/stdnum.luhn.rst0000644000000000000000000000010211721773163020113 0ustar rootroot00000000000000stdnum.luhn =========== .. automodule:: stdnum.luhn :members: python-stdnum-0.9/setup.cfg0000644000000000000000000000051712260536562016004 0ustar rootroot00000000000000[sdist] owner = root group = root [nosetests] with-doctest = true doctest-extension = doctest doctest-options = +IGNORE_EXCEPTION_DETAIL with-coverage = true cover-package = stdnum cover-erase = true cover-html = true cover-html-dir = coverage [build_sphinx] all_files = 1 [egg_info] tag_build = tag_date = 0 tag_svn_revision = 0 python-stdnum-0.9/stdnum/0000755000000000000000000000000012260536561015471 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/ro/0000755000000000000000000000000012260536561016111 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/ro/__init__.py0000644000000000000000000000164111720140726020216 0ustar rootroot00000000000000# __init__.py - collection of Romanian numbers # coding: utf-8 # # Copyright (C) 2012 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of Romanian numbers.""" # provide vat as an alias from stdnum.ro import cf as vat python-stdnum-0.9/stdnum/ro/cf.py0000644000000000000000000000527312154624371017061 0ustar rootroot00000000000000# cf.py - functions for handling Romanian CF (VAT) numbers # coding: utf-8 # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """CF (Cod de înregistrare în scopuri de TVA, Romanian VAT number). The Romanian CF is used for VAT purposes and can be from 2 to 10 digits long. >>> validate('RO 185 472 90') '18547290' >>> validate('185 472 91') Traceback (most recent call last): ... InvalidChecksum: ... >>> validate('1630615123457') # personal code '1630615123457' """ from stdnum.exceptions import * from stdnum.ro import cnp from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, ' -').upper().strip() if number.startswith('RO'): number = number[2:] return number def calc_check_digit(number): """Calculate the check digit for organisations. The number passed should not have the check digit included.""" weights = (7, 5, 3, 2, 1, 7, 5, 3, 2) number = (9 - len(number)) * '0' + number check = 10 * sum(weights[i] * int(n) for i, n in enumerate(number)) return str(check % 11 % 10) def validate(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" number = compact(number) if not number.isdigit() or number[0] == '0': raise InvalidFormat() if len(number) == 13: # apparently a CNP can also be used (however, not all sources agree) cnp.validate(number) elif 2 <= len(number) <= 10: if calc_check_digit(number[:-1]) != number[-1]: raise InvalidChecksum() else: raise InvalidLength() return number def is_valid(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/ro/cnp.py0000644000000000000000000000673412154624371017254 0ustar rootroot00000000000000# cnp.py - functions for handling Romanian CNP numbers # coding: utf-8 # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """CNP (Cod Numeric Personal, Romanian Numerical Personal Code). The CNP is a 13 digit number that includes information on the person's gender, birth date and country zone. >>> validate('1630615123457') '1630615123457' >>> validate('8800101221144') # invalid first digit Traceback (most recent call last): ... InvalidFormat: ... >>> validate('1632215123457') # invalid date Traceback (most recent call last): ... InvalidComponent: ... >>> validate('1630615123458') # invalid check digit Traceback (most recent call last): ... InvalidChecksum: ... """ import datetime from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" return clean(number, ' -').upper().strip() def calc_check_digit(number): """Calculate the check digit for personal codes. The number passed should not have the check digit included.""" # note that this algorithm has not been confirmed by an independent source weights = (2, 7, 9, 1, 4, 6, 3, 5, 8, 2, 7, 9) check = sum(weights[i] * int(n) for i, n in enumerate(number)) % 11 return '1' if check == 10 else str(check) def get_birth_date(number): """Split the date parts from the number and return the birth date.""" centuries = { '1': 1900, '2': 1900, '3': 1800, '4': 1800, '5': 2000, '6': 2000, } # we assume 1900 for the others in order to try to construct a date year = int(number[1:3]) + centuries.get(number[0], 1900) month = int(number[3:5]) day = int(number[5:7]) try: return datetime.date(year, month, day) except ValueError: raise InvalidComponent() def validate(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" number = compact(number) # first digit should be a known one (9=foreigner) if not number.isdigit() or number[0] not in '1234569': raise InvalidFormat() if len(number) != 13: raise InvalidLength() # check if birth date is valid birth_date = get_birth_date(number) # TODO: check that the birth date is not in the future # number[7:9] is the county, we ignore it for now, just check last digit if calc_check_digit(number[:-1]) != number[-1]: raise InvalidChecksum() return number def is_valid(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/luhn.py0000644000000000000000000000525012154624371017012 0ustar rootroot00000000000000# luhn.py - functions for performing the Luhn and Luhn mod N algorithms # # Copyright (C) 2010, 2011, 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """The Luhn and Luhn mod N algorithms. The Luhn algorithm is used to detect most accidental errors in various identification numbers. >>> validate('7894') Traceback (most recent call last): ... InvalidChecksum: ... >>> checksum('7894') 6 >>> calc_check_digit('7894') '9' >>> validate('78949') '78949' An alternative alphabet can be provided to use the Luhn mod N algorithm. The default alphabet is '0123456789'. >>> validate('1234', alphabet='0123456789abcdef') Traceback (most recent call last): ... InvalidChecksum: ... >>> checksum('1234', alphabet='0123456789abcdef') 14 """ from stdnum.exceptions import * def checksum(number, alphabet='0123456789'): """Calculate the Luhn checksum over the provided number. The checksum is returned as an int. Valid numbers should have a checksum of 0.""" n = len(alphabet) number = tuple(alphabet.index(i) for i in reversed(str(number))) return (sum(number[::2]) + sum(sum(divmod(i * 2, n)) for i in number[1::2])) % n def validate(number, alphabet='0123456789'): """Checks to see if the number provided passes the Luhn checksum.""" if not bool(number): raise InvalidFormat() try: valid = checksum(number, alphabet) == 0 except: raise InvalidFormat() if not valid: raise InvalidChecksum() return number def is_valid(number, alphabet='0123456789'): """Checks to see if the number provided passes the Luhn checksum.""" try: return bool(validate(number, alphabet)) except ValidationError: return False def calc_check_digit(number, alphabet='0123456789'): """With the provided number, calculate the extra digit that should be appended to make it pass the Luhn checksum.""" ck = checksum(str(number) + alphabet[0], alphabet) return alphabet[-ck] python-stdnum-0.9/stdnum/dk/0000755000000000000000000000000012260536561016067 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/dk/cpr.py0000644000000000000000000000671212154624370017231 0ustar rootroot00000000000000# cpr.py - functions for handling Danish CPR numbers # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """CPR (personnummer, the Danish citizen number). The CPR is the national number to identify Danish citizens. The number consists of 10 digits in the format DDMMYY-SSSS where the first part represents the birth date and the second a sequence number. The first digit of the sequence number indicates the century. The numbers used to validate using a checksum but since the sequence numbers ran out this was abandoned in 2007. >>> validate('211062-5629') '2110625629' >>> checksum('2110625629') 0 >>> validate('511062-5629') # invalid date Traceback (most recent call last): ... InvalidComponent: ... >>> get_birth_date('2110620629') datetime.date(1962, 10, 21) >>> get_birth_date('2110525629') datetime.date(2052, 10, 21) >>> format('2110625629') '211062-5629' """ import datetime from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" return clean(number, ' -').strip() def checksum(number): """Calculate the checksum. Note that the checksum isn't actually used any more. Valid numbers used to have a checksum of 0.""" weights = (4, 3, 2, 7, 6, 5, 4, 3, 2, 1) return sum(weights[i] * int(n) for i, n in enumerate(number)) % 11 def get_birth_date(number): """Split the date parts from the number and return the birth date.""" day = int(number[0:2]) month = int(number[2:4]) year = int(number[4:6]) if number[6] in '5678' and year >= 58: year += 1800 elif number[6] in '0123' or (number[6] in '49' and year >= 37): year += 1900 else: year += 2000 try: return datetime.date(year, month, day) except ValueError: raise InvalidComponent() def validate(number): """Checks to see if the number provided is a valid CPR number. This checks the length, formatting, embedded date and check digit.""" number = compact(number) if not number.isdigit(): raise InvalidFormat() if len(number) != 10: raise InvalidLength() # check if birth date is valid birth_date = get_birth_date(number) # TODO: check that the birth date is not in the future return number def is_valid(number): """Checks to see if the number provided is a valid CPR number. This checks the length, formatting, embedded date and check digit.""" try: return bool(validate(number)) except ValidationError: return False def format(number): """Reformat the passed number to the standard format.""" number = compact(number) return '-'.join((number[:6], number[6:])) python-stdnum-0.9/stdnum/dk/__init__.py0000644000000000000000000000163611720140741020175 0ustar rootroot00000000000000# __init__.py - collection of Danish numbers # coding: utf-8 # # Copyright (C) 2012 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of Danish numbers.""" # provide vat as an alias from stdnum.dk import cvr as vat python-stdnum-0.9/stdnum/dk/cvr.py0000644000000000000000000000436112154624370017235 0ustar rootroot00000000000000# cvr.py - functions for handling Danish CVR numbers # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """CVR (Momsregistreringsnummer, Danish VAT number). The CVR (Momsregistreringsnummer, VAT) is an 8 digit number with a straightforward check mechanism. >>> validate('DK 13585628') '13585628' >>> validate('DK 13585627') Traceback (most recent call last): ... InvalidChecksum: ... """ from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, ' -.,/:').upper().strip() if number.startswith('DK'): number = number[2:] return number def checksum(number): """Calculate the checksum.""" weights = (2, 7, 6, 5, 4, 3, 2, 1) return sum(weights[i] * int(n) for i, n in enumerate(number)) % 11 def validate(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" number = compact(number) if not number.isdigit() or number[0] == '0': raise InvalidFormat() if len(number) != 8: raise InvalidLength() if checksum(number) != 0: raise InvalidChecksum() return number def is_valid(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/cz/0000755000000000000000000000000012260536561016105 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/cz/rc.py0000644000000000000000000000740712154624370017071 0ustar rootroot00000000000000# rc.py - functions for handling Czech birth numbers # coding: utf-8 # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """RČ (Rodné číslo, the Czech birth number). The birth number (RČ, Rodné číslo) is the Czech national identifier. The number can be 9 or 10 digits long. Numbers given out after January 1st 1954 should have 10 digits. The number includes the birth date of the person and their gender. This number is identical to the Slovak counterpart. >>> validate('710319/2745') '7103192745' >>> validate('991231123') '991231123' >>> validate('7103192746') # invalid check digit Traceback (most recent call last): ... InvalidChecksum: ... >>> validate('1103492745') # invalid date Traceback (most recent call last): ... InvalidComponent: ... >>> validate('590312/123') # 9 digit number in 1959 Traceback (most recent call last): ... InvalidLength: ... >>> format('7103192745') '710319/2745' """ import datetime from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" return clean(number, ' /').upper().strip() def get_birth_date(number): """Split the date parts from the number and return the birth date.""" year = 1900 + int(number[0:2]) # females have 50 added to the month value, 20 is added when the serial # overflows (since 2004) month = int(number[2:4]) % 50 % 20 day = int(number[4:6]) # 9 digit numbers were used until January 1st 1954 if len(number) == 9: if year >= 1980: year -= 100 if year > 1953: raise InvalidLength('No 9 digit birth numbers after 1953.') elif year < 1954: year += 100 try: return datetime.date(year, month, day) except ValueError: raise InvalidComponent() def validate(number): """Checks to see if the number provided is a valid birth number. This checks the length, formatting, embedded date and check digit.""" number = compact(number) if not number.isdigit(): raise InvalidFormat() if len(number) not in (9, 10): raise InvalidLength() # check if birth date is valid birth_date = get_birth_date(number) # TODO: check that the birth date is not in the future # check the check digit (10 digit numbers only) if len(number) == 10: check = int(number[:-1]) % 11 # before 1985 the checksum could be 0 or 10 if birth_date < datetime.date(1985, 1, 1): check = check % 10 if number[-1] != str(check): raise InvalidChecksum() return number def is_valid(number): """Checks to see if the number provided is a valid birth number. This checks the length, formatting, embedded date and check digit.""" try: return bool(validate(number)) except ValidationError: return False def format(number): """Reformat the passed number to the standard format.""" number = compact(number) return number[:6] + '/' + number[6:] python-stdnum-0.9/stdnum/cz/__init__.py0000644000000000000000000000163411720140731020210 0ustar rootroot00000000000000# __init__.py - collection of Czech numbers # coding: utf-8 # # Copyright (C) 2012 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of Czech numbers.""" # provide vat as an alias from stdnum.cz import dic as vat python-stdnum-0.9/stdnum/cz/dic.py0000644000000000000000000000673212154624370017224 0ustar rootroot00000000000000# dic.py - functions for handling Czech VAT numbers # coding: utf-8 # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """DIČ (Daňové identifikační číslo, Czech VAT number). The number is an 8, 9 or 10 digit code that includes a check digit and is used to uniquely identify taxpayers for VAT (DPH in Czech). The number can refer to legal entities (8 digit numbers), individuals with a RČ (the 9 or 10 digit Czech birth number) or individuals without a RČ (9 digit numbers that begin with a 6). >>> compact('CZ 25123891') '25123891' >>> validate('25123891') # legal entity '25123891' >>> validate('25123890') # incorrect check digit Traceback (most recent call last): ... InvalidChecksum: ... >>> validate('7103192745') # RČ '7103192745' >>> validate('640903926') # special case '640903926' """ from stdnum.cz import rc from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, ' /').upper().strip() if number.startswith('CZ'): number = number[2:] return number def calc_check_digit_legal(number): """Calculate the check digit for 8 digit legal entities. The number passed should not have the check digit included.""" check = (11 - sum((8 - i) * int(n) for i, n in enumerate(number))) % 11 return str((check or 1) % 10) def calc_check_digit_special(number): """Calculate the check digit for special cases. The number passed should not have the first and last digits included.""" check = (11 - sum((8 - i) * int(n) for i, n in enumerate(number))) % 11 return str(9 - check % 10) def validate(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" number = compact(number) if not number.isdigit(): raise InvalidFormat() if len(number) == 8: # legal entities if number.startswith('9'): raise InvalidComponent() if calc_check_digit_legal(number[:-1]) != number[-1]: raise InvalidChecksum() elif len(number) == 9 and number.startswith('6'): # special cases (skip first digit in calculation) if calc_check_digit_special(number[1:-1]) != number[-1]: raise InvalidChecksum() elif len(number) in (9, 10): # 9 or 10 digit individual rc.validate(number) else: raise InvalidLength() return number def is_valid(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/imsi.dat0000644000000000000000000062717612260517272017145 0ustar rootroot00000000000000# generated from various sources # https://en.wikipedia.org/w/index.php?title=Mobile_country_code&action=raw 001 01 bands="GSM 900 / GSM 1800" brand="TEST" country="National operators" operator="Test Network" status="Operational" 00-99 202 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Cosmote" cc="gr" country="Greece" operator="COSMOTE - Mobile Telecommunications S.A." status="Operational" 05 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Vodafone" cc="gr" country="Greece" operator="Vodafone Greece" status="Operational" 09 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Wind" cc="gr" country="Greece" operator="Wind Hellas Telecommunications S.A." status="Operational" 10 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Wind" cc="gr" country="Greece" operator="Wind Hellas Telecommunications S.A." status="Operational" 00-99 204 01 cc="nl" country="Netherlands" operator="VastMobiel B.V." status="Non-Operational" 02 bands="LTE 2600" brand="Tele2" cc="nl" country="Netherlands" operator="Tele2 Nederland B.V." status="Operational" 03 bands="MVNE / PrivateGSM 1800" brand="Voiceworks" cc="nl" country="Netherlands" operator="Voiceworks B.V." status="Operational" 04 bands="GSM 900 / GSM 1800 / UMTS 2100 / LTE 1800/2600" brand="Vodafone" cc="nl" country="Netherlands" operator="Vodafone Libertel B.V." status="Operational" 05 cc="nl" country="Netherlands" operator="Elephant Talk Communications Premium Rate Services" 06 brand="Vectone Mobile Delight Mobile" cc="nl" country="Netherlands" operator="Mundio Mobile (Netherlands) Ltd" status="Operational" 07 bands="MVNE" cc="nl" country="Netherlands" operator="Teleena (MVNE)" status="Operational" 08 bands="GSM 900 / GSM 1800 / UMTS 2100 / LTE" brand="KPN" cc="nl" country="Netherlands" operator="KPN Mobile The Netherlands B.V." status="Operational" 09 brand="Lycamobile" cc="nl" country="Netherlands" operator="Lycamobile Netherlands Limited" 10 bands="GSM 900 / GSM 1800 / UMTS 2100 / LTE" brand="KPN" cc="nl" country="Netherlands" operator="KPN B.V." status="Operational" 12 bands="National Roaming Agreement on KPN" brand="Telfort" cc="nl" country="Netherlands" operator="KPN Mobile The Netherlands B.V." status="Operational" 13 cc="nl" country="Netherlands" operator="Unica Installatietechniek B.V." 14 cc="nl" country="Netherlands" operator="6GMOBILE B.V." status="went into Bankruptcy" 15 brand="Ziggo" cc="nl" country="Netherlands" operator="Ziggo B.V." 16 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="T-Mobile (BEN)" cc="nl" country="Netherlands" operator="T-Mobile Netherlands B.V" status="Operational" 17 bands="MVNE" brand="Intercity Zakelijk" cc="nl" country="Netherlands" operator="Intercity Mobile Communications B.V." status="Operational" 18 cc="nl" country="Netherlands" operator="UPC Nederland B.V." 19 cc="nl" country="Netherlands" operator="Mixe Communication Solutions B.V." 20 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="T-Mobile" cc="nl" country="Netherlands" operator="T-Mobile Netherlands B.V" status="Operational" 21 bands="GSM-R 900" cc="nl" country="Netherlands" operator="ProRail B.V." status="Operational" 22 cc="nl" country="Netherlands" operator="Ministerie van Defensie" 23 bands="MVNE" cc="nl" country="Netherlands" operator="ASPIDER Solutions Nederland B.V." status="Operational" 24 cc="nl" country="Netherlands" operator="Private Mobility Nederland B.V." 25 bands="PrivateGSM 1800" cc="nl" country="Netherlands" operator="CapX B.V." status="Operational" 26 cc="nl" country="Netherlands" operator="SpeakUp B.V." 27 cc="nl" country="Netherlands" operator="Breezz Nederland B.V." 28 cc="nl" country="Netherlands" operator="Lancelot B.V." 67 bands="PrivateGSM 1800" cc="nl" country="Netherlands" operator="RadioAccess B.V." status="Operational" 68 cc="nl" country="Netherlands" operator="Unify Group Holding B.V." 69 cc="nl" country="Netherlands" operator="KPN Mobile The Netherlands B.V." 00-99 206 01 bands="GSM 900 / GSM 1800 / UMTS 900 / UMTS 2100 / LTE 1800" brand="Proximus a" cc="be" country="Belgium" operator="Belgacom Mobile" status="Operational" 05 brand="Telenet" cc="be" country="Belgium" operator="Telenet" status="Operational" 10 bands="GSM 900 / GSM 1800 / UMTS 2100 / UMTS 900" brand="Mobistar" cc="be" country="Belgium" operator="Orange S.A." status="Operational" 20 bands="GSM 900 / GSM 1800 / UMTS 900 / UMTS 2100" brand="BASE" cc="be" country="Belgium" operator="KPN Group Belgium" status="Operational" 00-99 208 01 bands="GSM 900 / GSM 1800 / UMTS 2100 / UMTS 900 / LTE" brand="Orange" cc="fr" country="France" operator="Orange S.A." status="Operational" 02 bands="GSM 900 / GSM 1800 / UMTS 2100 / UMTS 900" brand="Orange" cc="fr" country="France" operator="Orange S.A." status="Operational" 03 bands="UMTS" brand="MobiquiThings" cc="fr" country="France" status="Operational" 04 bands="UMTS" brand="Sisteer" cc="fr" country="France" status="Operational" 05 bands="Satellite" cc="fr" country="France" operator="Globalstar Europe" status="Operational" 06 bands="Satellite" cc="fr" country="France" operator="Globalstar Europe" status="Operational" 07 bands="Satellite" cc="fr" country="France" operator="Globalstar Europe" status="Operational" 08 brand="Completel Mobile" cc="fr" country="France" 09 bands="GSM 900 / GSM 1800 / UMTS 2100 / UMTS 900 / LTE" brand="SFR" cc="fr" country="France" operator="Vivendi" status="Operational" 10 bands="GSM 900 / GSM 1800 / UMTS 2100 / UMTS 900 / LTE" brand="SFR" cc="fr" country="France" operator="Vivendi" status="Operational" 11 bands="UMTS 2100" brand="SFR" cc="fr" country="France" operator="Vivendi" status="Operational" 13 bands="GSM 900 / GSM 1800 / UMTS 2100 / UMTS 900" brand="SFR" cc="fr" country="France" operator="Vivendi" status="Operational" 14 bands="GSM-R" brand="RFF" cc="fr" country="France" operator="RFF" status="Operational" 15 bands="UMTS 2100 / UMTS 900" brand="Free Mobile" cc="fr" country="France" operator="Iliad" status="Operational" 16 bands="UMTS 2100 / UMTS 900" brand="Free Mobile" cc="fr" country="France" operator="Iliad" status="Operational" 20 bands="GSM 900 / GSM 1800 / UMTS 2100 / UMTS 900 / LTE" brand="Bouygues" cc="fr" country="France" operator="Bouygues Telecom" status="Operational" 21 bands="GSM 900 / GSM 1800 / UMTS 2100 / UMTS 900" brand="Bouygues" cc="fr" country="France" operator="Bouygues Telecom" status="" 22 bands="" brand="Transatel Mobile" cc="fr" country="France" operator="Transatel" status="" 23 bands="GSM, UMTS" brand="Virgin Mobile (MVNO)" cc="fr" country="France" operator="Omea Telecom" status="Operational" 24 bands="UMTS" brand="MobiquiThings" cc="fr" country="France" status="Operational" 25 bands="GSM 900 / GSM 1800 / UMTS 2100 / UMTS 900" brand="LycaMobile" cc="fr" country="France" operator="LycaMobile" status="Operational" 26 bands="GSM, UMTS" brand="NRJ Mobile (MVNO)" cc="fr" country="France" operator="NRJ Mobile" status="Operational" 88 bands="GSM 900 / GSM 1800" brand="Bouygues" cc="fr" country="France" operator="Bouygues Telecom" status="Operational" 00-99 212 01 bands="GSM 900 / UMTS 2100 / LTE 2600" brand="Office des Telephones" cc="mc" country="Monaco" operator="Monaco Telecom" status="Operational" 00-99 213 03 bands="GSM 900" brand="Mobiland" cc="ad" country="Andorra" operator="Servei De Tele. DAndorra" status="Operational" 00-99 214 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Vodafone" cc="es" country="Spain" operator="Vodafone Spain" status="Operational" 03 bands="GSM 900 / GSM 1800 / UMTS 900 / UMTS 2100" brand="Orange" cc="es" country="Spain" operator="France Telecom España SA" status="Operational" 04 bands="UMTS 2100 / GSM 1800" brand="Yoigo" cc="es" country="Spain" operator="Xfera Moviles SA" status="Operational" 05 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="TME" cc="es" country="Spain" operator="Telefónica Móviles España" status="Operational" 06 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Vodafone" cc="es" country="Spain" operator="Vodafone Spain" status="Operational" 07 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="movistar" cc="es" country="Spain" operator="Telefónica Móviles España" status="Operational" 08 bands="MVNO" brand="Euskaltel" cc="es" country="Spain" status="Operational" 09 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Orange" cc="es" country="Spain" operator="France Telecom España SA" status="Operational" 15 bands="MVNO" brand="BT" cc="es" country="Spain" operator="BT Group España Compañia de Servicios Globales de Telecomunicaciones S.A.U." status="Operational" 16 bands="MVNO" brand="TeleCable" cc="es" country="Spain" operator="Telecable de Asturias S.A.U." status="Operational" 17 bands="MVNO" brand="Móbil R" cc="es" country="Spain" operator="R Cable y Telecomunicaciones Galicia S.A." status="Operational" 18 bands="MVNO" brand="ONO" cc="es" country="Spain" operator="Cableuropa S.A.U." status="Operational" 19 bands="MVNO" brand="Simyo" cc="es" country="Spain" operator="E-PLUS Moviles Virtuales España S.L.U." status="Operational" 20 bands="MVNO" brand="Fonyou" cc="es" country="Spain" operator="Fonyou Telecom S.L." status="Operational" 21 bands="MVNO" brand="Jazztel" cc="es" country="Spain" operator="Jazz Telecom S.A.U." status="Operational" 22 bands="MVNO" brand="DigiMobil" cc="es" country="Spain" operator="Best Spain Telecom" status="Operational" 23 bands="MVNO" brand="Barablu" cc="es" country="Spain" operator="Barablu Móvil España" 24 bands="MVNO" brand="Eroski" cc="es" country="Spain" operator="Eroski Móvil España" status="Operational" 25 bands="MVNO" brand="LycaMobile" cc="es" country="Spain" operator="LycaMobile S.L." status="Operational" 00-99 216 01 bands="GSM 900 / GSM/LTE 1800 / UMTS 2100" brand="Telenor" cc="hu" country="Hungary" operator="Telenor Magyarország Zrt." status="Operational" 30 bands="GSM 900 / GSM/LTE 1800 / UMTS 2100" brand="T-Mobile" cc="hu" country="Hungary" operator="Magyar Telekom Plc" status="Operational" 70 bands="GSM/UMTS 900 / GSM 1800 / UMTS 2100" brand="Vodafone" cc="hu" country="Hungary" operator="Vodafone Magyarország Zrt." status="Operational" 71 bands="" brand="UPC Hungary" cc="hu" country="Hungary" operator="UPC Hungary Ldt" status="Operational" 00-99 218 03 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="HT-ERONET" cc="ba" country="Bosnia and Herzegovina" operator="Public Enterprise Croatian Telecom Ltd." status="Operational" 05 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="m:tel" cc="ba" country="Bosnia and Herzegovina" operator="RS Telecommunications JSC Banja Luka" status="Operational" 90 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="BH Mobile" cc="ba" country="Bosnia and Herzegovina" operator="BH Telecom" status="Operational" 00-99 219 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="T-Mobile" cc="hr" country="Croatia" operator="T-Mobile Croatia" status="Operational" 02 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Tele2" cc="hr" country="Croatia" operator="Tele2" status="Operational" 10 bands="GSM 900 / UMTS 2100" brand="Vip" cc="hr" country="Croatia" operator="Vipnet" status="Operational" 00-99 220 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Telenor" cc="rs" country="Serbia" operator="Telenor Serbia" status="Operational" 02 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Telenor" cc="rs" country="Serbia" operator="Telenor Montenegro" status="Not operational" 03 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="mt:s" cc="rs" country="Serbia" operator="Telekom Srbija" status="Operational" 05 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="VIP" cc="rs" country="Serbia" operator="VIP Mobile" status="Operational" 00-99 222 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="TIM" cc="it" country="Italy" operator="Telecom Italia SpA" status="Operational" 02 bands="Satellite (Globalstar)" brand="Elsacom" cc="it" country="Italy" status="Not operational" 04 brand="Intermatica" cc="it" country="Italy" 05 brand="Telespazio" cc="it" country="Italy" 07 bands="MVNO" brand="Noverca" cc="it" country="Italy" status="Operational" 10 bands="GSM 900 / GSM 1800 / UMTS 900 & 2100" brand="Vodafone" cc="it" country="Italy" operator="Vodafone Omnitel N.V." status="Operational" 30 bands="GSM-R 900" brand="RFI" cc="it" country="Italy" operator="Rete Ferroviaria Italiana" status="Operational" 35 bands="MVNO" brand="Lyca Italy" cc="it" country="Italy" operator="Lyca Mobile" status="Planned" 77 bands="UMTS 2100" brand="IPSE 2000" cc="it" country="Italy" status="Not operational" 88 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Wind" cc="it" country="Italy" operator="Wind Telecomunicazioni SpA" status="Operational" 98 bands="GSM 1800" brand="Blu" cc="it" country="Italy" status="Not operational" 99 bands="UMTS 2100" brand="3 Italia" cc="it" country="Italy" operator="Hutchison 3G" status="Operational" 00-99 226 01 bands="GSM 900/1800
    UMTS 900/2100
    LTE 1800" brand="Vodafone" cc="ro" country="Romania" operator="Vodafone România" status="Operational" 02 bands="CDMA 420" brand="Romtelecom" cc="ro" country="Romania" operator="Romtelecom" status="Operational" 03 bands="GSM 900/1800
    LTE 1800" brand="Cosmote" cc="ro" country="Romania" operator="Cosmote România" status="Operational" 04 bands="CDMA 450" brand="Cosmote/Zapp" cc="ro" country="Romania" operator="Cosmote România" status="Not operational" 05 bands="UMTS 2100" brand="Digi.Mobil" cc="ro" country="Romania" operator="RCS&RDS" status="Operational" 06 bands="UMTS 2100" brand="Cosmote/Zapp" cc="ro" country="Romania" operator="Cosmote România" status="Operational" 10 bands="GSM 900/1800
    UMTS 900/2100
    LTE 1800" brand="Orange" cc="ro" country="Romania" operator="Orange România" status="Operational" 00-99 228 01 bands="GSM 900 / GSM / LTE 1800 / UMTS 2100" brand="Swisscom" cc="ch" country="Switzerland" operator="Swisscom Ltd" status="Operational" 02 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Sunrise" cc="ch" country="Switzerland" operator="Sunrise Communications AG" status="Operational" 03 bands="GSM 1800 / UMTS 2100" brand="Orange" cc="ch" country="Switzerland" operator="Orange Communications SA" status="Operational" 05 bands="" cc="ch" country="Switzerland" operator="Togewanet AG (Comfone)" status="Reserved" 06 bands="GSM-R 900" brand="SBB-CFF-FFS" cc="ch" country="Switzerland" operator="SBB AG" status="Operational" 07 bands="GSM 1800" brand="IN&Phone" cc="ch" country="Switzerland" operator="IN&Phone SA" status="Operational" 08 bands="GSM 1800" brand="Tele4u" cc="ch" country="Switzerland" operator="TelCommunication Services AG" status="Operational" 09 bands="Roaming Hub" cc="ch" country="Switzerland" operator="Comfone" status="Inactive" 12 cc="ch" country="Switzerland" operator="Sunrise" status="Inactive" 50 bands="UMTS 2100" cc="ch" country="Switzerland" operator="3G Mobile AG" status="Reserved" 51 bands="MVNO" cc="ch" country="Switzerland" operator="BebbiCell AG" status="Operational" 52 brand="Barablu" cc="ch" country="Switzerland" operator="Barablu" 53 cc="ch" country="Switzerland" operator="UPC" status="Inactive" 54 bands="MVNO" cc="ch" country="Switzerland" operator="Lyca Mobile" status="Operational" 00-99 230 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="T-Mobile" cc="cy" country="Cyprus" operator="T-Mobile Czech Republic" status="Operational" 02 bands="CDMA2000 450 / GSM 900 / GSM 1800 / UMTS 2100" brand="O2" cc="cy" country="Cyprus" operator="Telefónica Czech Republic" status="Operational" 03 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Vodafone" cc="cy" country="Cyprus" operator="Vodafone Czech Republic" status="Operational" 04 bands="CDMA2000 410 - 430" brand="U:fon" cc="cy" country="Cyprus" operator="Air Telecom a. s." status="Operational" 05 cc="cy" country="Cyprus" operator="TRAVEL TELEKOMMUNIKATION, s.r.o." status="unknown" 06 cc="cy" country="Cyprus" operator="OSNO TELECOMUNICATION, s.r.o." status="unknown" 07 bands="MVNO" cc="cy" country="Cyprus" operator="ASTELNET, s.r.o." status="Operational" 98 bands="GSM-R 900" cc="cy" country="Cyprus" operator="Správa železniční dopravní cesty, s.o." status="Operational" 99 bands="GSM 1800" brand="Vodafone" cc="cy" country="Cyprus" operator="Vodafone Czech Republic" status="Operational" 00-99 231 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Orange" cc="sk" country="Slovakia" operator="Orange Slovensko" status="Operational" 02 bands="GSM 900 / GSM 1800" brand="Telekom" cc="sk" country="Slovakia" operator="Slovak Telekom" status="Operational" 03 bands="" cc="sk" country="Slovakia" operator="Unient Communications" status="" 04 bands="UMTS 2100" brand="T-Mobile" cc="sk" country="Slovakia" operator="T-Mobile Slovensko" status="Operational" 06 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="O2" cc="sk" country="Slovakia" operator="Telefónica O2 Slovakia" status="Operational" 99 bands="GSM-R" brand="ŽSR" cc="sk" country="Slovakia" operator="Železnice Slovenskej Republiky" status="Operational" 00-99 232 01 bands="GSM / UMTS / LTE 2600" brand="A1 TA" country="Austria - AT" operator="A1 Telekom Austria" status="operational network" 02 country="Austria - AT" operator="A1 Telekom Austria" status="reserved" 03 bands="GSM / UMTS / LTE 2600" brand="T-Mobile AT" country="Austria - AT" operator="T-Mobile Austria" status="operational network" 05 bands="GSM / UMTS" brand="Orange AT" country="Austria - AT" operator="Hutchison Drei Austria" status="operational network" 07 brand="tele.ring" country="Austria - AT" operator="T-Mobile Austria" status="MVNE / MNVO" 08 country="Austria - AT" status="MNVO / not active" 09 brand="Tele2Mobil" country="Austria - AT" operator="A1 Telekom Austria" status="MVNO as of Nov. 2013" 10 bands="UMTS / LTE" brand="3AT" country="Austria - AT" operator="Hutchison Drei Austria" status="operational network" 11 brand="bob" country="Austria - AT" operator="A1 Telekom Austria" status="MVNO" 12 brand="yesss!" country="Austria - AT" operator="A1 Telekom Austria" status="MNVE / MVNO" 13 country="Austria - AT" status="MNVO / not active" 14 country="Austria - AT" operator="Hutchison Drei Austria" status="reserved" 15 brand="Vectone" country="Austria - AT" operator="A1 Telekom Austria" status="MNVO" 16 country="Austria - AT" operator="Hutchison Drei Austria" status="reserved" 91 bands="GSM-R" brand="GSM-R A" country="Austria - AT" operator="ÖBB" status="operational network" 00-99 234 00 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="BT" cc="gb" country="United Kingdom" operator="BT Group" status="Operational" 01 bands="GSM 1800" brand="Vectone Mobile" cc="gb" country="United Kingdom" operator="Mundio Mobile Limited" status="Operational" 02 bands="GSM 900 / GSM 1800 / UMTS 2100 & 900" brand="O2 (UK)" cc="gb" country="United Kingdom" operator="Telefónica Europe" status="Operational" 03 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Airtel-Vodafone" cc="gb" country="United Kingdom" operator="Jersey Airtel Limited" status="Operational" 04 bands="GSM 1800" brand="FMS Solutions Ltd" cc="gb" country="United Kingdom" operator="FMS Solutions Ltd" status="Reserved" 05 cc="gb" country="United Kingdom" operator="COLT Mobile Telecommunications Limited" 06 cc="gb" country="United Kingdom" operator="Internet Computer Bureau Limited" 07 bands="GSM 1800" cc="gb" country="United Kingdom" operator="Cable & Wireless Worldwide" status="Operational" 08 cc="gb" country="United Kingdom" operator="OnePhone (UK) Ltd" 09 bands="GSM 900/1800" brand="Sure Mobile" cc="gb" country="United Kingdom" operator="Tismi BV" status="Operational" 10 bands="GSM 900 / GSM 1800 / UMTS 2100 & 900" brand="O2 (UK)" cc="gb" country="United Kingdom" operator="Telefónica Europe" status="Operational" 11 bands="GSM 900 / GSM 1800 / UMTS 2100 & 900" brand="O2 (UK)" cc="gb" country="United Kingdom" operator="Telefónica Europe" status="Operational" 12 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Railtrack" cc="gb" country="United Kingdom" operator="Network Rail Infrastructure Ltd" status="Operational" 13 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Railtrack" cc="gb" country="United Kingdom" operator="Network Rail Infrastructure Ltd" status="Operational" 14 bands="GSM 1800" brand="Hay Systems Ltd" cc="gb" country="United Kingdom" operator="Hay Systems Ltd" status="Operational" 15 bands="GSM 900 / GSM 1800 / UMTS 2100 & 900" brand="Vodafone UK" cc="gb" country="United Kingdom" operator="Vodafone" status="Operational" 16 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Talk Talk (Opal Tel Ltd)" cc="gb" country="United Kingdom" operator="TalkTalk Communications Limited" status="Operational" 17 cc="gb" country="United Kingdom" operator="FleXtel Limited" 18 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Cloud9" cc="gb" country="United Kingdom" operator="Cloud9" status="Operational" 19 bands="GSM 1800" brand="Private Mobile Networks PMN" cc="gb" country="United Kingdom" operator="Teleware plc" status="Operational" 20 bands="UMTS 2100" brand="3" cc="gb" country="United Kingdom" operator="Hutchison 3G UK Ltd" status="Operational" 22 bands="" brand="RoutoMessaging" cc="gb" country="United Kingdom" operator="Routo Telecommunications Limited" status="Operational" 24 bands="" brand="Greenfone" cc="gb" country="United Kingdom" operator="Stour Marine" status="Operational" 25 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Truphone" cc="gb" country="United Kingdom" operator="Truphone" status="Operational" 26 brand="Lycamobile" cc="gb" country="United Kingdom" status="Operational" 27 bands="GSM 900 / GSM 1800 / UMTS 2100" cc="gb" country="United Kingdom" operator="Teleena UK Limited" status="Operational" 30 bands="GSM 1800 / UMTS 2100" brand="T-Mobile UK" cc="gb" country="United Kingdom" operator="EE" status="Operational" 31 bands="GSM 1800 / UMTS 2100" brand="Virgin Mobile UK" cc="gb" country="United Kingdom" operator="Virgin Media" status="Operational" 32 bands="GSM 1800 / UMTS 2100" brand="Virgin Mobile UK" cc="gb" country="United Kingdom" operator="Virgin Media" status="Operational" 33 bands="GSM 1800 / UMTS 2100" brand="Orange (UK)" cc="gb" country="United Kingdom" operator="EE" status="Operational" 34 bands="GSM 1800 / UMTS 2100" brand="Orange (UK)" cc="gb" country="United Kingdom" operator="EE" status="Operational" 35 cc="gb" country="United Kingdom" operator="JSC Ingenium (UK) Limited" 36 cc="gb" country="United Kingdom" operator="Cable and Wireless Isle of Man Limited" 37 cc="gb" country="United Kingdom" operator="Synectiv Ltd" 50 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="JT" cc="gb" country="United Kingdom" operator="JT Group Limited" status="Operational" 51 bands="TD-LTE" brand="UK Broadband Limited" cc="gb" country="United Kingdom" operator="UK Broadband Limited" status="Operational" 55 bands="GSM 900 (Guernsey) / GSM 1800 (Jersey) / UMTS 2100" brand="Sure Mobile" cc="gb" country="United Kingdom" operator="Cable & Wireless Guernsey / Sure Mobile (Jersey)" status="Operational" 58 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Pronto GSM" cc="gb" country="United Kingdom" operator="Manx Telecom" status="Operational" 76 bands="GSM 900 / GSM 1800" brand="BT" cc="gb" country="United Kingdom" operator="BT Group" status="Operational" 78 bands="TETRA" brand="Airwave" cc="gb" country="United Kingdom" operator="Airwave (communications network)" status="Operational" 00-99 235 00 cc="gb" country="United Kingdom" operator="Mundio Mobile Limited" 01 cc="gb" country="United Kingdom" operator="EE" 02 cc="gb" country="United Kingdom" operator="EE" 77 brand="BT" cc="gb" country="United Kingdom" operator="BT Group" 91 cc="gb" country="United Kingdom" operator="Vodafone United Kingdom" 92 cc="gb" country="United Kingdom" operator="Cable & Wireless UK" 94 cc="gb" country="United Kingdom" operator="Hutchison 3G UK Ltd" 95 cc="gb" country="United Kingdom" operator="Network Rail Infrastructure Limited" 00-99 238 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="TDC" cc="dk" country="Denmark" operator="TDC A/S" status="Operational" 02 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Telenor" cc="dk" country="Denmark" operator="Telenor Denmark" status="Operational" 03 bands="" brand="End2End" cc="dk" country="Denmark" operator="MIGway A/S" status="Reserved" 05 bands="" cc="dk" country="Denmark" operator="ApS KBUS" status="Reserved" 06 bands="UMTS 2100" brand="3" cc="dk" country="Denmark" operator="Hi3G Denmark ApS" status="Operational" 07 bands="" cc="dk" country="Denmark" operator="Barablu Mobile Ltd." status="Reserved" 08 bands="" brand="Nordisk Mobiltelefon" cc="dk" country="Denmark" status="" 09 bands="-" cc="dk" country="Denmark" operator="Dansk Beredskabskommunikation A/S" status="" 10 bands="" brand="TDC" cc="dk" country="Denmark" operator="TDC A/S" status="Operational" 11 bands="" cc="dk" country="Denmark" operator="Dansk Beredskabskommunikation A/S" status="" 12 bands="" cc="dk" country="Denmark" operator="Lycamobile Denmark Ltd" status="" 20 bands="GSM 900 / GSM 1800" brand="Telia" cc="dk" country="Denmark" status="Operational" 23 bands="GSM-R" brand="GSM-R DK" cc="dk" country="Denmark" operator="Banedanmark" status="Operational" 30 bands="GSM 900 / GSM 1800" brand="Telia" cc="dk" country="Denmark" operator="Telia Nättjänster Norden AB" status="Operational" 40 bands="" cc="dk" country="Denmark" operator="Ericsson Danmark A/S" status="" 77 bands="GSM 900 / GSM 1800" brand="Telenor" cc="dk" country="Denmark" operator="Telenor Denmark" status="Operational" 00-99 240 01 bands="GSM 900 / GSM 1800" brand="Telia" cc="se" country="Sweden" operator="TeliaSonera Sverige AB" status="Operational" 02 bands="UMTS 900 / UMTS 2100" brand="3" cc="se" country="Sweden" operator="HI3G Access AB" status="Operational" 03 bands="CDMA2000 450" brand="Ice.net" cc="se" country="Sweden" operator="Netett Sverige AB" status="Operational" 04 bands="UMTS 2100" brand="SWEDEN" cc="se" country="Sweden" operator="3G Infrastructure Services AB" status="Operational" 05 bands="UMTS 2100" brand="Sweden 3G" cc="se" country="Sweden" operator="Svenska UMTS-Nät AB" status="Operational" 06 bands="UMTS 2100" brand="Telenor" cc="se" country="Sweden" operator="Telenor Sverige AB" status="Operational" 07 bands="GSM 900 / GSM 1800 (Now merged with Telenor into Net4Mobility)" brand="Tele2" cc="se" country="Sweden" operator="Tele2 Sverige AB" status="Inactive" 08 bands="GSM 900 / GSM 1800" brand="Telenor" cc="se" country="Sweden" operator="Telenor Sverige AB" status="Operational" 09 bands="GSM 900 / GSM 1800" brand="djuice" cc="se" country="Sweden" operator="Djuice Mobile Sweden, filial till Telenor Mobile Sweden AS" status="Inactive" 10 bands="Only used on femto- and nanocells" brand="Spring Mobil" cc="se" country="Sweden" operator="Spring Mobil AB" status="Operational" 11 bands="" cc="se" country="Sweden" operator="Lindholmen Science Park AB" status="" 12 bands="" brand="Lycamobile Sweden" cc="se" country="Sweden" operator="Lycamobile Sweden Limited" status="" 13 bands="" cc="se" country="Sweden" operator="Alltele Företag Sverige AB" status="" 14 bands="GSM 900 / GSM 1800 / UMTS 2100" cc="se" country="Sweden" operator="TDC Sverige AB" status="Inactive" 15 bands="GSM 900 / GSM 1800 / UMTS 2100" cc="se" country="Sweden" operator="Wireless Maingate Nordic AB" status="Operational" 16 bands="GSM" cc="se" country="Sweden" operator="42 Telecom AB" status="Operational" 17 bands="" brand="Gotanet" cc="se" country="Sweden" operator="Götalandsnätet AB" status="" 18 bands="" cc="se" country="Sweden" operator="Generic Mobile Systems Sweden AB" status="" 19 bands="" cc="se" country="Sweden" operator="Mundio Mobile (Sweden) Limited" status="" 20 bands="GSM" cc="se" country="Sweden" operator="Wireless Maingate Messaging Services AB" status="Operational" 21 bands="GSM-R 900" brand="MobiSir" cc="se" country="Sweden" operator="Trafikverket ICT" status="Operational" 22 bands="" cc="se" country="Sweden" operator="EuTel AB" status="" 23 bands="" cc="se" country="Sweden" operator="Infobip Limited" status="Operational" 24 bands="GSM 900 / LTE 2600/900/1800 (LTE1800 only available in major cities)" brand="Sweden 2G" cc="se" country="Sweden" operator="Net4Mobility HB" status="Operational" 25 bands="" cc="se" country="Sweden" operator="Digitel Mobile Srl" status="" 26 bands="GSM" cc="se" country="Sweden" operator="Beepsend AB" status="Operational" 27 bands="" cc="se" country="Sweden" operator="Fogg Mobile AB" status="" 28 bands="" cc="se" country="Sweden" operator="CoolTEL Aps" status="" 29 bands="" cc="se" country="Sweden" operator="Mercury International Carrier Services" status="" 30 bands="" cc="se" country="Sweden" operator="NextGen Mobile Ltd." status="" 31 bands="" cc="se" country="Sweden" operator="Mobimax AB" status="" 32 bands="" cc="se" country="Sweden" operator="Compatel Limited" status="" 33 bands="" cc="se" country="Sweden" operator="Mobile Arts AB" status="" 34 bands="" cc="se" country="Sweden" operator="Tigo LTD." status="" 35 bands="" cc="se" country="Sweden" operator="42 Telecom LTD" status="" 36 bands="" cc="se" country="Sweden" operator="interactive digital media GmbH" status="" 37 bands="" cc="se" country="Sweden" operator="CLX Networks AB" status="Operational" 38 bands="" cc="se" country="Sweden" operator="Voxbone SA" status="" 40 bands="" cc="se" country="Sweden" operator="ReWiCom Scandinavia AB" status="" 41 bands="" cc="se" country="Sweden" operator="Shyam Telecom UK Ltd." status="" 42 bands="" cc="se" country="Sweden" operator="Telenor Connexion AB" status="" 00-99 242 01 bands="GSM 900 / GSM 1800 / UMTS 900 / UMTS 2100" brand="Telenor" cc="no" country="Norway" status="Operational" 02 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="NetCom" cc="no" country="Norway" operator="NetCom GSM" status="Operational" 03 brand="Teletopia" cc="no" country="Norway" operator="Teletopia" status="Not operational" 04 bands="MNO" brand="Tele2" cc="no" country="Norway" operator="Tele2(Mobile Norway AS)" status="Operational" 05 bands="UMTS 900 / UMTS 2100" brand="Network Norway" cc="no" country="Norway" operator="Tele2(Mobile Norway AS)" status="Operational" 06 bands="CDMA2000 450" brand="Ice" cc="no" country="Norway" operator="Nordisk Mobiltelefon" status="Operational" 07 bands="MVNO of Telenor NO" brand="Ventelo" cc="no" country="Norway" operator="Ventelo AS" status="Operational" 08 bands="MVNO" brand="TDC" cc="no" country="Norway" operator="TDC Mobil AS" status="Operational" 09 bands="MVNO" brand="Com4" cc="no" country="Norway" operator="Com4 AS" status="Operational" 11 bands="Test" brand="SystemNet" cc="no" country="Norway" operator="SystemNet AS" status="" 20 bands="GSM-R 900" cc="no" country="Norway" operator="Jernbaneverket AS" status="Operational" 23 bands="MVNO" brand="Lyca" cc="no" country="Norway" operator="Lyca Mobile Ltd" status="Operational" 00-99 244 03 bands="GSM 1800" brand="DNA" cc="fi" country="Finland" operator="DNA Oy" status="Operational" 04 bands="MVNO" brand="AINA" cc="fi" country="Finland" operator="DNA Oy / Aina Oyj" status="Operational" 05 bands="GSM 900 / GSM 1800 / UMTS 900 / UMTS 2100 / LTE 1800 / LTE 2600" brand="Elisa" cc="fi" country="Finland" operator="Elisa Oyj" status="Operational" 07 bands="GSM 900 / GSM 1800" brand="Nokia" cc="fi" country="Finland" operator="Nokia Test Network" status="Not operational" 08 bands="GSM 1800 / UMTS 2100" brand="Nokia" cc="fi" country="Finland" operator="Nokia Test Network" status="Not Operational" 09 bands="GSM 900" brand="Finnet Group / Nokia Solutions and Networks" cc="fi" country="Finland" operator="Global Network" status="Not Operational" 10 bands="MVNO" brand="TDC" cc="fi" country="Finland" operator="TDC Oy" status="Operational" 11 bands="MVNO" brand="Vectone Mobile" cc="fi" country="Finland" operator="Mundio Mobile Oy" status="Operational" 12 bands="GSM 900 / GSM 1800 / UMTS 900 / UMTS 2100 / LTE 1800 / LTE 2600" brand="DNA" cc="fi" country="Finland" operator="DNA Oy" status="Operational" 13 bands="GSM 900 / GSM 1800" brand="DNA" cc="fi" country="Finland" operator="DNA Oy" status="Not Operational" 14 bands="GSM 900 / GSM 1800 / UMTS 900 / UMTS 2100" brand="AMT" cc="fi" country="Finland" operator="Ålands Telekommunikation Ab / Ålands Mobiltelefon" status="Operational" 15 bands="GSM 900" brand="SAMK" cc="fi" country="Finland" operator="Samk Student Test Network" status="Not Operational" 21 bands="MVNO" brand="Saunalahti" cc="fi" country="Finland" operator="Elisa Oyj" status="Operational" 25 bands="MVNO" brand="Datame" cc="fi" country="Finland" operator="Datame Oy" status="Operational" 26 bands="MVNO" brand="Compatel" cc="fi" country="Finland" operator="Compatel Ltd" status="Operational" 30 bands="MVNO" brand="Vectone Mobile" cc="fi" country="Finland" operator="Mundio Mobile Oy" status="Operational" 31 bands="MVNO" brand="Ukko Mobile" cc="fi" country="Finland" operator="Ukko Mobile Oy" status="Operational" 91 bands="GSM 900 / GSM 1800 / UMTS 900 / UMTS 2100 / LTE 1800 / LTE 2600" brand="Sonera" cc="fi" country="Finland" operator="TeliaSonera Finland Oyj" status="Operational" 00-99 246 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Omnitel" cc="lt" country="Lithuania" status="Operational" 02 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="BITĖ" cc="lt" country="Lithuania" operator="UAB Bitė Lietuva" status="Operational" 03 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Tele 2" cc="lt" country="Lithuania" status="Operational" 05 bands="GSM-R 900" brand="LitRail" cc="lt" country="Lithuania" operator="Lithuanian Railways" status="Operational" 06 bands="GSM 1800" brand="Mediafon" cc="lt" country="Lithuania" operator="UAB Mediafon" status="Operational" 00-99 247 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="LMT" cc="lv" country="Latvia" operator="Latvian Mobile Telephone" status="Operational" 02 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Tele2" cc="lv" country="Latvia" operator="Tele2" status="Operational" 03 bands="CDMA2000 450" brand="TRIATEL" cc="lv" country="Latvia" operator="Telekom Baltija" status="Operational" 05 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Bite" cc="lv" country="Latvia" operator="Bite Latvija" status="Operational" 06 bands="" cc="lv" country="Latvia" operator="Rigatta" status="Reserved" 07 bands="MVNO" brand="MTS" cc="lv" country="Latvia" operator="Master Telecom" status="Operational" 08 bands="MVNO" brand="IZZI" cc="lv" country="Latvia" operator="IZZI" status="Operational" 09 bands="MVNO" brand="Camel Mobile" cc="lv" country="Latvia" operator="Camel Mobile" status="Operational" 00-99 248 01 bands="GSM 900 / GSM 1800 / UMTS 900 / UMTS 2100/ LTE 1800 / LTE 2600" brand="EMT" cc="ee" country="Estonia" operator="Estonian Mobile Telecom" status="Operational" 02 bands="GSM 900 / GSM 1800 / UMTS 900 / UMTS 2100" brand="Elisa" cc="ee" country="Estonia" operator="Elisa Eesti" status="Operational" 03 bands="GSM 900 / GSM 1800 / UMTS 900 / UMTS 2100 / LTE" brand="Tele 2" cc="ee" country="Estonia" operator="Tele 2 Eesti" status="Operational" 04 bands="MVNO" cc="ee" country="Estonia" operator="OY Top Connect" status="Operational" 05 bands="" cc="ee" country="Estonia" operator="AS Bravocom Mobiil" status="" 06 bands="UMTS 2100" cc="ee" country="Estonia" operator="Progroup Holding" status="Operational" 08 bands="MVNO" brand="VIVEX" cc="ee" country="Estonia" operator="VIVEX OU" status="Operational" 00-99 250 01 bands="GSM 900 / GSM 1800 / UMTS 900 / UMTS 2100 / TD-LTE 2600 (test)" brand="MTS" cc="ru" country="Russian Federation" operator="Mobile TeleSystems" status="Operational" 02 bands="GSM 900 / GSM 1800 / UMTS 900 / UMTS 2100/ TD-LTE 2600" brand="MegaFon" cc="ru" country="Russian Federation" operator="MegaFon OJSC - previously known as North-West GSM" status="Operational" 03 bands="GSM 900 / GSM 1800" brand="NCC" cc="ru" country="Russian Federation" operator="Nizhegorodskaya Cellular Communications" status="Operational" 04 bands="GSM 900" brand="Sibchallenge" cc="ru" country="Russian Federation" operator="Sibchallenge" status="Not operational" 05 bands="GSM 900 / GSM 1800 / UMTS 2100 / CDMA2000 450" brand="ETK" cc="ru" country="Russian Federation" operator="Yeniseytelecom" status="Operational" 06 bands="CDMA2000 450" brand="Skylink" cc="ru" country="Russian Federation" operator="CJSC Saratov System of Cellular Communications" status="Operational" 07 bands="GSM 900 / GSM 1800" brand="SMARTS" cc="ru" country="Russian Federation" operator="Zao SMARTS" status="Operational" 09 bands="CDMA2000 450" brand="Skylink" cc="ru" country="Russian Federation" operator="Khabarovsky Cellular Phone" status="Operational" 10 bands="GSM 900" brand="DTC" cc="ru" country="Russian Federation" operator="Dontelekom" status="Not operational" 11 bands="LTE 2600" brand="Yota" cc="ru" country="Russian Federation" operator="Scartel" status="Operational" 12 bands="GSM 1800" brand="Akos" cc="ru" country="Russian Federation" operator="Baykal Westcom / New Telephone Company / Far Eastern Cellular" status="Operational" 13 bands="GSM 900 / GSM 1800" brand="KUGSM" cc="ru" country="Russian Federation" operator="Kuban GSM" status="Not operational" 14 bands="GSM 900 / GSM 1800 / UMTS 900 / UMTS 2100/ TD-LTE 2600" brand="MegaFon" cc="ru" country="Russian Federation" operator="MegaFon OJSC" status="Operational" 15 bands="GSM 1800" brand="SMARTS" cc="ru" country="Russian Federation" operator="SMARTS Ufa, SMARTS Uljanovsk" status="Operational" 16 bands="GSM 900 / GSM 1800" brand="NTC" cc="ru" country="Russian Federation" operator="New Telephone Company" status="Operational" 17 bands="GSM 900 / GSM 1800" brand="Utel" cc="ru" country="Russian Federation" operator="JSC Uralsvyazinform" status="Operational" 18 bands="TD-LTE 2300" brand="Osnova Telecom" cc="ru" country="Russian Federation" status="Not operational" 19 bands="GSM 1800" brand="INDIGO" cc="ru" country="Russian Federation" operator="INDIGO" status="Not operational" 20 bands="GSM 900 / GSM 1800" brand="Tele2" cc="ru" country="Russian Federation" operator="Tele2" status="Operational" 23 bands="GSM 900 / GSM 1800" brand="Mobicom - Novosibirsk" cc="ru" country="Russian Federation" operator="Mobicom - Novosibirsk" status="Not operational" 28 bands="GSM 900" brand="Beeline" cc="ru" country="Russian Federation" operator="Beeline" status="Not operational" 35 bands="GSM 1800" brand="MOTIV" cc="ru" country="Russian Federation" operator="EKATERINBURG-2000" status="Operational" 38 bands="GSM 900 / GSM 1800" brand="Tambov GSM" cc="ru" country="Russian Federation" operator="Central Telecommunication Company" status="Operational" 39 bands="GSM 900 / GSM 1800 /UMTS 2100" brand="Rostelecom" cc="ru" country="Russian Federation" operator="ROSTELECOM" status="Operational" 44 bands="" cc="ru" country="Russian Federation" operator="Stavtelesot / North Caucasian GSM" status="Not operational" 50 bands="GSM 900 / GSM 1800" brand="MTS" cc="ru" country="Russian Federation" operator="Bezlimitno.ru" status="Operational" 91 bands="GSM 1800" brand="Sonic Duo" cc="ru" country="Russian Federation" operator="Sonic Duo CJSC" status="Not operational" 92 bands="" cc="ru" country="Russian Federation" operator="Primtelefon" status="Not operational" 93 bands="" cc="ru" country="Russian Federation" operator="Telecom XXI" status="Not operational" 99 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Beeline" cc="ru" country="Russian Federation" operator="OJSC Vimpel-Communications" status="Operational" 00-99 255 01 bands="GSM 900 / GSM 1800 / CDMA 450" brand="MTS" cc="ua" country="Ukraine" operator="MTS Ukraine" status="Operational" 02 bands="GSM 900 / GSM 1800" brand="Beeline" cc="ua" country="Ukraine" operator="Kyivstar GSM JSC" status="Operational" 03 bands="GSM 900 / GSM 1800" brand="Kyivstar" cc="ua" country="Ukraine" operator="Kyivstar GSM JSC" status="Operational" 04 bands="CDMA 800" brand="IT" cc="ua" country="Ukraine" operator="Intertelecom" status="Operational" 05 bands="GSM 1800" brand="Golden Telecom" cc="ua" country="Ukraine" operator="Kyivstar GSM JSC" status="Operational" 06 bands="GSM 900 / GSM 1800" brand="life:)" cc="ua" country="Ukraine" operator="Astelit" status="Operational" 07 bands="UMTS 2100" brand="3Mob" cc="ua" country="Ukraine" operator="3Mob (Ukrtelecom UMTS )" status="Operational" 21 bands="CDMA 800" brand="PEOPLEnet" cc="ua" country="Ukraine" operator="Telesystems of Ukraine" status="Operational" 23 bands="CDMA 800" brand="CDMA Ukraine" cc="ua" country="Ukraine" operator="Intertelecom" status="Operational" 25 bands="CDMA 800" brand="NEWTONE" cc="ua" country="Ukraine" operator="CST Invest" status="Operational" 00-99 257 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="velcom" cc="by" country="Belarus" status="Operational" 02 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="MTS" cc="by" country="Belarus" operator="Mobile TeleSystems" status="Operational" 03 bands="CDMA2000" brand="DIALLOG" cc="by" country="Belarus" operator="BelCel" status="Operational" 04 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="life:)" cc="by" country="Belarus" operator="Belarussian Telecommunications Network" status="Operational" 501 brand="BelCel JV" cc="by" country="Belarus" 00-99 259 01 bands="GSM 900 / GSM 1800 / UMTS 2100 / LTE 2600" brand="Orange" cc="md" country="Moldova" operator="Orange Moldova" status="Operational" 02 bands="GSM 900 / GSM 1800 / UMTS 2100 / LTE 2600" brand="Moldcell" cc="md" country="Moldova" status="Operational" 03 bands="CDMA 450" brand="Unité" cc="md" country="Moldova" operator="Moldtelecom" status="Operational" 04 bands="GSM 900 / GSM 1800" brand="Eventis" cc="md" country="Moldova" operator="Eventis Telecom" status="Not operational" 05 bands="UMTS 2100" brand="Unité" cc="md" country="Moldova" operator="Moldtelecom" status="Operational" 99 bands="UMTS 2100" brand="Unité" cc="md" country="Moldova" operator="Moldtelecom" status="Operational" 00-99 260 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Plus" cc="pl" country="Poland" operator="Polkomtel Sp. z o.o." status="Operational" 02 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="T-Mobile" cc="pl" country="Poland" operator="T-Mobile Polska S.A." status="Operational" 03 bands="GSM 900 / GSM 1800 / UMTS 2100 / CDMA2000 450" brand="Orange" cc="pl" country="Poland" operator="Polska Telefonia Komórkowa Centertel Sp. z o.o." status="Operational" 04 bands="" cc="pl" country="Poland" operator="CenterNet S.A." status="Not operational" 05 bands="UMTS 2100" cc="pl" country="Poland" operator="Polska Telefonia Komórkowa Centertel Sp. z o.o." status="Operational" 06 bands="GSM 900/ GSM 1800 / UMTS 900 / UMTS 2100" brand="Play" cc="pl" country="Poland" operator="P4 Sp. z o.o." status="Operational" 07 bands="GSM 900 / UMTS 2100" brand="Netia" cc="pl" country="Poland" operator="Netia S.A." status="Operational" 08 bands="" cc="pl" country="Poland" operator="E-Telko Sp. z o.o." status="Not operational" 09 brand="Lycamobile" cc="pl" country="Poland" operator="Lycamobile Sp. z o.o." status="Operational" 10 bands="UMTS 850" brand="Sferia" cc="pl" country="Poland" operator="Sferia S.A." status="Operational" 11 bands="CDMA2000 420" brand="Nordisk Polska" cc="pl" country="Poland" operator="Nordisk Polska Sp. z o.o." status="Operational" 12 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Cyfrowy Polsat" cc="pl" country="Poland" operator="Cyfrowy Polsat S.A." status="Operational" 13 brand="Sferia" cc="pl" country="Poland" operator="Sferia S.A." status="Not operational" 14 brand="Sferia" cc="pl" country="Poland" operator="Sferia S.A." status="Not operational" 15 bands="LTE 1800" brand="CenterNet" cc="pl" country="Poland" operator="CenterNet S.A." status="Operational" 16 bands="GSM 1800 / LTE 1800" brand="Mobyland" cc="pl" country="Poland" operator="Mobyland Sp. z o.o." status="Operational" 17 bands="UMTS 900" brand="Aero2" cc="pl" country="Poland" operator="Aero 2 Sp. z o.o." status="Operational" 34 bands="UMTS 900" cc="pl" country="Poland" operator="T-Mobile Polska S.A." status="Operational" 98 cc="pl" country="Poland" operator="P4 Sp. z o.o." status="Not Operational" 00-99 262 01 bands="LTE 800 / GSM 900 / GSM/LTE 1800 / UMTS 2100 / LTE 2600" brand="T-Mobile" cc="de" country="Germany" operator="T-Mobile Deutschland GmbH" status="Operational" 02 bands="LTE 800 / GSM 900 / GSM 1800 / UMTS 2100 / LTE 2600" brand="Vodafone" cc="de" country="Germany" operator="Vodafone D2 GmbH" status="Operational" 03 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="E-Plus" cc="de" country="Germany" operator="E-Plus Mobilfunk" status="Operational" 04 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Vodafone" cc="de" country="Germany" status="Reserved" 05 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="E-Plus" cc="de" country="Germany" operator="E-Plus Mobilfunk" status="Reserved" 06 bands="LTE 800 / GSM 900 / GSM/LTE 1800 / UMTS 2100 / LTE 2600" brand="T-Mobile" cc="de" country="Germany" status="Reserved" 07 bands="LTE 800 / GSM 900 / GSM 1800 / UMTS 2100 / LTE 2600" brand="O2" cc="de" country="Germany" operator="O2 (Germany) GmbH & Co. OHG" status="Operational" 08 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="O2" cc="de" country="Germany" status="Reserved" 09 bands="GSM 900 / GSM 1800 / UMTS 2100 / LTE 2600" brand="Vodafone" cc="de" country="Germany" status="Internal testing IOT" 10 bands="GSM-R" cc="de" country="Germany" operator="Arcor AG & Co" status="Operational" 11 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="O2" cc="de" country="Germany" status="Reserved" 12 bands=""full" MVNO / MVNE" brand="Dolphin Telecom / sipgate" cc="de" country="Germany" operator="sipgate Wireless" status="Operational" 13 bands="UMTS 2100" cc="de" country="Germany" operator="Mobilcom Multimedia" status="Not operational" 14 bands="UMTS 2100" cc="de" country="Germany" operator="Group 3G UMTS" status="Not operational" 15 bands="TD-SCDMA" brand="Airdata" cc="de" country="Germany" status="Operational" 16 bands="GSM 900 / GSM 1800 / UMTS 2100 (MVNE)" brand="Telogic ex. Vistream" cc="de" country="Germany" status="" 20 bands="GSM" brand="OnePhone" cc="de" country="Germany" operator="E-Plus" status="Operational" 42 bands="GSM 1800" brand="27C3" cc="de" country="Germany" operator="Chaos Computer Club" status="Not operational" 43 bands="" brand="LYCA" cc="de" country="Germany" operator="Lycamobile" status="Operational" 60 bands="GSM-R 900" cc="de" country="Germany" operator="DB Telematik" status="Operational" 76 bands="GSM 900" cc="de" country="Germany" operator="Siemens AG" status="Operational" 77 bands="GSM 900" brand="E-Plus" cc="de" country="Germany" status="Operational" 901 bands="" brand="Debitel" cc="de" country="Germany" status="Operational" 92 bands="GSM 1800 / UMTS 2100" brand="Nash Technologies" cc="de" country="Germany" status="Operational" 00-99 266 01 bands="GSM 900" brand="GibTel" cc="gi" country="Gibraltar (United Kingdom)" operator="Gibtelecom" status="Operational" 06 bands="UMTS 2100" brand="CTS Mobile" cc="gi" country="Gibraltar (United Kingdom)" operator="CTS Gibraltar" status="Operational" 09 brand="Shine" cc="gi" country="Gibraltar (United Kingdom)" operator="Eazi Telecom" status="Operational" 00-99 268 01 bands="GSM 900 / GSM 1800 / UMTS 900/2100 / LTE 800/1800/2600" brand="Vodafone" cc="pt" country="Portugal" operator="Vodafone Portugal" status="Operacional" 03 bands="GSM 900 / UMTS 2100 / LTE 800/1800/2600" brand="Optimus" cc="pt" country="Portugal" operator="Sonaecom – Serviços de Comunicações, S.A." status="Operational" 04 bands="GSM 900 / GSM 1800 / UMTS 900/2100" brand="LycaMobile" cc="pt" country="Portugal" operator="MVNO" status="Operational" 06 bands="GSM 900 / GSM 1800 / UMTS 2100 / LTE 800/1800/2600" brand="TMN" cc="pt" country="Portugal" operator="Telecomunicações Móveis Nacionais" status="Operational" 07 bands="GSM 900 / UMTS 2100" brand="Vectonemobile - Delightmobile" cc="pt" country="Portugal" operator="MVNO" status="Operational" 21 bands="CDMA2000 450" brand="Zapp" cc="pt" country="Portugal" operator="Zapp Portugal" status="Not operational" 00-99 270 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="LuxGSM" cc="lu" country="Luxembourg" operator="P&T Luxembourg" status="Operational" 77 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Tango" cc="lu" country="Luxembourg" operator="Tango SA" status="Operational" 99 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Orange" cc="lu" country="Luxembourg" operator="Orange S.A." status="Operational" 00-99 272 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Vodafone" cc="ie" country="Ireland" operator="Vodafone Ireland" status="Operational" 02 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="O2" cc="ie" country="Ireland" operator="O2 Ireland" status="Operational" 03 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Meteor" cc="ie" country="Ireland" operator="Meteor Mobile Communications" status="Operational" 04 bands="" cc="ie" country="Ireland" operator="Access Telecom" status="" 05 bands="UMTS 2100" brand="3" cc="ie" country="Ireland" operator="Hutchison 3G Ireland limited" status="Operational" 07 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="eMobile" cc="ie" country="Ireland" operator="Eircom Mobile" status="Operational" 09 bands="" cc="ie" country="Ireland" operator="Clever Communications" status="" 11 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Tesco Mobile" cc="ie" country="Ireland" operator="Liffey Telecom" status="Operational" 13 bands="GSM 900 / GSM 1800" brand="Lycamobile" cc="ie" country="Ireland" operator="Lycamobile" status="Operational" 00-99 274 01 bands="GSM 900 / GSM 1800 / UMTS 2100 / LTE 1800" brand="Síminn" cc="is" country="Iceland" operator="Iceland Telecom" status="Operational" 02 bands="GSM 900 / GSM 1800 / UMTS 2100 / LTE 800" brand="Vodafone" cc="is" country="Iceland" operator="Og fjarskipti hf" status="Operational" 03 bands="" brand="Vodafone" cc="is" country="Iceland" operator="Vodafone Iceland" status="Operational" 04 bands="GSM 1800" brand="Viking" cc="is" country="Iceland" operator="IMC Island ehf" status="Operational" 06 bands="" cc="is" country="Iceland" operator="Núll níu ehf" status="Reserved" 07 bands="GSM 1800" brand="IceCell" cc="is" country="Iceland" operator="IceCell ehf" status="Operational" 08 bands="" brand="On-waves" cc="is" country="Iceland" operator="Iceland Telecom" status="Operational" 11 bands="UMTS 2100 / LTE 1800" brand="Nova" cc="is" country="Iceland" operator="Nova ehf" status="Operational" 12 bands="GSM 900 / GSM 1800" brand="Tal" cc="is" country="Iceland" operator="Tal hf" status="Operational" 00-99 276 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="AMC" cc="al" country="Albania" operator="Albanian Mobile Communications" status="Operational" 02 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Vodafone" cc="al" country="Albania" operator="Vodafone Albania" status="Operational" 03 bands="GSM 900 / GSM 1800" brand="Eagle Mobile" cc="al" country="Albania" operator="Eagle Mobile" status="Operational" 04 bands="GSM 900 / GSM 1800" brand="Plus Communication" cc="al" country="Albania" operator="Plus Communication" status="Operational" 00-99 278 01 bands="GSM 900 / UMTS 2100" brand="Vodafone" cc="mt" country="Malta" operator="Vodafone Malta" status="Operational" 21 bands="GSM 1800 / UMTS 2100" brand="GO" cc="mt" country="Malta" operator="Mobisle Communications Limited" status="Operational" 77 bands="UMTS 2100" brand="Melita" cc="mt" country="Malta" operator="Melita Plc" status="Operational" 00-99 280 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Cytamobile-Vodafone" cc="cy" country="Cyprus" operator="Cyprus Telecommunications Auth" status="Operational" 10 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="MTN" cc="cy" country="Cyprus" operator="Areeba Ltd" status="Operational" 20 bands="GSM 900 / GSM 1800" brand="PrimeTel" cc="cy" country="Cyprus" operator="PrimeTel PLC" status="Operational" 00-99 282 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Geocell" cc="ge" country="Georgia" operator="Geocell Limited" status="Operational" 02 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="MagtiCom" cc="ge" country="Georgia" operator="Magticom GSM" status="Operational" 03 bands="CDMA2000 450" brand="MagtiCom" cc="ge" country="Georgia" operator="Magtifix" status="Operational" 04 bands="GSM 1800" brand="Beeline" cc="ge" country="Georgia" operator="Mobitel LLC" status="Operational" 05 bands="CDMA2000 800" brand="Silknet" cc="ge" country="Georgia" operator="Silknet CDMA" status="Operational" 00-99 283 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Beeline" cc="am" country="Armenia" operator="ArmenTel" status="Operational" 04 bands="GSM 900 / UMTS 900" brand="Karabakh Telecom" cc="am" country="Armenia" operator="Karabakh Telecom" status="Operational" 05 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="VivaCell-MTS" cc="am" country="Armenia" operator="K Telecom CJSC" status="Operational" 10 bands="GSM 900 / GSM 1800 / UMTS 2100 / UMTS 900" brand="Orange" cc="am" country="Armenia" operator="Orange S.A." status="Operational" 00-99 284 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="M-Tel" cc="bg" country="Bulgaria" operator="Mobiltel" status="Operational" 03 bands="GSM 900 / GSM 1800 / UMTS 900 / UMTS 2100" brand="Vivacom" cc="bg" country="Bulgaria" operator="BTC" status="Operational" 04 bands="GSM 1800" brand="Undisclosed" cc="bg" country="Bulgaria" operator="Undisclosed" status="Reserved" 05 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="GLOBUL" cc="bg" country="Bulgaria" operator="Cosmo Bulgaria Mobile" status="Operational" 13 brand="MaxTelecom" cc="bg" country="Bulgaria" operator="Max Telecom LTD" status="Deploying" 00-99 286 01 bands="GSM 900 / UMTS 2100" brand="Turkcell" cc="tr" country="Turkey" operator="Turkcell Iletisim Hizmetleri A.S." status="Operational" 02 bands="GSM 900 / UMTS 2100" brand="Vodafone" cc="tr" country="Turkey" operator="Vodafone Turkey" status="Operational" 03 bands="GSM 1800 / UMTS 2100" brand="Avea" cc="tr" country="Turkey" status="Operational" 04 bands="GSM 1800" cc="tr" country="Turkey" operator="Aycell" status="Not operational" 00-99 288 01 bands="GSM 900" brand="Faroese Telecom" cc="fo" country="Faroe Islands (Denmark)" operator="Faroese Telecom" status="Operational" 02 bands="GSM 900" brand="Vodafone" cc="fo" country="Faroe Islands (Denmark)" operator="Vodafone Faroe Islands" status="Operational" 00-99 289 67 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Aquafon" cc="ge" country="Abkhazia" operator="Aquafon JSC" status="Operational" 68 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="A-Mobile" cc="ge" country="Abkhazia" operator="A-Mobile LLC" status="Operational" 88 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="A-Mobile" cc="ge" country="Abkhazia" operator="A-Mobile LLC" status="Operational" 00-99 290 01 bands="GSM 900" cc="gl" country="Greenland (Denmark)" operator="TELE Greenland A/S" status="Operational" 00-99 292 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="PRIMA" cc="sm" country="San Marino" operator="San Marino Telecom" status="Operational" 00-99 293 40 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Si.mobil" cc="si" country="Slovenia" operator="SI.MOBIL d.d." status="Operational" 41 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Mobitel" cc="si" country="Slovenia" operator="Mobitel D.D." status="Operational" 64 bands="UMTS 2100" brand="T-2" cc="si" country="Slovenia" operator="T-2 d.o.o." status="Operational" 70 bands="GSM 900 / GSM 1800 / UMTS 900 / UMTS 2100" brand="Tušmobil" cc="si" country="Slovenia" operator="Tušmobil d.o.o." status="Operational" 00-99 294 01 bands="GSM 900 / UMTS 2100" brand="T-Mobile MK" cc="mk" country="Macedonia" operator="T-Mobile Macedonia" status="Operational" 02 bands="GSM 900 / UMTS 2100" brand="ONE" cc="mk" country="Macedonia" operator="One" status="Operational" 03 bands="GSM 900 / GSM 1800 /UMTS 900" brand="Vip MK" cc="mk" country="Macedonia" operator="VIP Operator" status="Operational" 00-99 295 01 bands="GSM 900 / GSM 1800" brand="Swisscom" cc="li" country="Liechtenstein" operator="Swisscom Schweiz AG" status="Operational" 02 bands="GSM 1800 / UMTS 2100" brand="Orange" cc="li" country="Liechtenstein" operator="Orange Liechtenstein AG" status="Operational" 05 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="FL1" cc="li" country="Liechtenstein" operator="Mobilkom Liechtenstein AG" status="Operational" 06 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Cubic Telecom" cc="li" country="Liechtenstein" operator="Cubic Telecom AG" status="Operational" 77 bands="GSM 900" brand="Alpmobil" cc="li" country="Liechtenstein" operator="Alpcom AG" status="Not operational" 00-99 297 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Telenor" cc="me" country="Montenegro" operator="Telenor Montenegro" status="Operational" 02 bands="GSM 900 / UMTS 2100" brand="T-Mobile" cc="me" country="Montenegro" operator="T-Mobile Montenegro LLC" status="Operational" 03 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="m:tel CG" cc="me" country="Montenegro" operator="MTEL CG" status="Operational" 04 bands="GSM 900 / UMTS 2100" brand="T-Mobile" cc="me" country="Montenegro" operator="T-Mobile Montenegro" status="Operational" 00-99 302 220 bands="UMTS 850 / UMTS 1900 / LTE 1700" brand="Telus" cc="ca" country="Canada" operator="Koodo Mobility and Telus Mobility" status="Operational" 221 bands="" brand="Telus" cc="ca" country="Canada" operator="Telus Mobility" status="" 270 bands="UMTS 1700 / LTE 1700" brand="EastLink" cc="ca" country="Canada" operator="EastLink" status="Operational" 290 bands="iDEN 900" brand="Airtel Wireless" cc="ca" country="Canada" operator="Airtel Wireless" status="Operational" 320 bands="UMTS 1700" brand="Mobilicity" cc="ca" country="Canada" operator="DAVE Wireless" status="Operational" 350 bands="GSM 850" brand="FIRST" cc="ca" country="Canada" operator="FIRST Networks Operations" status="Operational" 360 bands="iDEN 800" brand="MiKe" cc="ca" country="Canada" operator="Telus Mobility" status="Operational" 361 bands="CDMA2000 800 / CDMA2000 1900" brand="Telus" cc="ca" country="Canada" operator="Telus Mobility" status="Operational" 370 bands="GSM 850 / GSM 1900 / UMTS 850 / UMTS 1900" brand="Fido" cc="ca" country="Canada" operator="Fido Solutions (Rogers Wireless)" status="Operational" 380 bands="UMTS 850 / UMTS 1900" brand="DMTS" cc="ca" country="Canada" operator="Dryden Mobility" status="Operational" 490 bands="UMTS 1700" brand="WIND Mobile" cc="ca" country="Canada" operator="Globalive Communications" status="Operational" 500 bands="UMTS 1700" brand="Videotron" cc="ca" country="Canada" operator="Videotron" status="Operational" 510 bands="UMTS 1700" brand="Videotron" cc="ca" country="Canada" operator="Videotron" status="Operational" 610 bands="UMTS 850 / UMTS 1900 /LTE 1700 / LTE 2600" brand="Bell" cc="ca" country="Canada" operator="Bell Mobility and Virgin Mobile Canada" status="Operational" 620 bands="GSM 1900 / UMTS 1900" brand="ICE Wireless" cc="ca" country="Canada" operator="ICE Wireless" status="Operational" 640 bands="CDMA2000 800 / CDMA2000 1900" brand="Bell" cc="ca" country="Canada" operator="Bell Mobility" status="Operational" 652 bands="CDMA2000" cc="ca" country="Canada" operator="BC Tel Mobility (Telus)" status="Operational" 653 bands="CDMA2000 800 / CDMA2000 1900" brand="Telus" cc="ca" country="Canada" operator="Telus Mobility" status="Operational" 655 bands="CDMA2000 800 / CDMA2000 1900" brand="MTS" cc="ca" country="Canada" operator="MTS Mobility" status="Operational" 656 bands="CDMA2000 / UMTS 850 / UMTS 1900 / LTE 1700 / LTE 2600" brand="TBay" cc="ca" country="Canada" operator="Thunder Bay Telephone Mobility" status="Operational" 657 bands="CDMA2000 800 / CDMA2000 1900" brand="Telus" cc="ca" country="Canada" operator="Telus Mobility" status="Operational" 660 bands="UMTS 850 / UMTS 1900 / LTE 1700" brand="MTS" cc="ca" country="Canada" operator="MTS Mobility" status="Operational" 680 bands="CDMA2000 800 / CDMA2000 1900 / UMTS 850 / UMTS 1900" brand="SaskTel" cc="ca" country="Canada" operator="SaskTel Mobility" status="Operational" 690 bands="UMTS 850 / UMTS 1900" brand="Bell" cc="ca" country="Canada" operator="Bell Mobility" status="Operational" 701 bands="CDMA2000" cc="ca" country="Canada" operator="MB Tel Mobility" status="Operational" 702 bands="CDMA2000" cc="ca" country="Canada" operator="MT&T Mobility (Aliant)" status="Operational" 703 bands="CDMA2000" cc="ca" country="Canada" operator="New Tel Mobility (Aliant)" status="Operational" 710 bands="Satellite CDMA" brand="Globalstar" cc="ca" country="Canada" status="Operational" 720 bands="GSM 850 / GSM 1900 / UMTS 850 / UMTS 1900 / LTE 1700 / LTE 2600" brand="Rogers Wireless" cc="ca" country="Canada" operator="Rogers Communications" status="Operational" 780 bands="UMTS 850 / UMTS 1900 / LTE 1700" brand="SaskTel" cc="ca" country="Canada" operator="SaskTel Mobility" status="Operational" 880 bands="UMTS 850 / UMTS 1900" brand="Bell / Telus / SaskTel" cc="ca" country="Canada" operator="Shared Telus, Bell, and SaskTel" status="Operational" 000-999 308 01 bands="GSM 900" brand="Ameris" cc="pm" country="Saint Pierre and Miquelon (France)" operator="St. Pierre-et-Miquelon Télécom" status="Operational" 02 bands="GSM 900" brand="GLOBALTEL" cc="pm" country="Saint Pierre and Miquelon (France)" operator="GLOBALTEL" status="Operational" 00-99 310 004 bands="" brand="Verizon" cc="us" country="United States of America" operator="Verizon Wireless" status="Operational" 005 bands="CDMA2000 850 / CDMA2000 1900" brand="Verizon" cc="us" country="United States of America" operator="Verizon Wireless" status="Operational" 010 bands="" cc="us" country="United States of America" operator="MCI" status="Not operational" 013 bands="" brand="MobileTel" cc="us" country="United States of America" status="" 014 bands="" cc="us" country="United States of America" operator="Testing" status="Operational" 016 bands="CDMA2000 1900 / CDMA2000 1700 / CDMA2000 2100" brand="Cricket Communications" cc="us" country="United States of America" operator="Cricket Wireless" status="Operational" 017 bands="" cc="us" country="United States of America" operator="North Sight Communications Inc." status="Operational" 020 bands="GSM 850 / GSM 1900" cc="us" country="United States of America" operator="Union Telephone Company" status="Operational" 026 bands="GSM 1900 / UMTS 1700 / UMTS 1900" brand="T-Mobile" cc="us" country="United States of America" status="Operational" 030 bands="GSM 850" brand="AT&T" cc="us" country="United States of America" operator="AT&T Mobility" status="Operational" 032 bands="CDMA2000 1900 / LTE 700" brand="IT&E Wireless" cc="gu" country="Guam (United States of America)" operator="IT&E Overseas, Inc" status="Operational" 033 bands="" cc="gu" country="Guam (United States of America)" operator="Guam Telephone Authority" status="" 034 bands="" brand="Airpeak" cc="us" country="United States of America" status="Operational" 040 bands="GSM 1900" brand="Concho" cc="us" country="United States of America" operator="Concho Cellular Telephone Co., Inc." status="Operational" 046 bands="GSM 1900" brand="SIMMETRY" cc="us" country="United States of America" operator="TMP Corp" status="Operational" 053 bands="CDMA2000 1900." cc="us" country="United States of America" operator="Virgin Mobile US" status="Operational" 054 bands="" cc="us" country="United States of America" operator="Alltel US" status="Operational" 060 bands="" cc="us" country="United States of America" operator="Consolidated Telcom" status="Operational" 066 bands="GSM AND CDMA" cc="us" country="United States of America" operator="U.S. Cellular" status="Operational" 070 bands="" cc="us" country="United States of America" operator="Highland Cellular" status="Operational" 080 bands="GSM 1900" brand="Corr" cc="us" country="United States of America" operator="Corr Wireless Communications LLC" status="Operational" 090 bands="CDMA2000 1900 / CDMA2000 1700 / CDMA2000 2100" brand="Cricket Communications" cc="us" country="United States of America" operator="Cricket Wireless" status="Operational" 100 bands="GSM 850" brand="Plateau Wireless" cc="us" country="United States of America" operator="New Mexico RSA 4 East Ltd. Partnership" status="Operational" 110 bands="GSM 850" brand="PTI Pacifica" cc="us" country="United States of America" operator="PTI Pacifica Inc." status="Operational" 120 bands="CDMA2000 1900" brand="Sprint" cc="us" country="United States of America" status="Operational" 140 bands="GSM 850 / GSM 1900" brand="mPulse" cc="gu" country="Guam (United States of America)" operator="GTA Wireless" status="Operational" 150 bands="GSM 850 / UMTS 850 / UMTS 1900" brand="AT&T" cc="us" country="United States of America" operator="AT&T Mobility" status="Operational" 160 bands="GSM 1900" cc="us" country="United States of America" operator="T-Mobile" status="Not operational" 170 bands="GSM 1900" brand="AT&T" cc="us" country="United States of America" operator="AT&T Mobility" status="Operational" 180 bands="GSM 850 / UMTS 850 / UMTS 1900" brand="West Central" cc="us" country="United States of America" operator="West Central Wireless" status="Operational" 190 bands="GSM 850" brand="Dutch Harbor" cc="us" country="United States of America" operator="Alaska Wireless Communications, LLC" status="Operational" 200 bands="GSM 1900" cc="us" country="United States of America" operator="T-Mobile" status="Not operational" 210 bands="GSM 1900" cc="us" country="United States of America" operator="T-Mobile" status="Not operational" 220 bands="GSM 1900" cc="us" country="United States of America" operator="T-Mobile" status="Not operational" 230 bands="GSM 1900" cc="us" country="United States of America" operator="T-Mobile" status="Not operational" 240 bands="GSM 1900" cc="us" country="United States of America" operator="T-Mobile" status="Not operational" 250 bands="GSM 1900" cc="us" country="United States of America" operator="T-Mobile" status="Not operational" 260 bands="GSM 1900 / UMTS 1900 / UMTS 1700/2100 (AWS)" cc="us" country="United States of America" operator="T-Mobile" status="Operational" 270 bands="GSM 1900" cc="us" country="United States of America" operator="T-Mobile" status="Not operational" 280 bands="GSM 1900" brand="AT&T" cc="us" country="United States of America" operator="AT&T Mobility" status="Not Operational" 290 bands="GSM 1900" cc="us" country="United States of America" operator="T-Mobile" status="Not operational" 300 bands="GSM 1900" brand="Big Sky Mobile" cc="us" country="United States of America" operator="Smart Call (Truphone)" status="Operational" 310 bands="GSM 1900" cc="us" country="United States of America" operator="T-Mobile" status="Not operational" 311 bands="GSM 1900" cc="us" country="United States of America" operator="Farmers Wireless" status="Operational" 320 bands="GSM 850 / GSM 1900" brand="Cellular One" cc="us" country="United States of America" operator="Smith Bagley, Inc." status="Operational" 330 bands="GSM 1900" brand="T-Mobile" cc="us" country="United States of America" status="Not operational" 340 bands="GSM 1900" brand="Westlink" cc="us" country="United States of America" operator="Westlink Communications" status="Operational" 350 bands="GSM 1900" cc="us" country="United States of America" operator="Carolina Phone" status="Not operational" 370 bands="CDMA2000 850" brand="Docomo" cc="gu" country="Guam (United States of America)" operator="NTT Docomo Pacific" status="Not operational" 380 bands="GSM 850 / GSM 1900 / UMTS 850 / UMTS 1900" brand="AT&T" cc="us" country="United States of America" operator="AT&T Mobility" status="Not operational" 390 bands="GSM 850" brand="Cellular One of East Texas" cc="us" country="United States of America" operator="TX-11 Acquisition, LLC" status="Operational" 400 bands="GSM 1900" brand="i CAN_GSM" cc="us" country="United States of America" operator="Wave Runner LLC (Guam)" status="Operational" 410 bands="GSM 850 / GSM 1900 / UMTS 850 / UMTS 1900" brand="AT&T" cc="us" country="United States of America" operator="AT&T Mobility" status="Operational" 420 bands="GSM 1900" brand="Cincinnati Bell" cc="us" country="United States of America" operator="Cincinnati Bell Wireless" status="Operational" 430 bands="GSM 1900" cc="us" country="United States of America" operator="Alaska Digitel" status="Operational" 440 bands="GSM 1900" brand="Cellular One" cc="us" country="United States of America" status="" 450 bands="GSM 850" brand="Viaero" cc="us" country="United States of America" operator="Viaero Wireless" status="Operational" 460 bands="GSM 1900" brand="Simmetry" cc="us" country="United States of America" operator="TMP Corporation" status="Operational" 470 bands="CDMA2000 1900" brand="nTelos" cc="us" country="United States of America" operator="NTT Docomo Pacific" status="Operational" 480 bands="" cc="us" country="United States of America" operator="Choice Phone" status="Operational" 490 bands="GSM 850 / GSM 1900" brand="T-Mobile" cc="us" country="United States of America" status="Operational" 500 bands="CDMA2000 800 / CDMA2000 1900" brand="Alltel" cc="us" country="United States of America" status="Operational" 510 bands="" brand="Airtel" cc="us" country="United States of America" operator="Airtel Wireless" status="Operational" 520 bands="" brand="VeriSign" cc="us" country="United States of America" status="" 530 bands="" cc="us" country="United States of America" operator="West Virginia Wireless" status="Operational" 540 bands="GSM 1900" brand="Oklahoma Western" cc="us" country="United States of America" operator="Oklahoma Western Telephone Company" status="Operational" 560 bands="GSM 850" brand="AT&T" cc="us" country="United States of America" operator="AT&T Mobility" status="Operational" 570 bands="GSM 1900" brand="Cellular One" cc="us" country="United States of America" operator="MTPCS, LLC" status="Operational" 580 bands="" brand="T-Mobile" cc="us" country="United States of America" status="Not operational" 59 bands="CDMA2000" brand="Cellular One" cc="bm" country="Bermuda" status="Operational" 590 bands="GSM 850 / GSM 1900" brand="Alltel" cc="us" country="United States of America" operator="Alltel Communications Inc" status="Operational" 610 bands="GSM 1900" brand="Epic Touch" cc="us" country="United States of America" operator="Elkhart Telephone Co." status="Operational" 620 bands="GSM 1900" brand="Coleman County Telecom" cc="us" country="United States of America" operator="Coleman County Telecommunications" status="Operational" 630 bands="GSM 1900" brand="AmeriLink PCS" cc="us" country="United States of America" operator="Choice Wireless" status="Operational" 640 bands="GSM 1900" brand="Airadigm" cc="us" country="United States of America" operator="Airadigm Communications" status="Operational" 650 bands="GSM 850" brand="Jasper" cc="us" country="United States of America" operator="Jasper Wireless, inc" status="Operational" 660 bands="GSM 1900" brand="T-Mobile" cc="us" country="United States of America" status="Not operational" 670 bands="" brand="Northstar" cc="us" country="United States of America" status="Operational" 680 bands="GSM 850 / GSM 1900" brand="AT&T" cc="us" country="United States of America" operator="AT&T Mobility" status="Operational" 690 bands="GSM 1900" brand="Immix" cc="us" country="United States of America" operator="Immix Wireless" status="Operational" 730 bands="" brand="SeaMobile" cc="us" country="United States of America" status="Operational" 740 bands="" brand="Convey" cc="us" country="United States of America" operator="Convey Communications Inc." status="Operational" 750 bands="CDMA2000 850 / CDMA2000 1900 / LTE 700" brand="Appalachian Wireless" cc="us" country="United States of America" operator="Appalachian Wireless" status="Operational" 760 bands="" brand="Panhandle" cc="us" country="United States of America" operator="Panhandle Telecommunications Systems Inc." status="Operational" 770 bands="GSM 1900" brand="i wireless" cc="us" country="United States of America" operator="Iowa Wireless Services" status="Operational" 780 bands="" cc="us" country="United States of America" operator="Airlink PCS" status="Not operational" 790 bands="GSM 1900" brand="PinPoint" cc="us" country="United States of America" operator="PinPoint Communications" status="Operational" 800 bands="GSM 1900" cc="us" country="United States of America" operator="T-Mobile" status="Not operational" 830 bands="GSM 850" brand="Caprock" cc="us" country="United States of America" operator="Caprock Cellular" status="Operational" 840 bands="GSM 1900" brand="telna Mobile" cc="us" country="United States of America" operator="Telecom North America Mobile, Inc." status="Operational" 850 bands="CDMA2000 850 / CDMA2000 1900 / GSM 850 / GSM 1900" brand="Aeris" cc="us" country="United States of America" operator="Aeris Communications, Inc." status="Operational" 870 bands="GSM 850" brand="PACE" cc="us" country="United States of America" operator="Kaplan Telephone Company" status="Operational" 880 bands="GSM 850" brand="Advantage" cc="us" country="United States of America" operator="Advantage Cellular Systems" status="Operational" 890 bands="GSM 850 / GSM 1900" brand="Unicel" cc="us" country="United States of America" operator="Rural Cellular Corporation" status="Operational" 900 bands="CDMA2000 850 / CDMA2000 1900" brand="Mid-Rivers Wireless" cc="us" country="United States of America" operator="Mid-Rivers Communications" status="Operational" 910 bands="GSM 850" brand="First Cellular" cc="us" country="United States of America" operator="First Cellular of Southern Illinois" status="Operational" 940 bands="" cc="us" country="United States of America" operator="Iris Wireless LLC" status="Operational" 950 bands="GSM 850" brand="XIT Wireless" cc="us" country="United States of America" operator="Texas RSA 1 dba XIT Cellular" status="Operational" 960 bands="" brand="Plateau Wireless" cc="us" country="United States of America" status="Operational" 970 bands="Satellite" brand="Globalstar" cc="us" country="United States of America" status="Operational" 980 bands="GSM 850 / UMTS 850 / UMTS 1900" brand="AT&T" cc="us" country="United States of America" operator="AT&T Mobility" status="Not operational" 990 bands="" brand="AT&T" cc="us" country="United States of America" operator="AT&T Mobility" status="Not operational" 000-999 311 000 bands="CDMA2000 850 / CDMA2000 1900" cc="us" country="United States of America" operator="Mid-Tex Cellular" status="Operational" 010 bands="GSM 1900" brand="Chariton Valley" cc="us" country="United States of America" operator="Chariton Valley Communications" status="Operational" 012 bands="CDMA2000 850 / CDMA2000 1900" brand="Verizon" cc="us" country="United States of America" operator="Verizon Wireless" status="Operational" 020 bands="GSM 850" cc="us" country="United States of America" operator="Missouri RSA 5 Partnership" status="Operational" 030 bands="GSM 1900" cc="us" country="United States of America" operator="Indigo Wireless" status="Operational" 040 bands="GSM 850 / GSM 1900" cc="us" country="United States of America" operator="Commnet Wireless" status="Operational" 050 bands="GSM 850 / GSM 1900" cc="us" country="United States of America" operator="Wikes Cellular" status="Operational" 060 bands="GSM 850 / GSM 1900" brand="Farmers Cellular" cc="us" country="United States of America" operator="Farmers Cellular Telephone" status="Operational" 070 bands="GSM 850" brand="Easterbrooke" cc="us" country="United States of America" operator="Easterbrooke Cellular Corporation" status="Operational" 080 bands="GSM 850" brand="Pine Cellular" cc="us" country="United States of America" operator="Pine Telephone Company" status="Operational" 090 bands="GSM 1900" brand="Long Lines Wireless" cc="us" country="United States of America" operator="Long Lines Wireless LLC" status="Operational" 100 bands="GSM 1900" cc="us" country="United States of America" operator="High Plains Wireless" status="Operational" 110 bands="GSM 1900" cc="us" country="United States of America" operator="High Plains Wireless" status="Operational" 120 bands="" cc="us" country="United States of America" operator="Choice Phone" status="Operational" 130 bands="GSM 850" cc="us" country="United States of America" operator="Cell One Amarillo" status="Operational" 140 bands="" brand="Sprocket" cc="us" country="United States of America" operator="MBO Wireless" status="Operational" 150 bands="GSM 850" cc="us" country="United States of America" operator="Wilkes Cellular" status="Operational" 160 bands="" cc="us" country="United States of America" operator="Endless Mountains Wireless" status="Operational" 170 bands="GSM 850" brand="PetroCom" cc="us" country="United States of America" operator="Broadpoint Inc" status="Operational" 180 bands="GSM 850 / UMTS 850 / UMTS 1900" cc="us" country="United States of America" operator="Cingular Wireless" status="Not operational" 190 bands="" cc="us" country="United States of America" operator="Cellular Properties" status="" 210 bands="GSM 1900 / UMTS 2100" cc="us" country="United States of America" operator="Emery Telcom Wireless" status="Operational" 220 cc="us" country="United States of America" operator="U.S. Cellular" status="Operational" 230 bands="" cc="us" country="United States of America" operator="C Spire Wireless" status="Operational" 250 bands="GSM 1900" brand="i CAN_GSM" cc="gu" country="Guam (United States of America)" operator="Wave Runner LLC" status="Not operational" 330 bands="" brand="Bug Tussel Wireless" cc="us" country="United States of America" operator="Bug Tussel Wireless" status="Operational" 480 bands="LTE 700 MHz C Block (4G LTE Network)" brand="Verizon" cc="us" country="United States of America" operator="Verizon Wireless" status="Operational" 481 cc="us" country="United States of America" 490 bands="TDD-LTE (Band 41)" brand="Sprint Corporation" cc="us" country="United States of America" operator="Sprint" status="Operational" 660 bands="CDMA2000 1900 / CDMA 2000 LTE/AWS 1700" brand="metroPCS" cc="us" country="United States of America" operator="metroPCS" status="Operational" 870 bands="" brand="Boost" cc="us" country="United States of America" operator="Boost Mobile" status="Operational" 960 bands="GSM 1900" brand="Lycamobile" cc="us" country="United States of America" operator="Lyca Technology Solutions" status="Operational" 970 bands="LTE/AWS 1700" brand="Big River Broadband" cc="us" country="United States of America" operator="Big River Broadband, LLC" status="Operational" 000-999 313 100 bands="700 MHz Public Safety Broadband" brand="700 MHz Public Safety Broadband" cc="us" country="United States of America" status="" 101 cc="us" country="United States of America" 000-999 316 010 bands="iDEN 800" brand="Nextel" cc="us" country="United States of America" operator="Nextel Communications" status="Not Operational" 011 bands="iDEN 800" cc="us" country="United States of America" operator="Southern Communications Services" status="Operational" 000-999 330 00 bands="PCS 1900" brand="Open Mobile" cc="pr" country="Puerto Rico" operator="PR Wireless" status="Operational" 110 bands="GSM 850 / GSM 1900 / UMTS 850 / LTE 700" brand="Claro Puerto Rico" cc="pr" country="Puerto Rico" operator="América Móvil" status="Operational" 120 bands="LTE 700" brand="Open Mobile" cc="pr" country="Puerto Rico" operator="PR Wireless" status="Operational" 00-99 334 01 bands="iDEN 800" brand="Nextel" cc="mx" country="Mexico" operator="Nextel México" status="Operational" 02 bands="TDMA 850 / GSM 1900 / UMTS 850 / LTE 1700" brand="Telcel" cc="mx" country="Mexico" operator="América Móvil" status="Operational" 03 bands="CDMA2001 1900 / CDMA2001 800 / GSM 1900 / UMTS 850" brand="movistar" cc="mx" country="Mexico" operator="Movistar - Telefónica Moviles (formerly Pegaso Comunicaciones y Sistemas)" status="Operational" 05 bands="GSM 850 / GSM 1900" brand="Iusacell" cc="mx" country="Mexico" operator="Iusacell" status="Operational" 09 bands="UMTS 1700." brand="Nextel" cc="mx" country="Mexico" operator="Nextel México" status="Operational" 00-99 338 020 bands="" brand="LIME" cc="jm" country="Jamaica" operator="LIME (Cable & Wireless)" status="Not Operational" 050 bands="GSM 900 / GSM 1800 / GSM 1900" brand="Digicel" cc="tc" country="Turks and Caicos Islands" operator="Digicel (Turks & Caicos) Limited" status="Operational" 180 bands="GSM 850 / GSM 1900 / WCDMA 850" brand="LIME" cc="jm" country="Jamaica" operator="LIME (Cable & Wireless)" status="Operational" 000-999 340 01 bands="GSM 900" brand="Orange" cc="mq" country="Martinique (France)" operator="Orange Caraïbe Mobiles" status="Operational" 02 bands="GSM 900 / GSM 1800" brand="Outremer" cc="mq" country="Martinique (France)" operator="Outremer Telecom" status="Operational" 03 bands="GSM 900 / GSM 1800" brand="Telcell" cc="gp" country="Guadeloupe (France)" operator="Saint Martin et Saint Barthelemy Telcell Sarl" status="Operational" 08 bands="GSM 900 / GSM 1800" brand="Dauphin" cc="gp" country="Guadeloupe (France)" operator="Dauphin Telecom" status="Operational" 20 bands="GSM 900" brand="Digicel" cc="mq" country="Martinique (France)" operator="DIGICEL Antilles Française Guyane" status="Operational" 00-99 342 600 bands="GSM 1900" brand="LIME" cc="bb" country="Barbados" operator="LIME (formerly known as Cable & Wireless)" status="Operational" 750 bands="GSM 900 / GSM 1800" brand="Digicel" cc="bb" country="Barbados" operator="Digicel (Barbados) Limited" status="Operational" 820 bands="" cc="bb" country="Barbados" operator="Sunbeach Communications" status="Reserved" 000-999 344 030 bands="GSM 1900" brand="APUA" cc="ag" country="Antigua and Barbuda" operator="Antigua Public Utilities Authority" status="Operational" 050 bands="GSM 900 / GSM 1900 / LTE 700" brand="Digicel" cc="ag" country="Antigua and Barbuda" operator="Antigua Wireless Ventures Limited" status="Operational" 920 bands="GSM 850 / GSM 1800/ GSM 1900" brand="LIME" cc="ag" country="Antigua and Barbuda" operator="Cable & Wireless Caribbean Cellular (Antigua) Limited" status="Operational" 000-999 346 050 bands="GSM 900 / GSM 1800" brand="Digicel" cc="ky" country="Cayman Islands (United Kingdom)" operator="Digicel Cayman Ltd." status="Operational" 140 bands="GSM 850 / GSM 1900" brand="LIME" cc="ky" country="Cayman Islands (United Kingdom)" operator="Cable & Wireless (Cayman Islands) Limited" status="Operational" 000-999 348 170 bands="GSM 850 / GSM 1900 / HSPA+ (4G) 850/1900" brand="LIME" cc="vg" country="British Virgin Islands" operator="Cable & Wireless" status="Operational" 570 bands="GSM 900 / GSM 1900" brand="CCT Boatphone" cc="vg" country="British Virgin Islands" operator="Caribbean Cellular Telephone" status="Operational" 770 bands="GSM 1800 / GSM 1900" brand="Digicel" cc="vg" country="British Virgin Islands" operator="Digicel (BVI) Limited" status="Operational" 000-999 350 01 bands="GSM 1900" brand="Digicel Bermuda" cc="bm" country="Bermuda" operator="Telecommunications (Bermuda & West Indies) Ltd" status="Reserved" 02 bands="GSM 1900" brand="Mobility" cc="bm" country="Bermuda" operator="M3 Wireless" status="Operational" 00-99 352 030 bands="GSM 900 / GSM 1800" brand="Digicel" cc="gd" country="Grenada" operator="Digicel Grenada Ltd." status="Operational" 110 bands="GSM 850" brand="Cable & Wireless" cc="gd" country="Grenada" operator="Cable & Wireless Grenada Ltd." status="Operational" 000-999 354 860 bands="GSM 850" brand="Cable & Wireless" cc="ms" country="Montserrat (United Kingdom)" operator="Cable & Wireless" status="Operational" 000-999 356 050 bands="GSM 900 / GSM 1800" brand="Digicel" cc="kn" country="Saint Kitts and Nevis" operator="Wireless Ventures (St Kitts-Nevis) Limited" status="Operational" 070 brand="Chippie" cc="kn" country="Saint Kitts and Nevis" operator="UTS" status="Operational" 110 bands="GSM 850 / GSM 1900" brand="LIME" cc="kn" country="Saint Kitts and Nevis" operator="Cable & Wireless St. Kitts & Nevis Ltd" status="Operational" 000-999 358 050 bands="GSM 900 / GSM 1800 / GSM 1900" brand="Digicel" cc="lc" country="Saint Lucia" status="" 110 bands="GSM 850" cc="lc" country="Saint Lucia" operator="Cable & Wireless" status="" 000-999 360 070 bands="GSM 900 / GSM 1800 / GSM 1900" brand="Digicel" cc="vc" country="Saint Vincent and the Grenadines" operator="Digicel (St. Vincent and the Grenadines) Limited" status="Operational" 100 bands="GSM 850" brand="Cingular Wireless" cc="vc" country="Saint Vincent and the Grenadines" status="" 110 bands="GSM 850" brand="Lime" cc="vc" country="Saint Vincent and the Grenadines" operator="Cable & Wireless (St. Vincent & the Grenadines) Ltd" status="Operational" 000-999 362 51 bands="GSM 900" brand="Telcell" cc="an" country="Former Netherlands Antilles (Kingdom of the Netherlands)" operator="Telcell N.V." status="Operational" 69 bands="GSM 900 / GSM 1800" brand="Digicel" cc="an" country="Former Netherlands Antilles (Kingdom of the Netherlands)" operator="Curaçao Telecom N.V." status="Operational" 91 bands="GSM 900" brand="UTS" cc="an" country="Former Netherlands Antilles (Kingdom of the Netherlands)" operator="Setel N.V." status="Operational" 94 bands="TDMA PCS" brand="Bayòs" cc="an" country="Former Netherlands Antilles (Kingdom of the Netherlands)" operator="Bòbò Frus N.V." status="Operational" 95 bands="CDMA2000 850" brand="MIO" cc="an" country="Former Netherlands Antilles (Kingdom of the Netherlands)" operator="E.O.C.G. Wireless" status="Operational" 00-99 363 01 bands="GSM 900 / GSM 1900 / TDMA 800" brand="SETAR" cc="aw" country="Aruba (Kingdom of the Netherlands)" operator="Servicio di Telecomunicacion di Aruba" status="Operational" 02 bands="GSM 900 / GSM 1800 / HSPA+ 2100" brand="Digicel" cc="aw" country="Aruba (Kingdom of the Netherlands)" operator="Digicel Aruba" status="Operational" 00-99 364 39 bands="GSM 850 / GSM 1900 / UMTS 850" brand="BaTelCo" cc="bs" country="Bahamas" operator="The Bahamas Telecommunications Company Ltd" status="Operational" 00-99 365 010 bands="" cc="ai" country="Anguilla" operator="Weblinks Limited" status="Operational" 840 bands="" cc="ai" country="Anguilla" operator="Cable & Wireless" status="Operational" 000-999 366 020 bands="GSM 900 / GSM 1900" brand="Digicel" cc="dm" country="Dominica" operator="Digicel Group Limited" status="Operational" 110 bands="GSM 850" cc="dm" country="Dominica" operator="Cable & Wireless" status="Operational" 000-999 368 01 bands="GSM 900 / GSM 850" brand="CUBACEL" cc="cu" country="Cuba" operator="Empresa de Telecomunicaciones de Cuba, SA" status="Operational" 00-99 370 01 bands="GSM 900 / GSM 1800 / 1900 / UMTS 900 / LTE 1800" brand="Orange" cc="do" country="Dominican Republic" operator="Orange Dominicana" status="Operational" 02 bands="CDMA2000 1900 / GSM 850 / GSM 1900 / UMTS 850" brand="Claro" cc="do" country="Dominican Republic" operator="Compañía Dominicana de Teléfonos, C por" status="Operational" 03 bands="AMPS / IS-95A 800 / CDMA2000 1900 / LTE 1900" brand="Tricom" cc="do" country="Dominican Republic" operator="Tricom S.A." status="Operational" 04 bands="CDMA2000 1900 / GSM 1900" brand="Viva" cc="do" country="Dominican Republic" operator="Trilogy Dominicana, S.A." status="Operational" 00-99 372 01 bands="GSM 850" brand="Voila" cc="ht" country="Haiti" operator="Communication Cellulaire d'Haiti S.A." status="Operational" 02 bands="GSM 1800" brand="Digicel" cc="ht" country="Haiti" operator="Unigestion Holding S.A." status="Operational" 03 bands="GSM 900" brand="Natcom" cc="ht" country="Haiti" operator="Telecommunication S.A." status="Operational" 00-99 374 12 bands="GSM 850 / GSM 1900" brand="bmobile" cc="tt" country="Trinidad and Tobago" operator="TSTT" status="Operational" 130 bands="GSM 850 / GSM 1900 / UMTS 1900" brand="Digicel" cc="tt" country="Trinidad and Tobago" operator="Digicel (Trinidad & Tobago) Limited" status="Operational" 00-99 376 350 bands="GSM 850" brand="C&W" cc="tc" country="Turks and Caicos Islands" operator="Cable & Wireless West Indies Ltd (Turks & Caicos)" status="Operational" 352 bands="UMTS 850" brand="Islandcom" cc="tc" country="Turks and Caicos Islands" operator="Islandcom Telecommunications" status="Operational" 000-999 400 01 bands="GSM 900 / GSM 1800/ UMTS 2100" brand="Azercell" cc="az" country="Azerbaijan" status="Operational" 02 bands="GSM 900 / GSM 1800/ UMTS 2100" brand="Bakcell" cc="az" country="Azerbaijan" status="Operational" 03 bands="CDMA2000" brand="FONEX" cc="az" country="Azerbaijan" operator="CATEL" status="Operational" 04 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Nar Mobile" cc="az" country="Azerbaijan" operator="Azerfon" status="Operational" 00-99 401 01 bands="GSM 900 / GSM 1800" brand="Beeline" cc="kz" country="Kazakhstan" operator="KaR-Tel LLP" status="Operational" 02 bands="GSM 900 / GSM 1800" brand="Kcell" cc="kz" country="Kazakhstan" operator="GSM Kazakhstan Ltd" status="Operational" 07 bands="CDMA2000 800" brand="Dalacom" cc="kz" country="Kazakhstan" operator="Altel" status="Operational" 08 bands="CDMA2000 800 / CDMA2000 450" brand="Kazakhtelecom" cc="kz" country="Kazakhstan" status="Operational" 77 bands="GSM 900 / GSM 1800" brand="Tele2.kz" cc="kz" country="Kazakhstan" status="Operational" 00-99 402 11 bands="GSM 900" brand="B-Mobile" cc="bt" country="Bhutan" operator="B-Mobile / Bhutan Telecom Ltd." status="Operational" 77 bands="GSM 900 / GSM 1800" brand="TashiCell" cc="bt" country="Bhutan" operator="Tashi InfoComm Limited" status="Operational" 00-99 404 01 bands="GSM 900" brand="Vodafone IN" cc="in" country="India" operator="Haryana" status="Operational" 02 bands="GSM 900" brand="AirTel" cc="in" country="India" operator="Punjab" status="Operational" 03 bands="GSM 900" brand="AirTel" cc="in" country="India" operator="Himachal Pradesh" status="Operational" 04 bands="GSM 1800" brand="IDEA" cc="in" country="India" operator="Delhi & NCR" status="Operational" 05 bands="GSM 900" brand="Vodafone IN" cc="in" country="India" operator="Gujarat" status="Operational" 07 bands="GSM 900" brand="IDEA" cc="in" country="India" operator="Andhra Pradesh" status="Operational" 09 bands="GSM 900" brand="Reliance" cc="in" country="India" operator="Assam" status="Operational" 10 bands="GSM 900" brand="AirTel" cc="in" country="India" operator="Delhi & NCR" status="Operational" 11 bands="GSM 900 / GSM 1800" brand="Vodafone IN" cc="in" country="India" operator="Delhi & NCR" status="Operational" 12 bands="GSM 900" brand="IDEA" cc="in" country="India" operator="Haryana" status="Operational" 13 bands="GSM 1800" brand="Vodafone IN" cc="in" country="India" operator="Andhra Pradesh" status="Operational" 14 bands="GSM 900 / GSM 1800" brand="IDEA" cc="in" country="India" operator="Punjab" status="Operational" 15 bands="GSM 900" brand="Vodafone IN" cc="in" country="India" operator="Uttar Pradesh (East)" status="Operational" 16 bands="GSM 900" brand="Airtel" cc="in" country="India" operator="North East" status="Operational" 17 bands="GSM 900 / GSM 1800" brand="AIRCEL" cc="in" country="India" operator="West Bengal" status="Operational" 18 bands="GSM 900" brand="Reliance" cc="in" country="India" operator="Himachal Pradesh" status="Operational" 19 bands="GSM 900 / GSM 1800" brand="IDEA" cc="in" country="India" operator="Kerala" status="Operational" 20 bands="GSM 900 / UMTS 2100" brand="Vodafone IN" cc="in" country="India" operator="Mumbai" status="Operational" 21 bands="GSM 900" brand="Loop Mobile" cc="in" country="India" operator="Mumbai" status="Operational" 22 bands="GSM 900" brand="IDEA" cc="in" country="India" operator="Maharashtra & Goa" status="Operational" 24 bands="GSM 900" brand="IDEA" cc="in" country="India" operator="Gujarat" status="Operational" 25 bands="GSM 900 / GSM 1800" brand="AIRCEL" cc="in" country="India" operator="Bihar" status="Operational" 27 bands="GSM 900" brand="Vodafone IN" cc="in" country="India" operator="Maharashtra & Goa" status="Operational" 28 bands="GSM 900" brand="AIRCEL" cc="in" country="India" operator="Orissa" status="Operational" 29 bands="GSM 900" brand="AIRCEL" cc="in" country="India" operator="Assam" status="Operational" 30 bands="GSM 900 / GSM 1800" brand="Vodafone IN" cc="in" country="India" operator="Kolkata" status="Operational" 31 bands="GSM 900" brand="AirTel" cc="in" country="India" operator="Kolkata" status="Operational" 34 bands="GSM 900 / UMTS 2100" brand="CellOne" cc="in" country="India" operator="Haryana" status="Operational" 36 bands="GSM 900" brand="Reliance" cc="in" country="India" operator="Bihar & Jharkhand" status="Operational" 37 bands="GSM 900 / UMTS 2100" brand="Aircel" cc="in" country="India" operator="Jammu & Kashmir" status="Operational" 38 bands="GSM 900 / UMTS 2100" brand="CellOne" cc="in" country="India" operator="Assam" status="Operational" 40 brand="AirTel" cc="in" country="India" operator="Chennai" status="Operational" 41 bands="GSM 900" brand="Aircel" cc="in" country="India" operator="Chennai" status="Operational" 42 bands="GSM 900" brand="Aircel" cc="in" country="India" operator="Tamil Nadu" status="Operational" 43 bands="GSM 900" brand="Vodafone IN" cc="in" country="India" operator="Tamil Nadu" status="Operational" 44 bands="GSM 900" brand="IDEA" cc="in" country="India" operator="Karnataka" status="Operational" 45 bands="GSM" brand="Airtel" cc="in" country="India" operator="Karnataka" status="Operational" 46 bands="GSM 900" brand="Vodafone IN" cc="in" country="India" operator="Kerala" status="Operational" 48 bands="GSM 900" brand="Dishnet Wireless" cc="in" country="India" operator="" status="Operational" 49 bands="GSM 900" brand="Airtel" cc="in" country="India" operator="Andhra Pradesh" status="Operational" 50 bands="GSM 900" brand="Reliance" cc="in" country="India" operator="North East" status="Operational" 51 bands="GSM 900 / UMTS 2100" brand="CellOne" cc="in" country="India" operator="Himachal Pradesh" status="Operational" 52 bands="GSM 900" brand="Reliance" cc="in" country="India" operator="Orissa" status="Operational" 53 bands="GSM 900 / UMTS 2100" brand="CellOne" cc="in" country="India" operator="Punjab" status="Operational" 54 bands="GSM 900 / UTMS 2100" brand="CellOne" cc="in" country="India" operator="Uttar Pradesh (West)" status="Operational" 55 bands="GSM 900 / UTMS 2100" brand="CellOne" cc="in" country="India" operator="Uttar Pradesh (East)" status="Operational" 56 bands="GSM 900" brand="IDEA" cc="in" country="India" operator="Uttar Pradesh (West)" status="Operational" 57 bands="GSM 900 / UMTS 2100" brand="CellOne" cc="in" country="India" operator="Gujarat" status="Operational" 58 bands="GSM 900 / UMTS 2100" brand="CellOne" cc="in" country="India" operator="Madhya Pradesh & Chhattisgarh" status="Operational" 59 bands="GSM 900 / UMTS 2100" brand="CellOne" cc="in" country="India" operator="Rajasthan" status="Operational" 60 bands="GSM 900" brand="Vodafone IN" cc="in" country="India" operator="Rajasthan" status="Operational" 62 bands="GSM 900 / UMTS 2100" brand="CellOne" cc="in" country="India" operator="Jammu & Kashmir" status="Operational" 64 bands="GSM 900 / UMTS 2100" brand="CellOne" cc="in" country="India" operator="Chennai" status="Operational" 66 bands="GSM 900 / UMTS 2100" brand="CellOne" cc="in" country="India" operator="Maharashtra & Goa" status="Operational" 67 bands="GSM 900 / UMTS 2100" brand="Reliance" cc="in" country="India" operator="Madhya Pradesh & Chhattisgarh" status="Operational" 68 bands="GSM 900 / UMTS 2100" brand="DOLPHIN" cc="in" country="India" operator="Delhi & NCR" status="Operational" 69 bands="GSM 900 / UMTS 2100" brand="DOLPHIN" cc="in" country="India" operator="Mumbai" status="Operational" 70 brand="AirTel" cc="in" country="India" operator="Rajasthan" status="Operational" 71 bands="GSM 900 / UMTS 2100" brand="CellOne" cc="in" country="India" operator="Karnataka (Bangalore)" status="Operational" 72 bands="GSM 900 / UMTS 2100" brand="CellOne" cc="in" country="India" operator="Kerala" status="Operational" 73 bands="GSM 900 / UMTS 2100" brand="CellOne" cc="in" country="India" operator="Andhra Pradesh" status="Operational" 74 bands="GSM 900 / UMTS 2100" brand="CellOne" cc="in" country="India" operator="West Bengal" status="Operational" 75 bands="GSM 900 / UMTS 2100" brand="CellOne" cc="in" country="India" operator="Bihar" status="Operational" 76 bands="GSM 900 / UMTS 2100" brand="CellOne" cc="in" country="India" operator="Orissa" status="Operational" 77 bands="GSM 900 / UMTS 2100" brand="CellOne" cc="in" country="India" operator="North East" status="Operational" 78 bands="GSM 900 / UMTS 2100" brand="Idea Cellular Ltd" cc="in" country="India" operator="Madhya Pradesh & Chattishgarh" status="Operational" 79 bands="GSM 900 / UMTS 2100" brand="CellOne" cc="in" country="India" operator="Andaman Nicobar" status="Operational" 80 bands="GSM900 / UMTS 2100" brand="CellOne" cc="in" country="India" operator="Tamil Nadu" status="Operational" 81 bands="GSM 900 / UMTS 2100" brand="CellOne" cc="in" country="India" operator="Kolkata" status="Operational" 82 bands="" brand="Idea" cc="in" country="India" operator="Himachal Pradesh" status="Operational" 83 bands="GSM 1800" brand="Reliance" cc="in" country="India" operator="Kolkata" status="Operational" 84 bands="GSM 1800" brand="Vodafone IN" cc="in" country="India" operator="Chennai" status="Operational" 85 bands="GSM 1800" brand="Reliance" cc="in" country="India" operator="West Bengal" status="Operational" 86 bands="" brand="Vodafone IN" cc="in" country="India" operator="Karnataka" status="Operational" 87 bands="" brand="IDEA" cc="in" country="India" operator="Rajasthan" status="Operational" 88 bands="" brand="Vodafone IN" cc="in" country="India" operator="Vodafone Punjab" status="Operational" 89 bands="" brand="Idea" cc="in" country="India" operator="Uttar Pradesh (East)" status="Operational" 90 bands="GSM 1800" brand="AirTel" cc="in" country="India" operator="Maharashtra" status="Operational" 91 bands="GSM 900" brand="AIRCEL" cc="in" country="India" operator="Kolkata" status="Operational" 92 bands="GSM 1800 / UMTS 2100" brand="AirTel" cc="in" country="India" operator="Mumbai" status="Operational" 93 bands="GSM 1800" brand="AirTel" cc="in" country="India" operator="Madhya Pradesh" status="Operational" 94 brand="AirTel" cc="in" country="India" operator="Tamil Nadu" status="Operational" 95 bands="GSM 1800" brand="AirTel" cc="in" country="India" operator="Kerala" status="Operational" 96 bands="GSM 1800" brand="AirTel" cc="in" country="India" operator="Haryana" status="Operational" 97 brand="AirTel" cc="in" country="India" operator="Uttar Pradesh (West)" status="Operational" 98 brand="AirTel" cc="in" country="India" operator="Gujarat" status="Operational" 00-99 405 01 bands="GSM 1800" brand="Reliance" cc="in" country="India" operator="Andhra Pradesh" status="Operational" 025 bands="CDMA 2000 / GSM 1800 / UMTS 2100" brand="TATA DOCOMO" cc="in" country="India" operator="Andhra Pradesh" status="Operational" 026 bands="CDMA 2000" brand="TATA DOCOMO" cc="in" country="India" operator="Assam" status="Operational" 027 bands="CDMA 2000 / GSM 1800" brand="TATA DOCOMO" cc="in" country="India" operator="Bihar/Jharkhand" status="Operational" 028 bands="CDMA 2000 / GSM 1800" brand="TATA DOCOMO" cc="in" country="India" operator="Chennai" status="Operational" 029 bands="CDMA 2000" brand="TATA DOCOMO" cc="in" country="India" operator="Delhi" status="Operational" 03 bands="GSM 1800" brand="Reliance" cc="in" country="India" operator="Bihar" status="Operational" 030 bands="CDMA 2000 / GSM 1800 / UMTS 2100" brand="TATA DOCOMO" cc="in" country="India" operator="Gujarat" status="Operational" 031 bands="CDMA 2000 / GSM 1800 / UMTS 2100" brand="TATA DOCOMO" cc="in" country="India" operator="Haryana" status="Operational" 032 bands="CDMA 2000 / GSM 1800 / UMTS 2100" brand="TATA DOCOMO" cc="in" country="India" operator="Himachal Pradesh" status="Operational" 033 bands="CDMA 2000" brand="TATA DOCOMO" cc="in" country="India" operator="Jammu & Kashmir" status="Operational" 034 bands="CDMA 2000 / GSM 1800 / UMTS 2100" brand="TATA DOCOMO" cc="in" country="India" operator="Karnataka" status="Operational" 035 bands="CDMA 2000 / GSM 1800 / UMTS 2100" brand="TATA DOCOMO" cc="in" country="India" operator="Kerala" status="Operational" 036 bands="CDMA 2000 / GSM 1800" brand="TATA DOCOMO" cc="in" country="India" operator="Kolkata" status="Operational" 037 bands="CDMA 2000 / GSM 1800 / UMTS 2100" brand="TATA DOCOMO" cc="in" country="India" operator="Maharashtra & Goa" status="Operational" 038 bands="CDMA 2000 / GSM 1800 / UMTS 2100" brand="TATA DOCOMO" cc="in" country="India" operator="Madhya Pradesh" status="Operational" 039 bands="CDMA 2000 / GSM 1800" brand="TATA DOCOMO" cc="in" country="India" operator="Mumbai" status="Operational" 04 bands="GSM 1800" brand="Reliance" cc="in" country="India" operator="Chennai" status="Operational" 041 bands="CDMA 2000 / GSM 1800" brand="TATA DOCOMO" cc="in" country="India" operator="Orissa" status="Operational" 042 bands="CDMA 2000 / GSM 1800 / UMTS 2100" brand="TATA DOCOMO" cc="in" country="India" operator="Punjab" status="Operational" 043 bands="CDMA 2000 / GSM 1800 / UMTS 2100" brand="TATA DOCOMO" cc="in" country="India" operator="Rajasthan" status="Operational" 044 bands="CDMA 2000 / GSM 1800" brand="TATA DOCOMO" cc="in" country="India" operator="Tamil Nadu including Chennai" status="Operational" 045 bands="CDMA 2000 / GSM 1800" brand="TATA DOCOMO" cc="in" country="India" operator="Uttar Pradesh (E)" status="Operational" 046 bands="CDMA 2000 / GSM 1800 / UMTS 2100" brand="TATA DOCOMO" cc="in" country="India" operator="Uttar Pradesh (W) & Uttarkhand" status="Operational" 047 bands="CDMA 2000 / GSM 1800" brand="TATA DOCOMO" cc="in" country="India" operator="West Bengal" status="Operational" 05 bands="GSM 1800" brand="Reliance" cc="in" country="India" operator="Delhi & NCR" status="Operational" 06 bands="GSM 1800" brand="Reliance" cc="in" country="India" operator="Gujarat" status="Operational" 07 bands="GSM" brand="Reliance" cc="in" country="India" operator="Haryana" status="Operational" 08 bands="GSM" brand="Reliance" cc="in" country="India" operator="Himachal Pradesh" status="Operational" 09 bands="GSM 1800 / UMTS 2100" brand="Reliance" cc="in" country="India" operator="Jammu & Kashmir" status="Operational" 10 bands="GSM" brand="Reliance" cc="in" country="India" operator="Karnataka" status="Operational" 11 bands="GSM" brand="Reliance" cc="in" country="India" operator="Kerala" status="Operational" 12 bands="GSM" brand="Reliance" cc="in" country="India" operator="Kolkata" status="Operational" 13 bands="GSM" brand="Reliance" cc="in" country="India" operator="Maharashtra & Goa" status="Operational" 14 bands="GSM" brand="Reliance" cc="in" country="India" operator="Madhya Pradesh" status="Operational" 15 bands="GSM 1800 / UMTS 2100" brand="Reliance" cc="in" country="India" operator="Mumbai" status="Operational" 17 bands="GSM" brand="Reliance" cc="in" country="India" operator="Orissa" status="Operational" 18 bands="GSM" brand="Reliance" cc="in" country="India" operator="Punjab" status="Operational" 19 bands="GSM" brand="Reliance" cc="in" country="India" operator="Rajasthan" status="Operational" 20 bands="GSM" brand="Reliance" cc="in" country="India" operator="Tamil Nadu" status="Operational" 21 bands="GSM" brand="Reliance" cc="in" country="India" operator="Uttar Pradesh (East)" status="Operational" 22 bands="GSM" brand="Reliance" cc="in" country="India" operator="Uttar Pradesh (West)" status="Operational" 23 bands="GSM" brand="Reliance" cc="in" country="India" operator="West Bengal" status="Operational" 51 bands="GSM 900" brand="AirTel" cc="in" country="India" operator="West Bengal" status="Operational" 52 bands="GSM 900" brand="AirTel" cc="in" country="India" operator="Bihar & Jharkhand" status="Operational" 53 bands="GSM" brand="AirTel" cc="in" country="India" operator="Orissa" status="Operational" 54 bands="GSM 900" brand="AirTel" cc="in" country="India" operator="Uttar Pradesh (East)" status="Operational" 55 bands="GSM 900 / UTMS 2100" brand="Airtel" cc="in" country="India" operator="Jammu & Kashmir" status="Operational" 56 bands="GSM 900 / GSM 1800" brand="AirTel" cc="in" country="India" operator="Assam" status="Operational" 66 bands="GSM 900 / GSM 1800" brand="Vodafone IN" cc="in" country="India" operator="Uttar Pradesh (West)" status="Operational" 67 brand="Vodafone IN" cc="in" country="India" operator="West Bengal" status="Operational" 70 bands="GSM 1800" brand="IDEA" cc="in" country="India" operator="Bihar & Jharkhand" status="Operational" 750 bands="GSM 1800" brand="Vodafone IN" cc="in" country="India" operator="Jammu & Kashmir" status="Operational" 751 bands="GSM 1800" brand="Vodafone IN" cc="in" country="India" operator="Assam" status="Operational" 752 bands="GSM 1800" brand="Vodafone IN" cc="in" country="India" operator="Bihar & Jharkhand" status="Operational" 753 bands="GSM 1800" brand="Vodafone IN" cc="in" country="India" operator="Orissa" status="Operational" 754 bands="GSM 1800" brand="Vodafone IN" cc="in" country="India" operator="Himachal Pradesh" status="Operational" 755 bands="GSM 1800" brand="Vodafone IN" cc="in" country="India" operator="North East" status="Operational" 756 bands="GSM 1800" brand="Vodafone IN" cc="in" country="India" operator="Madhya Pradesh & Chhattisgarh" status="Operational" 799 bands="GSM 900 / GSM 1800" brand="IDEA" cc="in" country="India" operator="Mumbai" status="Operational" 800 bands="GSM 1800" brand="AIRCEL" cc="in" country="India" operator="Delhi & NCR" status="Operational" 801 bands="GSM 1800" brand="AIRCEL" cc="in" country="India" operator="Andhra Pradesh" status="Operational" 802 bands="GSM 1800" brand="AIRCEL" cc="in" country="India" operator="Gujarat" status="Not operational" 803 bands="GSM 1800" brand="AIRCEL" cc="in" country="India" operator="Karnataka" status="Operational" 804 bands="GSM 1800" brand="AIRCEL" cc="in" country="India" operator="Maharashtra & Goa" status="Operational" 805 bands="GSM 1800" brand="AIRCEL" cc="in" country="India" operator="Mumbai" status="Operational" 806 bands="GSM 1800" brand="AIRCEL" cc="in" country="India" operator="Rajasthan" status="Operational" 807 bands="GSM 1800" brand="AIRCEL" cc="in" country="India" operator="Haryana" status="Not operational" 808 bands="GSM 1800" brand="AIRCEL" cc="in" country="India" operator="Madhya Pradesh" status="Not operational" 809 bands="GSM 1800" brand="AIRCEL" cc="in" country="India" operator="Kerala" status="Operational" 810 bands="GSM 1800" brand="AIRCEL" cc="in" country="India" operator="Uttar Pradesh (East)" status="Operational" 811 bands="GSM" brand="AIRCEL" cc="in" country="India" operator="Uttar Pradesh (West)" status="Operational" 812 bands="GSM" brand="AIRCEL" cc="in" country="India" operator="Punjab" status="Not operational" 818 bands="GSM" brand="Uninor" cc="in" country="India" operator="Uttar Pradesh (West)" status="Operational" 819 bands="GSM" brand="Uninor" cc="in" country="India" operator="Andhra Pradesh" status="Operational" 820 bands="GSM 1800" brand="Uninor" cc="in" country="India" operator="Karnataka" status="Operational" 821 bands="GSM 1800" brand="Uninor" cc="in" country="India" operator="Kerala" status="Operational" 822 bands="GSM" brand="Uninor" cc="in" country="India" operator="Kolkata" status="Operational" 824 bands="GSM 1800" brand="Videocon Datacom" cc="in" country="India" operator="Assam" status="Reserved" 827 bands="GSM 1800" brand="Videocon Datacom" cc="in" country="India" operator="Gujarat" status="Operational" 834 bands="GSM 1800" brand="Videocon Datacom" cc="in" country="India" operator="Madhya Pradesh" status="Reserved" 840 bands="4G" brand="Jio" cc="in" country="India" operator="West Bengal" status="Launching Soon" 844 bands="GSM" brand="Uninor" cc="in" country="India" operator="Delhi & NCR" status="Not operational" 845 bands="GSM 1800" brand="IDEA" cc="in" country="India" operator="Assam" status="Operational" 846 bands="GSM 1800 / UTMS 2100" brand="IDEA" cc="in" country="India" operator="Jammu & Kashmir" status="Operational" 847 bands="GSM 1800" brand="IDEA" cc="in" country="India" operator="Karnataka" status="Operational" 848 bands="GSM 1800" brand="IDEA" cc="in" country="India" operator="Kolkata" status="Operational" 849 bands="GSM 1800" brand="IDEA" cc="in" country="India" operator="North East" status="Operational" 850 bands="GSM 1800" brand="IDEA" cc="in" country="India" operator="Orissa" status="Operational" 851 bands="GSM 1800" brand="IDEA" cc="in" country="India" operator="Punjab" status="Operational" 852 bands="GSM 1800" brand="IDEA" cc="in" country="India" operator="Tamil Nadu" status="Operational" 853 bands="GSM 1800" brand="IDEA" cc="in" country="India" operator="West Bengal" status="Operational" 854 bands="4G" brand="Jio" cc="in" country="India" operator="Andra Pradesh" status="Launching Soon" 855 bands="4G" brand="Jio" cc="in" country="India" operator="Assam" status="Launching Soon" 856 bands="4G" brand="Jio" cc="in" country="India" operator="Bhiar" status="Launching Soon" 857 bands="4G" brand="Jio" cc="in" country="India" operator="Gujarat" status="Launching Soon" 858 bands="4G" brand="Jio" cc="in" country="India" operator="Haryana" status="Launching Soon" 859 bands="4G" brand="Jio" cc="in" country="India" operator="Himachal Pradesh" status="Launching Soon" 860 bands="4G" brand="Jio" cc="in" country="India" operator="Jammu Kashmir" status="Launching Soon" 861 bands="4G" brand="Jio" cc="in" country="India" operator="Karnataka" status="Launching Soon" 862 bands="4G" brand="Jio" cc="in" country="India" operator="Kerala" status="Launching Soon" 863 bands="4G" brand="Jio" cc="in" country="India" operator="Madhyya Pradesh" status="Launching Soon" 864 bands="4G" brand="Jio" cc="in" country="India" operator="Maharashtra" status="Launching Soon" 865 bands="4G" brand="Jio" cc="in" country="India" operator="North East" status="Launching Soon" 866 bands="4G" brand="Jio" cc="in" country="India" operator="Orissa" status="Launching Soon" 867 bands="4G" brand="Jio" cc="in" country="India" operator="Punjab" status="Launching Soon" 868 bands="4G" brand="Jio" cc="in" country="India" operator="Rajasthan" status="Launching Soon" 869 bands="4G" brand="Jio" cc="in" country="India" operator="Tamil Nadu Chennai" status="Launching Soon" 870 bands="4G" brand="Jio" cc="in" country="India" operator="Uttar Pradesh West" status="Launching Soon" 871 bands="4G" brand="Jio" cc="in" country="India" operator="Uttar Pradesh East" status="Launching Soon" 872 bands="4G" brand="Jio" cc="in" country="India" operator="Delhi" status="Launching Soon" 873 bands="4G" brand="Jio" cc="in" country="India" operator="Kolkatta" status="Launching Soon" 874 bands="4G" brand="Jio" cc="in" country="India" operator="Mumbai" status="Launching Soon" 875 bands="GSM 1800" brand="Uninor" cc="in" country="India" operator="Assam" status="Reserved" 880 bands="GSM 1800" brand="Uninor" cc="in" country="India" operator="West Bengal" status="Operational" 881 bands="GSM 1800" brand="S Tel" cc="in" country="India" operator="Assam" status="Reserved" 908 bands="GSM 1800" brand="IDEA" cc="in" country="India" operator="Andhra Pradesh" status="Operational" 909 bands="GSM 1800" brand="IDEA" cc="in" country="India" operator="Delhi" status="Operational" 910 bands="GSM 1800" brand="IDEA" cc="in" country="India" operator="Haryana" status="Operational" 911 bands="GSM 1800" brand="IDEA" cc="in" country="India" operator="Maharashtra" status="Operational" 912 bands="GSM 1800" brand="Etisalat DB(cheers)" cc="in" country="India" operator="Andhra Pradesh" status="Non operational" 913 bands="GSM 1800" brand="Etisalat DB(cheers)" cc="in" country="India" operator="Delhi & NCR" status="Non operational" 914 bands="GSM 1800" brand="Etisalat DB(cheers)" cc="in" country="India" operator="Gujarat" status="Non operational" 917 bands="GSM 1800" brand="Etisalat DB(cheers)" cc="in" country="India" operator="Kerala" status="Non operational" 927 bands="" brand="Uninor" cc="in" country="India" operator="Gujarat" status="operational" 929 bands="GSM 1800" brand="Uninor" cc="in" country="India" operator="Maharashtra" status="Operational" 00-99 410 01 bands="GSM 900 / GSM 1800" brand="Mobilink" cc="pk" country="Pakistan" operator="Mobilink-PMCL" status="Operational" 03 bands="GSM 900/ GSM 1800" brand="Ufone" cc="pk" country="Pakistan" operator="Pakistan Telecommunication Mobile Ltd" status="Operational" 04 bands="GSM 900 / GSM 1800" brand="Zong" cc="pk" country="Pakistan" operator="China Mobile" status="Operational" 06 bands="GSM 900 / GSM 1800" brand="Telenor" cc="pk" country="Pakistan" operator="Telenor Pakistan" status="Operational" 07 bands="GSM 900 / GSM 1800" brand="Warid" cc="pk" country="Pakistan" operator="WaridTel" status="Operational" 00-99 412 01 bands="GSM 900 / GSM 1800" brand="AWCC" cc="af" country="Afghanistan" operator="Afghan Wireless Communication Company" status="Operational" 20 bands="GSM 900" brand="Roshan" cc="af" country="Afghanistan" operator="Telecom Development Company Afghanistan Ltd." status="Operational" 40 bands="GSM 900 / GSM 1800/ UMTS 2100" brand="MTN" cc="af" country="Afghanistan" operator="MTN Group Afghanistan" status="Operational" 50 bands="GSM 900 / GSM 1800 /UMTS 2100" brand="Etisalat" cc="af" country="Afghanistan" operator="Etisalat Afghanistan" status="Operational" 55 bands="CDMA 800 /" brand="WASEL" cc="af" country="Afghanistan" operator="WASEL Afghanistan" status="Operational" 00-99 413 01 bands="GSM-900/1800 (GPRS, EDGE)
    2100 MHz UMTS, HSPA, HSPA+, DC-HSPA+
    1800 MHz FD-LTE" brand="Mobitel" cc="lk" country="Sri Lanka" operator="Mobitel (Pvt) Ltd" status="Operational" 02 bands="GSM-900/1800 (GPRS, EDGE)
    2100 MHz UMTS, HSPA, HSPA+, DC-HSPA+
    1800 MHz FD-LTE" brand="Dialog" cc="lk" country="Sri Lanka" operator="Dialog Axiata PLC" status="Operational" 03 bands="GSM-900/1800 (GPRS, EDGE)
    2100 MHz UMTS, HSPA, HSPA+, DC-HSPA+
    1800 MHz FD-LTE (Planned)" brand="Etisalat" cc="lk" country="Sri Lanka" operator="Etisalat Lanka (Pvt) Ltd" status="Operational" 04 bands="LTE-2300, CDMA-800" brand="Lanka Bell" cc="lk" country="Sri Lanka" operator="Lanka Bell Ltd" status="Operational" 05 bands="GSM-900/1800 (GPRS, EDGE)
    2100 MHz UMTS, HSPA, HSPA+" brand="Airtel" cc="lk" country="Sri Lanka" operator="Bharti Airtel Lanka (Pvt) Ltd" status="Operational" 08 bands="GSM-900/1800 (GPRS, EDGE)
    2100 MHz UMTS, HSPA" brand="Hutch" cc="lk" country="Sri Lanka" operator="Hutchison Telecommunications Lanka (Pvt) Ltd" status="Operational" 00-99 414 01 bands="GSM 900" brand="MPT" cc="mm" country="Myanmar" operator="Myanmar Post and Telecommunication" status="Operational" 00-99 415 01 bands="GSM 900" brand="Alfa" cc="lb" country="Lebanon" operator="MIC 1" status="Operational" 03 bands="GSM 900" brand="mtc touch" cc="lb" country="Lebanon" operator="MIC 2" status="Operational" 05 bands="GSM 900" brand="Ogero Mobile" cc="lb" country="Lebanon" operator="Ogero Telecom" status="Planned" 00-99 416 01 bands="GSM 900" brand="zain JO" cc="jo" country="Jordan" operator="Jordan Mobile Telephone Services" status="Operational" 03 bands="GSM 1800" brand="Umniah" cc="jo" country="Jordan" operator="Umniah Mobile Company" status="Operational" 74 bands="iDEN 800" brand="XPress Telecom" cc="jo" country="Jordan" status="Operational" 77 bands="GSM 900" brand="Orange" cc="jo" country="Jordan" operator="Petra Jordanian Mobile Telecommunications Company (MobileCom)" status="Operational" 00-99 417 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Syriatel" cc="sy" country="Syria" operator="Syriatel Mobile Telecom" status="Operational" 02 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="MTN" cc="sy" country="Syria" operator="MTN Syria" status="Operational" 00-99 418 05 bands="GSM 900" brand="Asia Cell" cc="iq" country="Iraq" operator="Asia Cell Telecommunications Company" status="Operational" 08 bands="GSM 900" brand="SanaTel" cc="iq" country="Iraq" status="Operational" 20 bands="GSM 900 / GSM 1800" brand="Zain" cc="iq" country="Iraq" operator="Zain Iraq" status="Operational" 30 bands="GSM 900" brand="Zain" cc="iq" country="Iraq" operator="Zain Iraq" status="Operational" 40 bands="GSM 900" brand="Korek" cc="iq" country="Iraq" operator="Telecom Ltd" status="Operational" 45 bands="UMTS" brand="Mobitel" cc="iq" country="Iraq" operator="Mobitel Co. Ltd." status="Operational" 62 bands="CDMA2000 EVDO RevA 800/1900" brand="Itisaluna" cc="iq" country="Iraq" operator="Itisaluna Wireless CO." status="Operational" 92 bands="CDMA" brand="Omnnea" cc="iq" country="Iraq" operator="Omnnea Wireless" status="Operational" 00-99 419 02 bands="GSM 900 / UMTS 2100" brand="zain KW" cc="kw" country="Kuwait" operator="Zain Kuwait" status="Operational" 03 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Wataniya" cc="kw" country="Kuwait" operator="National Mobile Telecommunications" status="Operational" 04 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Viva" cc="kw" country="Kuwait" operator="Kuwait Telecommunication Company" status="Operational" 00-99 420 01 bands="GSM 900 / UMTS 2100 / LTE 2300" brand="Al Jawal (STC )" cc="sa" country="Saudi Arabia" operator="Saudi Telecom Company" status="Operational" 03 bands="GSM 900 / UMTS 2100 / LTE 2600" brand="Mobily" cc="sa" country="Saudi Arabia" operator="Etihad Etisalat Company" status="Operational" 04 bands="GSM 900 / GSM 1800 / UMTS 2100 / LTE 1800/ LTE 2600" brand="Zain SA" cc="sa" country="Saudi Arabia" operator="Zain Saudi Arabia" status="Operational" 21 bands="RGSM 900" brand="RGSM" cc="sa" country="Saudi Arabia" operator="Saudi Railways GSM" status="Operational" 00-99 421 01 bands="GSM 900" brand="SabaFon" cc="ye" country="Yemen" status="Operational" 02 bands="GSM 900" brand="MTN" cc="ye" country="Yemen" operator="Spacetel Yemen" status="Operational" 03 bands="CDMA2000 800" brand="Yemen Mobile" cc="ye" country="Yemen" operator="Yemen Mobile" status="Operational" 04 bands="GSM 900" brand="HiTS-UNITEL" cc="ye" country="Yemen" operator="Y" status="Operational" 00-99 422 02 bands="GSM 900 / GSM 1800" brand="Oman Mobile" cc="om" country="Oman" operator="Oman Telecommunications Company" status="Operational" 03 bands="GSM 900 / GSM 1800" brand="Nawras" cc="om" country="Oman" operator="Omani Qatari Telecommunications Company SAOC" status="Operational" 00-99 424 02 bands="GSM 900 / UMTS 2100" brand="Etisalat" cc="ae" country="United Arab Emirates" operator="E mirates Telecom Corp" status="Operational" 03 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="du" cc="ae" country="United Arab Emirates" operator="Emirates Integrated Telecommunications Company" status="Operational" 00-99 425 01 bands="GSM 900 / UMTS 900 / GSM 1800 / UMTS 2100" brand="Orange" cc="il" country="Israel" operator="Partner Communications Company Ltd" status="Operational" 02 bands="UMTS 850 / GSM 1800 / UMTS 2100" brand="Cellcom" cc="il" country="Israel" operator="Cellcom Israel Ltd" status="Operational" 03 bands="CDMA2000 800 / UMTS 850 / UMTS 2100" brand="Pelephone" cc="il" country="Israel" operator="Pelephone Communications Ltd." status="Operational" 05 bands="GSM 900" brand="Jawwal" cc="ps" country="Palestine, State of" operator="Palestine Cellular Communications, Ltd." status="Operational" 06 bands="GSM 900 / GSM 1800" brand="Wataniya" cc="ps" country="Palestine, State of" operator="Wataniya Palestine Mobile Telecommunications Company" status="Operational" 07 bands="iDEN 800 / UMTS 2100" brand="Hot Mobile" cc="il" country="Israel" operator="Hot Mobile Ltd" status="Operational" 08 bands="UMTS 2100" brand="Golan Telecom" cc="il" country="Israel" status="Operational" 14 bands="GSM 900 / UMTS 900 / GSM 1800 / UMTS 2100" brand="Youphone" cc="il" country="Israel" status="Operational" 15 bands="UMTS 850 / GSM 1800 / UMTS 2100" brand="Home Cellular" cc="il" country="Israel" status="Operational" 16 bands="UMTS 850 / UMTS 2100" brand="Rami Levy" cc="il" country="Israel" status="Operational" 18 bands="UMTS 850 / UMTS 2100" brand="Cellact Communications" cc="il" country="Israel" operator="Cellact Communications Ltd." status="Operational" 00-99 426 01 bands="GSM 900 / GSM 1800 / LTE 1800" brand="Batelco" cc="bh" country="Bahrain" operator="Bahrain Telecommunications Company" status="Operational" 02 bands="GSM 900 / GSM 1800" brand="zain BH" cc="bh" country="Bahrain" operator="Zain Bahrain" status="Operational" 04 bands="GSM 900 / GSM 1800" brand="VIVA" cc="bh" country="Bahrain" operator="Viva Bahrain" status="Operational" 05 bands="GSM 900 / GSM 1800" brand="Batelco" cc="bh" country="Bahrain" operator="Bahrain Telecommunications Company" status="Operational" 00-99 427 01 bands="GSM 900 / GSM 1800" brand="ooredoo" cc="qa" country="Qatar" operator="ooredoo" status="Operational" 02 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Vodafone" cc="qa" country="Qatar" operator="Vodafone Qatar" status="Operational" 05 bands="TETRA 380" brand="Ministry of Interior" cc="qa" country="Qatar" operator="Ministry of Interior" status="Operational" 00-99 428 88 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Unitel" cc="mn" country="Mongolia" operator="Unitel LLC" status="Operational" 91 bands="CDMA2000 800 / UMTS 2100" brand="Skytel" cc="mn" country="Mongolia" operator="Skytel LLC" status="Operational" 98 bands="CDMA2000 450" brand="G.Mobile" cc="mn" country="Mongolia" operator="G-Mobile LLC" status="Operational" 99 bands="GSM 900 / UMTS 2100" brand="MobiCom" cc="mn" country="Mongolia" operator="Mobicom Corporation" status="Operational" 00-99 429 01 bands="GSM 900 / GSM 1800" brand="Namaste / NT Mobile" cc="np" country="Nepal" operator="Nepal Telecom" status="Operational" 02 bands="GSM 900 / GSM 1800" brand="Ncell" cc="np" country="Nepal" operator="Ncell Pvt. Ltd.Spice Nepal" status="Operational" 03 bands="CDMA2000 800" brand="Sky/C-Phone" cc="np" country="Nepal" operator="Nepal Telecom" status="Operational" 04 bands="GSM 900" brand="SmartCell" cc="np" country="Nepal" operator="Smart Telecom Pvt. Ltd." status="Operational" 00-99 432 11 bands="GSM 900 / GSM 1800" brand="IR-MCI" cc="ir" country="Iran" operator="Mobile Communications Company of Iran" status="Operational" 14 bands="GSM 900" brand="TKC" cc="ir" country="Iran" operator="KFZO" status="Operational" 19 bands="GSM 900" brand="MTCE" cc="ir" country="Iran" operator="Mobile Telecommunications Company of Esfahan" status="Operational" 20 bands="UMTS" brand="Rightel" cc="ir" country="Iran" status="Operational" 32 bands="GSM 900 / GSM 1800" brand="Taliya" cc="ir" country="Iran" operator="Rafsanjan Industrial Complex" status="Operational" 35 bands="GSM 900 / GSM 1800" brand="Irancell" cc="ir" country="Iran" operator="Irancell Telecommunications Services Company" status="Operational" 70 bands="GSM 900 / GSM 1800" brand="TCI" cc="ir" country="Iran" operator="Telephone Communications Company of Iran" status="Operational" 93 bands="GSM 1800" brand="Iraphone" cc="ir" country="Iran" operator="Iraphone" status="Operational" 00-99 434 01 bands="GSM 900 / GSM 1800" cc="uz" country="Uzbekistan" operator="Buztel" status="Not operational" 02 bands="GSM 900 / GSM 1800" cc="uz" country="Uzbekistan" operator="Uzmacom" status="Not operational" 03 bands="CDMA2000 450 EVDO Rev A" brand="UzMobile" cc="uz" country="Uzbekistan" operator="Uzbektelekom" status="Operational" 04 bands="GSM 900 / GSM 1800" brand="Beeline" cc="uz" country="Uzbekistan" operator="Unitel LLC" status="Operational" 05 bands="GSM 900 / GSM 1800" brand="Ucell" cc="uz" country="Uzbekistan" operator="Coscom" status="Operational" 06 bands="CDMA2000 800" brand="Perfectum Mobile" cc="uz" country="Uzbekistan" operator="RUBICON WIRELESS COMMUNICATION" status="Operational" 07 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="MTS" cc="uz" country="Uzbekistan" operator="Uzdunrobita" status="Operational" 00-99 436 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Tcell" cc="tj" country="Tajikistan" operator="JV Somoncom" status="Operational" 02 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Tcell" cc="tj" country="Tajikistan" operator="Indigo Tajikistan" status="Operational" 03 bands="GSM 900 / GSM 1800" brand="Megafon" cc="tj" country="Tajikistan" operator="TT Mobile" status="Operational" 04 bands="GSM 900 / GSM 1800 / UMTS 2100 / LTE 1800 / LTE 2100" brand="Babilon-M" cc="tj" country="Tajikistan" operator="Babilon-Mobile" status="Operational" 05 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Tacom" cc="tj" country="Tajikistan" operator="Vimpelcom" status="Operational" 12 bands="UMTS 2100" brand="Tcell" cc="tj" country="Tajikistan" operator="Indigo" status="" 00-99 437 01 bands="GSM 900 / GSM 1800" brand="Beeline" cc="kg" country="Kyrgyzstan" operator="Sky Mobile LLC" status="Operational" 03 bands="CDMA2000" brand="Fonex" cc="kg" country="Kyrgyzstan" operator="Aktel Ltd" status="Operational" 05 bands="GSM 900 / GSM 1800" brand="MegaCom" cc="kg" country="Kyrgyzstan" operator="Alfa Telecom CJSC" status="Operational" 09 bands="GSM 900 / GSM 1800" brand="O!" cc="kg" country="Kyrgyzstan" operator="NurTelecom LLC" status="Operational" 00-99 438 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="MTS (BARASH Communication)" cc="tm" country="Turkmenistan" operator="ES "MTS-Turkmenistan"" status="Operational" 02 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="TM-Cell" cc="tm" country="Turkmenistan" operator="Altyn Asyr" status="Operational" 00-99 440 00 bands="UMTS 1700" brand="eMobile" cc="jp" country="Japan" operator="EMOBILE Limited" status="Operational" 01 bands="UMTS / WCDMA / HSDPA / HSUPA / LTE (4G)" brand="NTT docomo" cc="jp" country="Japan" operator="NTT docomo" status="Operational" 02 bands="UMTS 2100" brand="NTT docomo" cc="jp" country="Japan" operator="NTT DoCoMo - Kansai" status="Operational" 03 bands="UMTS 2100" brand="NTT docomo" cc="jp" country="Japan" operator="NTT DoCoMo - Hokuriku" status="Operational" 04 bands="UMTS 900 / UMTS 2100" brand="SoftBank" cc="jp" country="Japan" operator="SoftBank Mobile Corp" status="Operational" 06 bands="UMTS 900 / UMTS 2100" brand="SoftBank" cc="jp" country="Japan" operator="SoftBank Mobile Corp" status="Operational" 07 bands="CDMA2000 / 1X EV-DO Rev.A" brand="KDDI" cc="jp" country="Japan" operator="KDDI Corporation" status="Operational" 08 bands="CDMA2000" brand="KDDI" cc="jp" country="Japan" operator="KDDI Corporation" status="Operational" 09 bands="UMTS 800 / UMTS 1700 / UMTS 2100" brand="NTT docomo" cc="jp" country="Japan" operator="NTT docomo - Kansai" status="Operational" 10 bands="UMTS 800 / UMTS 1700 / UMTS 2100 / WCDMA / HSDPA / HSUPA / LTE (4G)" brand="NTT docomo" cc="jp" country="Japan" operator="NTT docomo" status="Operational" 11 bands="UMTS 800 / UMTS 1700 / UMTS 2100" brand="NTT docomo" cc="jp" country="Japan" operator="NTT docomo - Tokai" status="Operational" 12 bands="UMTS / WCDMA / HSDPA / HSUPA / LTE (4G)" brand="NTT docomo" cc="jp" country="Japan" operator="NTT docomo" status="Operational" 13 bands="UMTS / WCDMA / HSDPA / HSUPA / LTE (4G)" brand="NTT docomo" cc="jp" country="Japan" operator="NTT docomo" status="Operational" 14 bands="UMTS 800 / UMTS 1700 / UMTS 2100" brand="NTT docomo" cc="jp" country="Japan" operator="NTT docomo - Tohoku" status="Operational" 15 bands="UMTS / WCDMA / HSDPA / HSUPA / LTE (4G)" brand="NTT docomo" cc="jp" country="Japan" operator="NTT docomo" status="Operational" 16 bands="UMTS / WCDMA / HSDPA / HSUPA / LTE (4G)" brand="NTT docomo" cc="jp" country="Japan" operator="NTT docomo" status="Operational" 17 bands="UMTS / WCDMA / HSDPA / HSUPA / LTE (4G)" brand="NTT docomo" cc="jp" country="Japan" operator="NTT docomo" status="Operational" 18 bands="UMTS 800 / UMTS 1700 / UMTS 2100" brand="NTT docomo" cc="jp" country="Japan" operator="NTT docomo - Tokai" status="Operational" 19 bands="UMTS 800 / UMTS 1700 / UMTS 2100" brand="NTT docomo" cc="jp" country="Japan" operator="NTT docomo - Hokkaido" status="Operational" 20 bands="UMTS 900 / UMTS 2100" brand="SoftBank" cc="jp" country="Japan" operator="SoftBank Mobile Corp" status="Operational" 21 bands="UMTS / WCDMA / HSDPA / HSUPA / LTE (4G)" brand="NTT docomo" cc="jp" country="Japan" operator="NTT docomo" status="Operational" 22 bands="UMTS 800 / UMTS 1700 / UMTS 2100" brand="NTT docomo" cc="jp" country="Japan" operator="NTT docomo - Kansai" status="Operational" 23 bands="UMTS 800 / UMTS 1700 / UMTS 2100" brand="NTT docomo" cc="jp" country="Japan" operator="NTT docomo - Tokai" status="Operational" 24 bands="UMTS 800 / UMTS 1700 / UMTS 2100" brand="NTT docomo" cc="jp" country="Japan" operator="NTT docomo - Chugoku" status="Operational" 25 bands="UMTS 800 / UMTS 1700 / UMTS 2100" brand="NTT docomo" cc="jp" country="Japan" operator="NTT docomo - Hokkaido" status="Operational" 26 bands="UMTS 800 / UMTS 1700 / UMTS 2100" brand="NTT docomo" cc="jp" country="Japan" operator="NTT docomo - Kyushu" status="Operational" 27 bands="UMTS 800 / UMTS 1700 / UMTS 2100" brand="NTT docomo" cc="jp" country="Japan" operator="NTT docomo - Tohoku" status="Operational" 28 bands="UMTS 800 / UMTS 1700 / UMTS 2100" brand="NTT docomo" cc="jp" country="Japan" operator="NTT docomo - Shikoku" status="Operational" 29 bands="UMTS / WCDMA / HSDPA / HSUPA / LTE (4G)" brand="NTT docomo" cc="jp" country="Japan" operator="NTT docomo" status="Operational" 30 bands="UMTS / WCDMA / HSDPA / HSUPA / LTE (4G)" brand="NTT docomo" cc="jp" country="Japan" operator="NTT docomo" status="Operational" 31 bands="UMTS 800 / UMTS 1700 / UMTS 2100" brand="NTT docomo" cc="jp" country="Japan" operator="NTT docomo - Kansai" status="Operational" 32 bands="UMTS / WCDMA / HSDPA / HSUPA / LTE (4G)" brand="NTT docomo" cc="jp" country="Japan" operator="NTT docomo" status="Operational" 33 bands="UMTS 800 / UMTS 1700 / UMTS 2100" brand="NTT docomo" cc="jp" country="Japan" operator="NTT docomo - Tokai" status="Operational" 34 bands="UMTS 800 / UMTS 1700 / UMTS 2100" brand="NTT docomo" cc="jp" country="Japan" operator="NTT docomo - Kyushu" status="Operational" 35 bands="UMTS 800 / UMTS 1700 / UMTS 2100" brand="NTT DoCoMo" cc="jp" country="Japan" operator="NTT DoCoMo - Kansai" status="Operational" 36 bands="UMTS / WCDMA / HSDPA / HSUPA / LTE (4G)" brand="NTT DoCoMo" cc="jp" country="Japan" operator="NTT DoCoMo" status="Operational" 37 bands="UMTS / WCDMA / HSDPA / HSUPA / LTE (4G)" brand="NTT DoCoMo" cc="jp" country="Japan" operator="NTT DoCoMo" status="Operational" 38 bands="UMTS / WCDMA / HSDPA / HSUPA / LTE (4G)" brand="NTT DoCoMo" cc="jp" country="Japan" operator="NTT DoCoMo" status="Operational" 39 bands="UMTS / WCDMA / HSDPA / HSUPA / LTE (4G)" brand="NTT DoCoMo" cc="jp" country="Japan" operator="NTT DoCoMo" status="Operational" 40 bands="UMTS / HSPA+ / DC-HSDPA" brand="SoftBank" cc="jp" country="Japan" operator="SoftBank Mobile Corp" status="Operational" 41 bands="UMTS / HSPA+ / DC-HSDPA" brand="SoftBank" cc="jp" country="Japan" operator="SoftBank Mobile Corp" status="Operational" 42 bands="UMTS / HSPA+ / DC-HSDPA" brand="SoftBank" cc="jp" country="Japan" operator="SoftBank Mobile Corp" status="Operational" 43 bands="UMTS / HSPA+ / DC-HSDPA" brand="SoftBank" cc="jp" country="Japan" operator="SoftBank Mobile Corp" status="Operational" 44 bands="UMTS / HSPA+ / DC-HSDPA" brand="SoftBank" cc="jp" country="Japan" operator="SoftBank Mobile Corp" status="Operational" 45 bands="UMTS / HSPA+ / DC-HSDPA" brand="SoftBank" cc="jp" country="Japan" operator="SoftBank Mobile Corp" status="Operational" 46 bands="UMTS / HSPA+ / DC-HSDPA" brand="SoftBank" cc="jp" country="Japan" operator="SoftBank Mobile Corp" status="Operational" 47 bands="UMTS / HSPA+ / DC-HSDPA" brand="SoftBank" cc="jp" country="Japan" operator="SoftBank Mobile Corp" status="Operational" 48 bands="UMTS / HSPA+ / DC-HSDPA" brand="SoftBank" cc="jp" country="Japan" operator="SoftBank Mobile Corp" status="Operational" 49 bands="UMTS / HSDPA / LTE (4G)" brand="NTT DoCoMo" cc="jp" country="Japan" operator="NTT DoCoMo" status="Operational" 50 bands="WCDMA" brand="KDDI" cc="jp" country="Japan" operator="KDDI Corporation" status="Operational" 51 bands="WCDMA" brand="KDDI" cc="jp" country="Japan" operator="KDDI Corporation" status="Operational" 52 bands="WCDMA" brand="KDDI" cc="jp" country="Japan" operator="KDDI Corporation" status="Operational" 53 bands="WCDMA" brand="KDDI" cc="jp" country="Japan" operator="KDDI Corporation" status="Operational" 54 bands="WCDMA" brand="KDDI" cc="jp" country="Japan" operator="KDDI Corporation" status="Operational" 55 bands="WCDMA" brand="KDDI" cc="jp" country="Japan" operator="KDDI Corporation" status="Operational" 56 bands="WCDMA" brand="KDDI" cc="jp" country="Japan" operator="KDDI Corporation" status="Operational" 58 bands="UMTS 800 / UMTS 1700 / UMTS 2100" brand="NTT DoCoMo" cc="jp" country="Japan" operator="NTT DoCoMo - Kansai" status="Operational" 60 bands="UMTS 800 / UMTS 1700 / UMTS 2100" brand="NTT DoCoMo" cc="jp" country="Japan" operator="NTT DoCoMo - Kansai" status="Operational" 61 bands="UMTS 800 / UMTS 1700 / UMTS 2100" brand="NTT DoCoMo" cc="jp" country="Japan" operator="NTT DoCoMo - Chugoku" status="Operational" 62 bands="UMTS 800 / UMTS 1700 / UMTS 2100" brand="NTT DoCoMo" cc="jp" country="Japan" operator="NTT DoCoMo - Kyushu" status="Operational" 63 bands="UMTS / WCDMA / HSDPA / HSUPA / LTE (4G)" brand="NTT DoCoMo" cc="jp" country="Japan" operator="NTT DoCoMo" status="Operational" 64 bands="UMTS / WCDMA / HSDPA / HSUPA / LTE (4G)" brand="NTT DoCoMo" cc="jp" country="Japan" operator="NTT DoCoMo" status="Operational" 65 bands="UMTS 800 / UMTS 1700 / UMTS 2100" brand="NTT DoCoMo" cc="jp" country="Japan" operator="NTT DoCoMo - Shikoku" status="Operational" 66 bands="UMTS / WCDMA / HSDPA / HSUPA / LTE (4G)" brand="NTT DoCoMo" cc="jp" country="Japan" operator="NTT DoCoMo" status="Operational" 67 bands="UMTS 800 / UMTS 1700 / UMTS 2100" brand="NTT DoCoMo" cc="jp" country="Japan" operator="NTT DoCoMo - Tohoku" status="Operational" 68 bands="UMTS 800 / UMTS 1700 / UMTS 2100" brand="NTT DoCoMo" cc="jp" country="Japan" operator="NTT DoCoMo - Kyushu" status="Operational" 69 bands="UMTS / WCDMA / HSDPA / HSUPA / LTE (4G)" brand="NTT DoCoMo" cc="jp" country="Japan" operator="NTT DoCoMo" status="Operational" 70 bands="CDMA2000 800 / CDMA2000 2100" brand="au" cc="jp" country="Japan" operator="KDDI Corporation" status="Operational" 71 bands="WCDMA" brand="KDDI" cc="jp" country="Japan" operator="KDDI Corporation" status="Operational" 72 bands="WCDMA" brand="KDDI" cc="jp" country="Japan" operator="KDDI Corporation" status="Operational" 73 bands="WCDMA" brand="KDDI" cc="jp" country="Japan" operator="KDDI Corporation" status="Operational" 74 bands="WCDMA" brand="KDDI" cc="jp" country="Japan" operator="KDDI Corporation" status="Operational" 75 bands="WCDMA" brand="KDDI" cc="jp" country="Japan" operator="KDDI Corporation" status="Operational" 76 bands="WCDMA" brand="KDDI" cc="jp" country="Japan" operator="KDDI Corporation" status="Operational" 77 bands="WCDMA" brand="KDDI" cc="jp" country="Japan" operator="KDDI Corporation" status="Operational" 78 bands="UMTS / HSDPA" cc="jp" country="Japan" operator="Okinawa Cellular Telephone" status="Operational" 79 bands="WCDMA" brand="KDDI" cc="jp" country="Japan" operator="KDDI Corporation" status="Operational" 80 bands="GSM" brand="TU-KA" cc="jp" country="Japan" operator="TU-KA Cellular Tokyo" status="Not operational" 81 bands="GSM" brand="TU-KA" cc="jp" country="Japan" operator="TU-KA Cellular Tokyo" status="Not operational" 82 bands="GSM" brand="TU-KA" cc="jp" country="Japan" operator="TU-KA Phone Kansai" status="Not operational" 83 bands="GSM" brand="TU-KA" cc="jp" country="Japan" operator="TU-KA Cellular Tokai" status="Not operational" 84 bands="GSM" brand="TU-KA" cc="jp" country="Japan" operator="TU-KA Phone Kansai" status="Not operational" 85 bands="GSM" brand="TU-KA" cc="jp" country="Japan" operator="TU-KA Cellular Tokai" status="Not operational" 86 bands="GSM" brand="TU-KA" cc="jp" country="Japan" operator="TU-KA Cellular Tokyo" status="Not operational" 87 bands="UMTS / HSDPA" brand="NTT DoCoMo" cc="jp" country="Japan" operator="NTT DoCoMo - Chugoku" status="Operational" 88 bands="WCDMA" brand="KDDI" cc="jp" country="Japan" operator="KDDI Corporation" status="Operational" 89 bands="WCDMA" brand="KDDI" cc="jp" country="Japan" operator="KDDI Corporation" status="Operational" 90 bands="UMTS / HSPA+ / DC-HSDPA" brand="SoftBank" cc="jp" country="Japan" operator="SoftBank Mobile Corp" status="Operational" 92 bands="UMTS / HSPA+ / DC-HSDPA" brand="SoftBank" cc="jp" country="Japan" operator="SoftBank Mobile Corp" status="Operational" 93 bands="UMTS / HSPA+ / DC-HSDPA" brand="SoftBank" cc="jp" country="Japan" operator="SoftBank Mobile Corp" status="Operational" 94 bands="UMTS / HSPA+ / DC-HSDPA" brand="SoftBank" cc="jp" country="Japan" operator="SoftBank Mobile Corp" status="Operational" 95 bands="UMTS / HSPA+ / DC-HSDPA" brand="SoftBank" cc="jp" country="Japan" operator="SoftBank Mobile Corp" status="Operational" 96 bands="UMTS / HSPA+ / DC-HSDPA" brand="SoftBank" cc="jp" country="Japan" operator="SoftBank Mobile Corp" status="Operational" 97 bands="UMTS / HSPA+ / DC-HSDPA" brand="SoftBank" cc="jp" country="Japan" operator="SoftBank Mobile Corp" status="Operational" 98 bands="UMTS / HSPA+ / DC-HSDPA" brand="SoftBank" cc="jp" country="Japan" operator="SoftBank Mobile Corp" status="Operational" 99 bands="LTE (4G)" brand="NTT DoCoMo" cc="jp" country="Japan" operator="NTT DoCoMo" status="Operational" 00-99 450 02 bands="CDMA2000 1700" brand="KT" cc="kr" country="South Korea" operator="KT" status="Discontinued" 03 bands="CDMA2000 800" brand="Power 017" cc="kr" country="South Korea" operator="Shinsegi Telecom, Inc." status="Discontinued" 04 bands="CDMA2000 1700" brand="KT" cc="kr" country="South Korea" operator="KT" status="Discontinued" 05 bands="CDMA2000 800 / UMTS 2100 / LTE 850 / LTE 1800" brand="SKTelecom" cc="kr" country="South Korea" operator="SK Telecom" status="Operational" 06 bands="CDMA2000 1700 / LTE 850 2100 2600" brand="LG U+" cc="kr" country="South Korea" operator="LG Telecom" status="Operational" 08 bands="UMTS 2100 / LTE 1800" brand="olleh" cc="kr" country="South Korea" operator="KT" status="Operational" 11 bands="UMTS 2100" brand="SKTelecom" cc="kr" country="South Korea" operator="Korea Cable Telecom(t-plus), Eco-mobile" status="Operational" 00-99 452 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="MobiFone" cc="vn" country="Vietnam" operator="Vietnam Mobile Telecom Services Company (VMS)" status="Operational" 02 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Vinaphone" cc="vn" country="Vietnam" operator="Vietnam Telecom Services Company" status="Operational" 03 bands="CDMA2000 800" brand="S-Fone" cc="vn" country="Vietnam" operator="S-Telecom" status="Operational" 04 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Viettel Mobile" cc="vn" country="Vietnam" operator="Viettel Telecom" status="Operational" 05 bands="GSM 900 / UMTS 1900 / UMTS 2100" brand="Vietnamobile (HT Mobile )" cc="vn" country="Vietnam" operator="Hanoi Telecom" status="Operational" 06 bands="CDMA2000 450" brand="EVNTelecom" cc="vn" country="Vietnam" operator="EVNTelecom - EVN" status="Operational" 07 bands="GSM 1800" brand="G-Mobile" cc="vn" country="Vietnam" operator="GTEL Mobile JSC" status="Operational" 08 bands="UMTS 2100" brand="3G EVNTelecom" cc="vn" country="Vietnam" operator="EVNTelecom - EVN" status="Operational" 00-99 454 00 bands="GSM 900 / GSM 1800 / UMTS 900 / UMTS 2100 / LTE 1800 / LTE 2600" brand="1O1O / One2Free / New World Mobility" cc="hk" country="Hong Kong" operator="CSL Limited" status="Operational" 01 bands="GSM 900 / GSM 1800" cc="hk" country="Hong Kong" operator="CITIC Telecom 1616" status="Operational" 02 bands="GSM 900 / GSM 1800" cc="hk" country="Hong Kong" operator="CSL Limited" status="Operational" 03 bands="UMTS 900 / UMTS 2100 / LTE 1800 / LTE 2600" brand="3" cc="hk" country="Hong Kong" operator="Hutchison Telecom" status="Operational" 04 bands="GSM 900 / GSM 1800" brand="3 (2G)" cc="hk" country="Hong Kong" operator="Hutchison Telecom" status="Operational" 05 bands="CDMA2000 800" brand="3 (CDMA)" cc="hk" country="Hong Kong" operator="Hutchison Telecom" status="Not operational" 06 bands="GSM 900 / GSM 1800 / UMTS 850 / UMTS 2100 / LTE 1800" brand="SmarTone" cc="hk" country="Hong Kong" operator="SmarTone Mobile Communications Limited" status="Operational" 07 bands="GSM 900 / GSM 1800" cc="hk" country="Hong Kong" operator="China Unicom (Hong Kong) Limited" status="Operational" 08 brand="Truphone" cc="hk" country="Hong Kong" operator="Truphone Limited" status="Operational" 09 bands="GSM 900 / GSM 1800" cc="hk" country="Hong Kong" operator="China Motion Telecom" status="Operational" 10 bands="GSM 1800" brand="New World Mobility" cc="hk" country="Hong Kong" operator="CSL Limited" status="Not Operational" 11 cc="hk" country="Hong Kong" operator="China-Hong Kong Telecom" status="Operational" 12 bands="GSM 1800 / LTE 1800 / LTE 2600" brand="CMCC HK" cc="hk" country="Hong Kong" operator="China Mobile Hong Kong Company Limited" status="Operational" 13 bands="UMTS 2100" brand="CMCC HK" cc="hk" country="Hong Kong" operator="China Mobile Hong Kong Company Limited" status="MVNO" 14 bands="GSM 900 / GSM 1800" cc="hk" country="Hong Kong" operator="Hutchison Telecom" status="Operational" 15 bands="GSM 1800" cc="hk" country="Hong Kong" operator="SmarTone Mobile Communications Limited" status="Operational" 16 bands="GSM 1800" brand="PCCW Mobile (2G)" cc="hk" country="Hong Kong" operator="PCCW-HKT" status="Operational" 17 bands="GSM 1800" cc="hk" country="Hong Kong" operator="SmarTone Mobile Communications Limited" status="Operational" 18 bands="GSM 900 / GSM 1800" cc="hk" country="Hong Kong" operator="CSL Limited" status="Not Operational" 19 bands="UMTS 2100 / LTE 1800 / LTE 2600" brand="PCCW Mobile (3G/4G)" cc="hk" country="Hong Kong" operator="PCCW-HKT" status="Operational" 22 bands="GSM 1800" brand="P Plus" cc="hk" country="Hong Kong" operator="P Plus Communications" status="Not operational" 29 bands="CDMA2000 1xEV-DO 800" brand="PCCW Mobile (CDMA)" cc="hk" country="Hong Kong" operator="PCCW-HKT" status="Operational" 00-99 455 00 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="SmarTone" cc="mo" country="Macau (China)" operator="SmarTone Macao" status="Operational" 01 bands="GSM 900 / GSM 1800" brand="CTM" cc="mo" country="Macau (China)" operator="C.T.M. Telemovel+" status="Operational" 02 bands="CDMA2000 800" brand="China Telecom" cc="mo" country="Macau (China)" operator="China Telecom" status="Operational" 03 bands="GSM 900 / GSM 1800" brand="3" cc="mo" country="Macau (China)" operator="Hutchison Telecom" status="Operational" 04 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="CTM" cc="mo" country="Macau (China)" operator="C.T.M. Telemovel+" status="Operational" 05 bands="UMTS 900 / UMTS 2100" brand="3" cc="mo" country="Macau (China)" operator="Hutchison Telecom" status="Operational" 00-99 456 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Cellcard" cc="kh" country="Cambodia" operator="The Royal Group" status="Operational" 02 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Smart" cc="kh" country="Cambodia" operator="Latelz Company Limited" status="Operational" 03 bands="GSM 1800 / UMTS 2100" brand="qb" cc="kh" country="Cambodia" operator="Cambodia Advance Communications Co. Ltd" status="Operational" 04 bands="GSM 1800 / UMTS 2100" brand="qb" cc="kh" country="Cambodia" operator="Cambodia Advance Communications Co. Ltd" status="Operational" 05 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Smart" cc="kh" country="Cambodia" operator="Latelz Company Limited" status="Operational" 06 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Smart" cc="kh" country="Cambodia" operator="Latelz Company Limited" status="Operational" 08 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Cellcard" cc="kh" country="Cambodia" operator="The Royal Group" status="Operational" 09 bands="GSM 900 / GSM 1800" brand="Beeline" cc="kh" country="Cambodia" operator="Sotelco Ltd." status="Operational" 11 bands="CDMA2000" brand="Excell" cc="kh" country="Cambodia" status="Operational" 18 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Cellcard" cc="kh" country="Cambodia" operator="The Royal Group" status="Operational" 00-99 457 01 bands="GSM 900 / GSM 1800 / UMTS 2100 /LTE 4G/" brand="LTC" cc="la" country="Laos" operator="LaoTelecom" status="Operational" 02 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="ETL" cc="la" country="Laos" operator="Enterprise of Telecommunications Lao" status="Operational" 03 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Unitel" cc="la" country="Laos" operator="Star Telecom Co., Ltd" status="Operational" 08 bands="GSM 900 / GSM 1800 /LTE 4G" brand="Beeline" cc="la" country="Laos" operator="VimpelCom Lao Ltd" status="Operational" 00-99 460 00 bands="GSM 900 / GSM 1800 / TD-SCDMA 1900 / TD-SCDMA 2000 / TD-LTE 1900 / TD-LTE 2300 / TD-LTE 2600" brand="China Mobile" cc="cn" country="China" operator="China Mobile" status="Operational" 01 bands="GSM 900 / GSM 1800 / UMTS 2100 / TD-LTE 2300 / TD-LTE 2600 / FDD-LTE 1800" brand="China Unicom" cc="cn" country="China" operator="China Unicom" status="Operational" 02 bands="GSM 900 / GSM 1800 / TD-SCDMA 1900 / TD-SCDMA 2000 / TD-LTE 1900 / TD-LTE 2300 / TD-LTE 2600" brand="China Mobile" cc="cn" country="China" operator="China Mobile" status="Not Operational" 03 bands="CDMA2000 800 / CDMA2000 2100 / FDD-LTE 2100 / TD-LTE 2300 / TD-LTE 2600" brand="China Telecom" cc="cn" country="China" operator="China Telecom" status="Operational" 05 bands="CDMA2000 800 / CDMA2000 2100 / FDD-LTE 2100 / TD-LTE 2300 / TD-LTE 2600" brand="China Telecom" cc="cn" country="China" operator="China Telecom" status="Not Operational" 06 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="China Unicom" cc="cn" country="China" operator="China Unicom" status="Not Operational" 07 bands="GSM 900 / GSM 1800 / TD-SCDMA 1900 / TD-SCDMA 2000 / TD-LTE 1900 / TD-LTE 2300 / TD-LTE 2600" brand="China Mobile" cc="cn" country="China" operator="China Mobile" status="Not Operational" 20 bands="GSM-R" brand="China Tietong" cc="cn" country="China" operator="China Tietong" status="Operational" 00-99 466 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="FarEasTone" cc="tw" country="Taiwan" operator="Far EasTone Telecommunications Co Ltd" status="Operational" 05 bands="CDMA2000 800" brand="APTG" cc="tw" country="Taiwan" operator="Asia Pacific Telecom" status="Operational" 06 bands="GSM 1800" brand="Tuntex" cc="tw" country="Taiwan" operator="Tuntex Telecom" status="Not operational" 11 bands="Refer to 466-92 Chunghwa Telecom" brand="Chunghwa LDM" cc="tw" country="Taiwan" operator="LDTA/Chunghwa Telecom" status="Operational" 88 bands="GSM 1800" brand="KG Telecom" cc="tw" country="Taiwan" operator="KG Telecom" status="Not operational" 89 bands="UMTS 2100" brand="VIBO" cc="tw" country="Taiwan" operator="VIBO Telecom" status="Operational" 92 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Chungwa" cc="tw" country="Taiwan" operator="Chunghwa Telecom" status="Operational" 93 bands="GSM 900" brand="MobiTai" cc="tw" country="Taiwan" operator="Mobitai Communications" status="Not operational" 97 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Taiwan Mobile" cc="tw" country="Taiwan" operator="Taiwan Mobile Co. Ltd" status="Operational" 99 bands="GSM 900" brand="TransAsia" cc="tw" country="Taiwan" operator="TransAsia Telecoms" status="Not operational" 00-99 467 05 bands="UMTS 2100" brand="Koryolink" cc="kp" country="North Korea" operator="Cheo Technology Jv Company" status="Operational" 193 bands="GSM 900" brand="SunNet" cc="kp" country="North Korea" operator="Korea Posts and Telecommunications Corporation" status="discontinued" 00-99 470 01 bands="GSM 900/ GSM 1800" brand="Grameenphone" cc="bd" country="Bangladesh" operator="GrameenPhone Ltd" status="Operational" 02 bands="GSM 900 / GSM 1800" brand="Robi" cc="bd" country="Bangladesh" operator="Axiata Bangladesh Ltd." status="Operational" 03 bands="GSM 900/ GSM 1800" brand="Banglalink" cc="bd" country="Bangladesh" operator="Orascom Telecom Holding" status="Operational" 04 bands="GSM 900 / GSM 1800" brand="TeleTalk" cc="bd" country="Bangladesh" operator="Teletalk Bangladesh Limited" status="Operational" 05 bands="CDMA2000 800" brand="Citycell" cc="bd" country="Bangladesh" operator="Pacific Bangladesh Telecom Limited" status="Operational" 06 bands="GSM 900/ GSM 1800" brand="Beeong3G Warid Telekom" cc="bd" country="Bangladesh" operator="Beeong Ltd" status="Reserved" 07 bands="GSM 900 / GSM 1800" brand="Airtel" cc="bd" country="Bangladesh" operator="Bharti airtel Bangladesh Ltd." status="Operational" 00-99 472 01 bands="GSM 900 / UMTS 2100" brand="Dhiraagu" cc="mv" country="Maldives" operator="Dhivehi Raajjeyge Gulhun" status="Operational" 02 bands="GSM 900 / UMTS 2100" brand="Wataniya" cc="mv" country="Maldives" operator="Wataniya Telecom Maldives" status="Operational" 00-99 502 01 bands="CDMA2000 450 (depreciated)011-(6digits)" brand="ATUR 450" cc="my" country="Malaysia" operator="Telekom Malaysia Bhd" status="Operational" 10 cc="my" country="Malaysia" operator="DiGi Telecommunications" 11 brand="TM Homeline" cc="my" country="Malaysia" operator="Telekom Malaysia Bhd" 12 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Maxis" cc="my" country="Malaysia" operator="Maxis Mobile Services SDN Berhad" status="Operational" 13 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Celcom" cc="my" country="Malaysia" operator="Celcom Axiata Berhad" status="Operational" 14 cc="my" country="Malaysia" operator="Telekom Malaysia Berhad for PSTN SMS" 150 bands="MVNO" brand="Tune Talk" cc="my" country="Malaysia" operator="Tune Talk Sdn Bhd" status="Operational" 151 bands="MVNO" cc="my" country="Malaysia" operator="Baraka Telecom Sdn Bhd (MVNE)" status="Operational" 152 bands="WiMAX 2.3 GHz / LTE 4G" brand="Yes" cc="my" country="Malaysia" operator="YTL Communications Sdn Bhd" status="Operational" 156 bands="LTE 4G / MVNO" brand="Altel" cc="my" country="Malaysia" operator="Altel Communications Sdn Bhd" status="Operational" 16 bands="GSM 1800 / UMTS 2100" brand="DiGi" cc="my" country="Malaysia" operator="DiGi Telecommunications" status="Operational" 17 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Hotlink" cc="my" country="Malaysia" operator="Maxis Prepaid" status="Operational" 18 bands="CDMA 850" brand="TM Homeline" cc="my" country="Malaysia" operator="Telekom Malaysia Bhd" status="Operational" 19 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Celcom" cc="my" country="Malaysia" operator="Celcom Axiata Berhad" status="Operational" 20 bands="CDMA" cc="my" country="Malaysia" operator="Electcoms Wireless Sdn Bhd" status="Operational" 00-99 505 01 bands="GSM 900 / GSM 1800 / UMTS 850 / UMTS 2100 / LTE 1800" brand="Telstra" cc="au" country="Australia" operator="Telstra Corporation Limited" status="Operational" 02 bands="GSM 900 / GSM 1800 / UMTS 900 / UMTS 2100/ LTE 1800/2300" brand="Optus" cc="au" country="Australia" operator="Singtel Optus Proprietary Limited" status="Operational" 03 bands="GSM 900 / GSM 1800 / UMTS 850 / UMTS 900 / UMTS 2100" brand="Vodafone" cc="au" country="Australia" operator="Vodafone Hutchison Australia Proprietary Limited" status="Operational" 04 bands="" cc="au" country="Australia" operator="Department of Defence" status="Operational" 05 brand="Ozitel" cc="au" country="Australia" status="Not operational" 06 bands="UMTS 2100" brand="3" cc="au" country="Australia" operator="Vodafone Hutchison Australia Proprietary Limited" status="Not operational" 08 bands="GSM 900" brand="One.Tel" cc="au" country="Australia" operator="One.Tel Limited" status="Not operational" 09 brand="Airnet" cc="au" country="Australia" status="Not operational" 10 bands="GSM 900" brand="Norfolk Telecom" cc="nf" country="Norfolk Island" operator="Norfolk Telecom" status="Operational" 12 bands="UMTS 2100" brand="3" cc="au" country="Australia" operator="Vodafone Hutchison Australia Proprietary Limited" status="Not operational" 13 bands="GSM 1800" brand="Railcorp" cc="au" country="Australia" operator="Rail Corporation New South Wales" status="Reserved" 14 bands="GSM 1800 / UMTS 2100" brand="AAPT" cc="au" country="Australia" operator="Telecom New Zealand" status="Operational" 15 brand="3GIS" cc="au" country="Australia" status="Not operational" 16 bands="GSM 1800" brand="Victorian Rail Track" cc="au" country="Australia" status="Reserved" 18 brand="Pactel" cc="au" country="Australia" operator="Pactel International Pty Ltd" status="Reserved" 19 brand="Lycamobile Pty Ltd" cc="au" country="Australia" 21 bands="MVNO" brand="SOUL" cc="au" country="Australia" operator="TPG Telecom Limited" status="" 23 bands="LTE 2100" cc="au" country="Australia" operator="Challenge Networks Pty. Ltd." status="Planning" 24 bands="" brand="Advance Communications Technologies Pty. Ltd." cc="au" country="Australia" status="" 26 bands="" cc="au" country="Australia" operator="Dialogue Communications Pty. Ltd." status="" 27 bands="" cc="au" country="Australia" operator="Nexium Telecommunications" status="" 38 bands="GSM 900 / GSM 1800 / UMTS 900 / UMTS 2100" brand="Crazy John's" cc="au" country="Australia" operator="Vodafone Hutchison Australia Proprietary Limited" status="Operational" 62 cc="au" country="Australia" 71 bands="" brand="Telstra" cc="au" country="Australia" operator="Telstra Corporation Limited" status="Operational" 72 bands="" brand="Telstra" cc="au" country="Australia" operator="Telstra Corporation Limited" status="Operational" 88 brand="Localstar Holding Pty. Ltd." cc="au" country="Australia" status="Not operational" 90 bands="" brand="Optus" cc="au" country="Australia" operator="Singtel Optus Proprietary Limited" status="Operational" 99 bands="GSM 1800" brand="One.Tel" cc="au" country="Australia" operator="One.Tel" status="Not operational" 00-99 510 00 bands="Satellite" brand="PSN" cc="id" country="Indonesia" operator="PT Pasifik Satelit Nusantara (ACeS)" status="Operational" 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="INDOSAT" cc="id" country="Indonesia" operator="PT Indonesian Satellite Corporation Tbk (INDOSAT)" status="Operational" 03 bands="CDMA2000 800" brand="StarOne" cc="id" country="Indonesia" operator="PT Indosat Tbk" status="Operational" 07 bands="CDMA2000 800" brand="TelkomFlexi" cc="id" country="Indonesia" operator="PT Telkom" status="Operational" 08 bands="GSM 1800 / UMTS 2100" brand="AXIS" cc="id" country="Indonesia" operator="PT Natrindo Telepon Seluler" status="Operational" 09 bands="CDMA2000 1900" brand="SMART" cc="id" country="Indonesia" operator="PT Smart Telecom" status="Operational" 10 bands="GSM 900 / GSM 1800 / UMTS 2100/apn free arutmin" brand="Telkomsel" cc="id" country="Indonesia" operator="PT Telekomunikasi Selular" status="Operational" 11 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="XL" cc="id" country="Indonesia" operator="PT XL Axiata Tbk" status="Operational" 20 bands="GSM 1800" brand="TELKOMMobile" cc="id" country="Indonesia" operator="PT Telkom Indonesia Tbk" status="Not operational" 21 bands="GSM 1800" brand="IM3" cc="id" country="Indonesia" operator="PT Indonesian Satellite Corporation Tbk (INDOSAT)" status="Not operational" 27 bands="CDMA2000 450" brand="Ceria" cc="id" country="Indonesia" operator="PT Sampoerna Telekomunikasi Indonesia" status="Operational" 28 bands="CDMA2000 800" brand="Fren/Hepi" cc="id" country="Indonesia" operator="PT Mobile-8 Telecom" status="Operational" 89 bands="GSM 1800 / UMTS 2100" brand="3" cc="id" country="Indonesia" operator="PT Hutchison CP Telecommunications" status="Operational" 99 bands="CDMA2000 800" brand="Esia" cc="id" country="Indonesia" operator="PT Bakrie Telecom" status="Operational" 995 cc="id" country="Indonesia" 00-99 514 01 bands="GSM 850/900/1800, UMTS 2100" brand="Telin" cc="tl" country="East Timor" operator="PT Telekomunikasi Indonesia International" status="Planned" 02 bands="GSM 900" cc="tl" country="East Timor" operator="Timor Telecom" status="Operational" 03 bands="" cc="tl" country="East Timor" operator="Viettel Timor-Leste" status="Planned" 00-99 515 01 bands="GSM 900" brand="Islacom" cc="ph" country="Philippines" operator="Globe Telecom via Innove Communications" status="Not operational" 02 bands="EDGE 900 / EDGE 1800 / UMTS 850 / UMTS 2100" brand="Globe" cc="ph" country="Philippines" operator="Globe Telecom" status="Operational" 03 bands="EDGE 900 / EDGE 1800 / UMTS 850 / UMTS 2100" brand="Smart" cc="ph" country="Philippines" operator="PLDT via Smart Communications" status="Operational" 05 bands="EDGE 1800 / UMTS 2100" brand="Sun" cc="ph" country="Philippines" operator="Digital Telecommunications Philippines" status="Operational" 11 bands="" cc="ph" country="Philippines" operator="PLDT via ACeS Philippines" status="" 18 bands="GSM 900 / UMTS 2100 (defunct)" brand="Cure" cc="ph" country="Philippines" operator="PLDT via Smart's Connectivity Unlimited Resources Enterprise" status="Operational" 88 bands="" cc="ph" country="Philippines" operator="Nextel" status="" 00-99 520 00 bands="HSPA+ 850" brand="my by CAT" cc="th" country="Thailand" operator="CAT Telecom" status="Operational" 01 bands="GSM 900 / HSPA+ 900" brand="AIS" cc="th" country="Thailand" operator="Advanced Info Service" status="Operational" 02 bands="CDMA 2000 1x EVDO REV.A 800" brand="CAT CDMA" cc="th" country="Thailand" operator="CAT Telecom" status="Operational" 03 bands="HSPA+ 2100" brand="AIS 3G" cc="th" country="Thailand" operator="AWN" status="Operational" 04 bands="HSPA+ 2100 / LTE 2100" brand="truemove H 4G LTE" cc="th" country="Thailand" operator="Real Future" status="Operational" 05 bands="HSPA+ 2100" brand="dtac 3G" cc="th" country="Thailand" operator="DTN" status="Operational" 10 bands="" brand="?" cc="th" country="Thailand" operator="WCS IQ" status="" 15 bands="HSPA+ 2100" brand="TOT 3G" cc="th" country="Thailand" operator="Telephone Organization of Thailand (TOT)" status="Operational" 18 bands="GSM 1800 / HSPA+ 850" brand="dtac" cc="th" country="Thailand" operator="Total Access Communication" status="Operational" 23 bands="GSM 1800" brand="AIS GSM 1800" cc="th" country="Thailand" operator="AIS)" status="Operational" 25 bands="PHS 1900" brand="WE PCT" cc="th" country="Thailand" operator="True Corporation" status="Operational" 99 bands="GSM 1800" brand="truemove" cc="th" country="Thailand" operator="True Corporation" status="Operational" 00-99 525 01 bands="GSM 900/1800, UMTS 900/2100, LTE 1800/2600" brand="SingTel" cc="sg" country="Singapore" operator="Singapore Telecom" status="Operational" 02 bands="GSM 1800" brand="SingTel-G18" cc="sg" country="Singapore" operator="Singapore Telecom" status="Operational" 03 bands="GSM 900/1800, UMTS 900/2100, LTE 1800/2600" brand="M1" cc="sg" country="Singapore" operator="M1 Limited" status="Operational" 05 bands="GSM 1800, UMTS 900/2100, LTE 1800" brand="StarHub" cc="sg" country="Singapore" operator="StarHub Mobile" status="Operational" 06 bands="" brand="StarHub" cc="sg" country="Singapore" operator="StarHub Mobile" status="" 07 bands="" brand="SingTel" cc="sg" country="Singapore" operator="Singapore Telecom" status="" 12 bands="iDEN 800" brand="Grid" cc="sg" country="Singapore" operator="GRID Communications Pte Ltd." status="Operational" 00-99 528 01 bands="" cc="bn" country="Brunei" operator="Jabatan Telekom Brunei" status="" 02 bands="UMTS 2100" brand="B-Mobile" cc="bn" country="Brunei" operator="B-Mobile Communications Sdn Bhd" status="Operational" 11 bands="GSM 900 / UMTS 2100" brand="DSTCom" cc="bn" country="Brunei" operator="Data Stream Technology" status="Operational" 00-99 530 00 bands="AMPS 800 / TDMA 800" brand="Telecom" cc="nz" country="New Zealand" operator="Telecom New Zealand" status="Not operational" 01 bands="GSM 900 / GSM 1800 / UMTS 900 / UMTS 2100 / LTE 1800" brand="Vodafone" cc="nz" country="New Zealand" operator="Vodafone New Zealand" status="Operational" 02 bands="CDMA2000 800" brand="Telecom" cc="nz" country="New Zealand" operator="Telecom New Zealand" status="Not operational" 03 bands="UMTS 2000" brand="Woosh" cc="nz" country="New Zealand" operator="Woosh Wireless New Zealand Walker" status="Operational" 04 bands="UMTS 2100" brand="TelstraClear" cc="nz" country="New Zealand" operator="TelstraClear New Zealand" status="Not operational" 05 bands="UMTS 850 / UMTS 2100 / LTE 1800" brand="XT Mobile Network" cc="nz" country="New Zealand" operator="Telecom New Zealand" status="Operational" 06 bands="UMTS 850 / UMTS 2100" brand="Skinny" cc="nz" country="New Zealand" operator="Telecom New Zealand" status="Operational" 24 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="2degrees" cc="nz" country="New Zealand" operator="2degrees" status="Operational" 00-99 536 02 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Digicel" cc="nr" country="Nauru" operator="Digicel (Nauru) Corporation" status="Operational" 00-99 537 01 bands="GSM 900" brand="BeMobile" cc="pg" country="Papua New Guinea" operator="Pacific Mobile Communications" status="Operational" 03 bands="GSM 900 / UMTS 900" brand="Digicel" cc="pg" country="Papua New Guinea" operator="Digicel PNG" status="Operational" 00-99 539 01 bands="GSM 900" brand="U-Call" cc="to" country="Tonga" operator="Tonga Communications Corporation" status="Operational" 43 bands="" cc="to" country="Tonga" operator="Shoreline Communication" status="Operational" 88 bands="GSM 900" brand="Digicel" cc="to" country="Tonga" operator="Digicel (Tonga) Limited" status="Operational" 00-99 540 01 bands="GSM 900" brand="BREEZE" cc="sb" country="Solomon Islands" operator="Solomon Telekom Co Ltd" status="Operational" 02 bands="GSM 900 / GSM 1800" brand="BeMobile" cc="sb" country="Solomon Islands" operator="BMobile (SI) Ltd" status="Operational" 00-99 541 00 bands="GSM 900" brand="AIL" cc="vu" country="Vanuatu" operator="ACeS International (AIL)" status="Operational" 01 bands="GSM 900" brand="SMILE" cc="vu" country="Vanuatu" operator="Telecom Vanuatu Ltd" status="Operational" 05 bands="GSM 900, UMTS 900" brand="Digicel" cc="vu" country="Vanuatu" operator="Digicel Vanuatu Ltd" status="Operational" 00-99 542 01 bands="GSM 900 / UMTS 2100" brand="Vodafone" cc="fj" country="Fiji" operator="Vodafone Fiji" status="Operational" 02 bands="GSM 900 /UMTS 900 /UMTS 2100 /WIMAX 4G" brand="Digicel" cc="fj" country="Fiji" operator="Digicel Fiji" status="Operational" 00-99 544 11 bands="GSM" brand="Bluesky" cc="as" country="American Samoa (United States of America)" operator="Bluesky" status="Operational" 00-99 545 01 bands="UMTS 850 / LTE 700" brand="Kiribati - TSKL" cc="ki" country="Kiribati" operator="Telecom Services Kiribati Ltd" status="Operational" 09 bands="GSM 900" brand="Kiribati - Frigate Net" cc="ki" country="Kiribati" operator="Telecom Services Kiribati Ltd" status="Operational" 00-99 546 01 bands="GSM 900" brand="Mobilis" cc="nc" country="New Caledonia (France)" operator="OPT New Caledonia" status="Operational" 00-99 547 20 bands="GSM 900 / UMTS 2100" brand="Vini" cc="pf" country="French Polynesia" operator="Tikiphone SA" status="Operational" 00-99 548 01 bands="GSM 900" cc="ck" country="Cook Islands (New Zealand)" operator="Telecom Cook" status="Operational" 00-99 549 01 bands="GSM 900" brand="Digicel" cc="ws" country="Samoa" operator="Digicel Pacific Ltd." status="Operational" 27 bands="GSM 900" brand="Bluesky" cc="ws" country="Samoa" operator="Bluesky Samoa Ltd" status="Operational" 00-99 550 01 bands="GSM 900" cc="fm" country="Federated States of Micronesia" operator="FSMTC" status="Operational" 00-99 551 01 cc="mh" country="Marshall Islands" operator="Marshall Islands National Telecommunications Authority (MINTA)" status="Operational" 00-99 552 01 bands="GSM 900" brand="PNCC" cc="pw" country="Palau" operator="Palau National Communications Corp." status="Operational" 80 bands="GSM 1800" brand="Palau Mobile" cc="pw" country="Palau" operator="Palau Mobile Corporation" status="Operational" 00-99 553 01 bands="GSM 900" brand="TTC" cc="tv" country="Tuvalu" operator="Tuvalu Telecom" status="Operational" 00-99 555 01 bands="GSM 900" brand="Telecom Niue" cc="nu" country="Niue" operator="Telecom Niue" status="Operational" 00-99 602 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Mobinil" cc="eg" country="Egypt" operator="ECMS-Mobinil" status="Operational" 02 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Vodafone" cc="eg" country="Egypt" operator="Vodafone Egypt" status="Operational" 03 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Etisalat" cc="eg" country="Egypt" operator="Etisalat Egypt" status="Operational" 00-99 603 01 bands="GSM 900 / GSM 1800 / GSM 2100 / CDMA2000 1900" brand="Mobilis" cc="dz" country="Algeria" operator="ATM Mobilis" status="Operational" 02 bands="GSM 900 / GSM 1800" brand="Djezzy" cc="dz" country="Algeria" operator="Orascom Telecom Algerie Spa" status="Operational" 03 bands="GSM 900 / GSM 1800" brand="Nedjma" cc="dz" country="Algeria" operator="Wataniya Telecom Algerie" status="Operational" 00-99 604 00 bands="GSM 900 / GSM 1800" brand="Méditel" cc="ma" country="Morocco" operator="Medi Telecom" status="Operational" 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="IAM" cc="ma" country="Morocco" operator="Ittissalat Al Maghrib (Maroc Telecom)" status="Operational" 02 bands="GSM 900 / GSM 1800" brand="Wana Corporate" cc="ma" country="Morocco" operator="Wana)" status="Operational" 05 bands="GSM 900 / GSM 1800" brand="INWI" cc="ma" country="Morocco" operator="WANA - Groupe ONA" status="Operational" 00-99 605 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Orange" cc="tn" country="Tunisia" operator="Orange Tunisie" status="Operational" 02 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Tunicell" cc="tn" country="Tunisia" operator="Tunisie Telecom" status="Operational" 03 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Tunisiana" cc="tn" country="Tunisia" operator="Orascom Telecom Tunisie" status="Operational" 00-99 606 00 bands="GSM900 / GSM 1800 / UMTS 2100" brand="Libyana" cc="ly" country="Libya" operator="Libyana" status="Operational" 01 bands="GSM900 / GSM 1800" brand="Madar" cc="ly" country="Libya" operator="Al-Madar Al-Jadeed" status="Operational" 02 bands="GSM900 / GSM 1800" brand="Al-Jeel Phone" cc="ly" country="Libya" operator="Al-Jeel Al-Jadeed" status="Operational" 03 bands="GSM900 / GSM 1800 / UMTS 2100" brand="Libya Phone" cc="ly" country="Libya" operator="Libya Telecom and Technology (LTT)" status="Operational" 06 bands="CDMA2000" brand="Hatef Libya" cc="ly" country="Libya" operator="Hatef Libya" status="Operational" 00-99 607 01 bands="GSM 900 / GSM 1900" brand="Gamcel" cc="gm" country="Gambia" operator="Gamcel" status="Operational" 02 bands="GSM 900 / GSM 1900" brand="Africel" cc="gm" country="Gambia" operator="Africel" status="Operational" 03 bands="GSM 900 / GSM 1900" brand="Comium" cc="gm" country="Gambia" operator="Comium" status="Operational" 04 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="QCell" cc="gm" country="Gambia" operator="QCell Gambia" status="Operational" 00-99 608 01 bands="GSM 900 / UMTS 2100" brand="Orange" cc="sn" country="Senegal" operator="Sonatel" status="Operational" 02 bands="GSM 900 / UMTS 2100" brand="Tigo" cc="sn" country="Senegal" operator="Millicom International Cellular S.A." status="Operational" 03 bands="GSM 900 / UMTS 2100" brand="Expresso" cc="sn" country="Senegal" operator="Sudatel" status="Operational" 00-99 609 01 bands="GSM 900" brand="Mattel" cc="mr" country="Mauritania" operator="Mattel" status="Operational" 02 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Chinguitel" cc="mr" country="Mauritania" operator="Chinguitel" status="Operational" 10 bands="GSM 900" brand="Mauritel" cc="mr" country="Mauritania" operator="Mauritel Mobiles" status="Operational" 00-99 610 01 bands="GSM 900" brand="Malitel" cc="ml" country="Mali" operator="Malitel SA" status="Operational" 02 bands="GSM 900" brand="Orange" cc="ml" country="Mali" operator="Orange Mali SA" status="Operational" 00-99 611 01 bands="GSM 900 / GSM 1800" brand="Orange S.A." cc="gn" country="Guinea" operator="Orange" status="Operational" 02 bands="GSM 900" brand="Sotelgui" cc="gn" country="Guinea" operator="Sotelgui Lagui" status="Operational" 03 bands="GSM 900" brand="Telecel Guinee" cc="gn" country="Guinea" operator="INTERCEL Guinée" status="Operational" 04 bands="GSM 900 / GSM 1800" brand="MTN" cc="gn" country="Guinea" operator="Areeba Guinea" status="Operational" 05 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Cellcom" cc="gn" country="Guinea" operator="Cellcom" status="Operational" 00-99 612 01 bands="" cc="ci" country="Ivory Coast" operator="Cora de Comstar" status="Not operational" 02 bands="GSM 900 / GSM 1800" brand="Moov" cc="ci" country="Ivory Coast" status="Operational" 03 bands="GSM 900" brand="Orange" cc="ci" country="Ivory Coast" status="Operational" 04 bands="GSM 900 / GSM 1800" brand="KoZ" cc="ci" country="Ivory Coast" operator="Comium Ivory Coast Inc" status="Operational" 05 bands="GSM 900" brand="MTN" cc="ci" country="Ivory Coast" status="Operational" 06 bands="GSM 1800" brand="ORICEL" cc="ci" country="Ivory Coast" operator="ORICEL" status="Operational" 00-99 613 01 bands="GSM 900" brand="Telmob" cc="bf" country="Burkina Faso" operator="Onatel" status="Operational" 02 bands="GSM 900" brand="Airtel" cc="bf" country="Burkina Faso" operator="Airtel Burkina Faso" status="Operational" 03 bands="GSM 900" brand="Telecel Faso" cc="bf" country="Burkina Faso" operator="Telecel Faso SA" status="Operational" 00-99 614 01 bands="GSM 900" brand="SahelCom" cc="ne" country="Niger" operator="La Société Sahélienne de Télécommunications (SahelCom)" status="Operational" 02 bands="GSM 900" brand="Airtel" cc="ne" country="Niger" operator="Bharti Airtel Limited" status="Operational" 03 bands="GSM 900" brand="Moov" cc="ne" country="Niger" operator="Atlantique Telecom (subsidiary of Etisalat)" status="Operational" 04 bands="GSM 900 / GSM 1800" brand="Orange" cc="ne" country="Niger" operator="Orange Niger" status="Operational" 00-99 615 01 bands="GSM 900" brand="Togo Cell" cc="tg" country="Togo" operator="Togo Telecom" status="Operational" 03 bands="GSM 900" brand="Moov" cc="tg" country="Togo" operator="Moov Togo" status="Operational" 00-99 616 01 bands="GSM 900 / GSM 1800" brand="Libercom" cc="bj" country="Benin" operator="Benin Telecoms Mobile" status="Operational" 02 bands="GSM 900" brand="Moov" cc="bj" country="Benin" operator="Telecel Benin" status="Operational" 03 bands="GSM 900" brand="MTN" cc="bj" country="Benin" operator="Spacetel Benin" status="Operational" 04 bands="GSM 900 / GSM 1800" brand="BLK" cc="bj" country="Benin" operator="BLK Communication Benin" status="Operational" 05 bands="GSM 900 / GSM 1800" brand="Glo" cc="bj" country="Benin" operator="Glo Communication Benin" status="Operational" 00-99 617 01 bands="GSM 900 / GSM 1800 / UMTS 2100 / LTE 1800" brand="Orange" cc="mu" country="Mauritius" operator="Cellplus Mobile Communications Ltd." status="Operational" 02 bands="GSM 900 / CDMA2000" brand="MTML" cc="mu" country="Mauritius" operator="Mahanagar Telephone (Mauritius) Ltd." status="Operational" 10 bands="GSM 900 / GSM 1800 / UMTS 2100 / LTE 1800" brand="Emtel" cc="mu" country="Mauritius" operator="Emtel Ltd." status="Operational" 00-99 618 01 bands="GSM 900" brand="Lonestar Cell" cc="lr" country="Liberia" operator="Lonestar Communications Corporation" status="Operational" 02 bands="" brand="Libercell" cc="lr" country="Liberia" operator="Atlantic Wireless (Liberia) Inc." status="Operational" 04 bands="GSM 900" brand="Comium" cc="lr" country="Liberia" operator="Comium Liberia" status="Operational" 07 bands="GSM 900 / GSM 1800" brand="Cellcom" cc="lr" country="Liberia" operator="Cellcom Telecommunications, Inc" status="Operational" 20 bands="CDMA2000" brand="LIBTELCO" cc="lr" country="Liberia" operator="Liberia Telecommunications Corporation" status="Operational" 00-99 619 01 bands="GSM 900" brand="Airtel" cc="sl" country="Sierra Leone" operator="Bharti Airtel Limited" status="Operational" 02 bands="" brand="Tigo" cc="sl" country="Sierra Leone" operator="Millicom (SL) Limited" status="" 03 bands="GSM 900" brand="Africell" cc="sl" country="Sierra Leone" operator="Lintel Sierra Leone Limited" status="Operational" 04 bands="GSM 900/1800" brand="Comium" cc="sl" country="Sierra Leone" operator="Comium Sierra leone INC" status="Operational" 05 bands="GSM 900" brand="Africell" cc="sl" country="Sierra Leone" operator="Lintel Sierra Leone Limited" status="Operational" 25 bands="" brand="Mobitel" cc="sl" country="Sierra Leone" operator="Mobitel" status="Operational" 00-99 620 01 bands="GSM 900 / GSM 1800" brand="MTN" cc="gh" country="Ghana" operator="MTN Group" status="Operational" 02 bands="GSM 900 / GSM 1800" brand="Vodafone" cc="gh" country="Ghana" operator="Vodafone Group" status="Operational" 03 bands="GSM 900 / GSM 1800" brand="tiGO" cc="gh" country="Ghana" operator="Millicom Ghana" status="Operational" 04 bands="CDMA2000" brand="Expresso" cc="gh" country="Ghana" operator="Kasapa / Hutchison Telecom" status="Operational" 06 bands="GSM 900 / GSM 1800 / WCDMA" brand="Airtel" cc="gh" country="Ghana" operator="Airtel" status="Operational" 07 bands="GSM 900 / GSM 1800 / WCDMA" brand="Globacom" cc="gh" country="Ghana" operator="Globacom Group" status="Operational" 00-99 621 20 bands="GSM 900 / GSM 1800" brand="Airtel" cc="ng" country="Nigeria" operator="Bharti Airtel Limited" status="Operational" 25 bands="CDMA2000 800 / CDMA2000 1900" brand="Visafone" cc="ng" country="Nigeria" operator="Visafone Communications Ltd." status="Operational" 30 bands="GSM 900 / GSM 1800" brand="MTN" cc="ng" country="Nigeria" operator="MTN Nigeria Communications Limited" status="Operational" 40 bands="GSM 900 / GSM 1800" brand="M-Tel" cc="ng" country="Nigeria" operator="Nigerian Mobile Telecommunications Limited" status="Non-Operational" 50 bands="GSM 900 / GSM 1800" brand="Glo" cc="ng" country="Nigeria" operator="Globacom Ltd" status="Operational" 60 bands="GSM 900 / GSM 1800" brand="Etisalat" cc="ng" country="Nigeria" operator="Emerging Markets Telecommunication Services Ltd (Etisalat)" status="Operational" 00-99 622 01 bands="GSM 900" brand="Airtel" cc="td" country="Chad" operator="Bharti Airtel SA" status="Operational" 02 bands="CDMA2000" brand="Tawali" cc="td" country="Chad" operator="Sotel Chad" status="Operational" 03 bands="GSM 900" brand="Tigo" cc="td" country="Chad" operator="Millicom" status="Operational" 04 bands="GSM 900 / GSM 1800" brand="Salam" cc="td" country="Chad" operator="Sotel Mobile" status="Operational" 00-99 623 01 bands="GSM 900" brand="CTP" cc="cf" country="Central African Republic" operator="Centrafrique Telecom Plus" status="Operational" 02 bands="GSM 900" brand="TC" cc="cf" country="Central African Republic" operator="Telecel Centrafrique" status="Operational" 03 bands="GSM 1800" brand="Orange" cc="cf" country="Central African Republic" operator="Orange RCA" status="Reserved" 04 bands="GSM 900" brand="Nationlink" cc="cf" country="Central African Republic" operator="Nationlink Telecom RCA" status="Operational" 00-99 624 01 bands="GSM 900" brand="MTN Cameroon" cc="cm" country="Cameroon" operator="Mobile Telephone Network Cameroon Ltd" status="Operational" 02 bands="GSM 900" brand="Orange" cc="cm" country="Cameroon" operator="Orange Cameroun S.A." status="Operational" 00-99 625 01 bands="GSM 900" brand="CVMOVEL" cc="cv" country="Cape Verde" operator="CVMovel, S.A." status="Operational" 02 bands="GSM 1800" brand="T+" cc="cv" country="Cape Verde" operator="T+" status="Operational" 00-99 626 01 bands="GSM 900" brand="CSTmovel" cc="st" country="Sao Tome and Principe" operator="Companhia Santomese de Telecomunicaçôe" status="Operational" 00-99 627 01 bands="GSM 900" brand="Orange GQ" cc="gq" country="Equatorial Guinea" operator="GETESA" status="Operational" 03 bands="GSM 900 / GSM 1800" brand="Hits GQ" cc="gq" country="Equatorial Guinea" operator="HiTs EG.SA" status="Operational" 00-99 628 01 bands="GSM 900" brand="Libertis" cc="ga" country="Gabon" operator="Gabon Telecom & Libertis S.A." status="Operational" 02 bands="GSM 900" brand="Moov" cc="ga" country="Gabon" operator="Atlantique Télécom (Etisalat Group) Gabon S.A." status="Operational" 03 bands="GSM 900" brand="Airtel" cc="ga" country="Gabon" operator="Airtel Gabon S.A." status="Operational" 04 bands="GSM 900" brand="Azur" cc="ga" country="Gabon" operator="USAN Gabon S.A." status="Operational" 00-99 629 01 bands="GSM 900" brand="Airtel" cc="cg" country="Republic of the Congo" operator="Celtel Congo" status="Operational" 07 bands="GSM 900" cc="cg" country="Republic of the Congo" operator="Warid Telecom" status="Operational" 10 bands="GSM 900" brand="Libertis Telecom" cc="cg" country="Republic of the Congo" operator="MTN CONGO S.A" status="Operational" 00-99 630 01 bands="GSM 900 / GSM 1800" brand="Vodacom" cc="cd" country="Democratic Republic of the Congo" operator="Vodacom Congo RDC sprl" status="Operational" 02 bands="GSM 900" brand="groupe bahati" cc="cd" country="Democratic Republic of the Congo" operator="airtel Congo" status="Operational" 04 bands="" cc="cd" country="Democratic Republic of the Congo" operator="Cellco" status="" 05 bands="GSM 900 / GSM 1800" brand="Supercell" cc="cd" country="Democratic Republic of the Congo" operator="Supercell SPRL" status="Operational" 10 brand="Libertis Telecom" cc="cd" country="Democratic Republic of the Congo" status="Operational" 86 bands="GSM 900 / GSM 1800" brand="France telecom" cc="cd" country="Democratic Republic of the Congo" operator="orange.TM" status="Operational" 89 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Tigo DRC Sait Telecom" cc="cd" country="Democratic Republic of the Congo" operator="OASIS SPRL" status="Operational" 992 bands="GSM 900" brand="lintel holding" cc="cd" country="Democratic Republic of the Congo" operator="Africell RDC sprl" status="Operational" 00-99 631 02 bands="GSM 900 / GSM 1800 / LTE 2100" brand="UNITEL" cc="ao" country="Angola" operator="UNITEL S.a.r.l." status="Operational" 04 bands="GSM 900 / UMTS 900 / LTE 1800" brand="MOVICEL" cc="ao" country="Angola" operator="MOVICEL Telecommunications S.A." status="Operational" 00-99 632 02 bands="GSM 900" brand="MTN Areeba" cc="gw" country="Guinea-Bissau" operator="Spacetel Guiné-Bissau S.A." status="Operational" 03 bands="GSM 900/1800" brand="Orange" cc="gw" country="Guinea-Bissau" status="Operational" 07 bands="GSM 900/1800" brand="Guinetel" cc="gw" country="Guinea-Bissau" status="Operational" 00-99 633 01 bands="GSM 900" brand="Cable & Wireless" cc="sc" country="Seychelles" operator="Cable & Wireless Seychelles" status="Operational" 02 bands="GSM 1800" brand="Mediatech International" cc="sc" country="Seychelles" operator="Mediatech International" status="Operational" 10 bands="GSM 900 / UMTS 2100" brand="Airtel" cc="sc" country="Seychelles" operator="Telecom Seychelles Ltd" status="Operational" 00-99 634 01 bands="GSM 900 / UMTS 2100" brand="Zain SD" cc="sd" country="Sudan" operator="Zain Group - Sudan" status="Operational" 02 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="MTN" cc="sd" country="Sudan" operator="MTN Sudan" status="Operational" 05 brand="Canar Telecom" cc="sd" country="Sudan" operator="Operational" status="CDMA2000 450" 07 bands="GSM 1800 / UMTS 2100 / CDMA2000 800" brand="Sudani One" cc="sd" country="Sudan" operator="Sudatel Group" status="Operational" 09 brand="Privet Network" cc="sd" country="Sudan" operator="NEC" 00-99 635 10 bands="GSM 900" brand="MTN" cc="rw" country="Rwanda" operator="MTN Rwandacell SARL" status="Operational" 12 bands="GSM ???" brand="Rwandatel" cc="rw" country="Rwanda" operator="Rwandatel S.A." status="Not operational" 13 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Tigo" cc="rw" country="Rwanda" operator="TIGO RWANDA S.A" status="Operational" 14 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Airtel" cc="rw" country="Rwanda" operator="Airtel RWANDA" status="Operational" 00-99 636 011 bands="GSM 900 / GSM 1800 / UMTS 21000" brand="ETH-MTN" cc="et" country="Ethiopia" operator="Ethio Telecom" status="Operational" 000-999 637 01 bands="GSM 900 GSM 1800 3G 2100" brand="Telesom" cc="so" country="Somalia" operator="Telesom" status="Operational" 04 bands="GSM 900 / GSM 1800" brand="Somafone" cc="so" country="Somalia" operator="Somafone FZLLC" status="Operational" 10 bands="GSM 900" brand="Nationlink" cc="so" country="Somalia" operator="NationLink Telecom" status="Operational" 25 bands="GSM 900" brand="Hormuud" cc="so" country="Somalia" operator="Hormuud Telecom Somalia Inc" status="Operational" 30 bands="GSM 900" brand="Golis" cc="so" country="Somalia" operator="Golis Telecom Somalia" status="Operational" 57 bands="GSM 900 / GSM 1800" brand="Unittel" cc="so" country="Somalia" operator="Unitted Telecom" status="Operational" 60 bands="GSM 900/ GSM 1800" brand="Nationlink Telecom" cc="so" country="Somalia" operator="Nationlink Telecom" status="Operational" 71 bands="900/1800/2100" brand="Somtel" cc="so" country="Somalia" operator="2G/3G" status="Operational" 82 bands="GSM 900 / GSM 1800 / CDMA2000" brand="Telcom" cc="so" country="Somalia" operator="Telcom Somalia" status="Operational" 00-99 638 01 bands="GSM 900" brand="Evatis" cc="dj" country="Djibouti" operator="Djibouti Telecom SA" status="Operational" 00-99 639 02 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Safaricom" cc="ke" country="Kenya" operator="Safaricom Limited" status="Operational" 03 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Airtel" cc="ke" country="Kenya" operator="B Airtel" status="Operational" 05 bands="GSM 900" brand="yu" cc="ke" country="Kenya" operator="Econet Wireless Kenya" status="Operational" 07 bands="CDMA2000 / GSM 900 / GSM 1800 / UMTS 2100" brand="Orange Kenya" cc="ke" country="Kenya" operator="Telkom Kenya" status="Operational" 00-99 640 02 bands="GSM 900 / GSM 1800" brand="tiGO" cc="tz" country="Tanzania" operator="MIC Tanzania Limited" status="Operational" 03 bands="GSM 900 / GSM 1800" brand="Zantel" cc="tz" country="Tanzania" operator="Zanzibar Telecom Ltd" status="Operational" 04 bands="GSM 900 / GSM 1800" brand="Vodacom" cc="tz" country="Tanzania" operator="Vodacom Tanzania Limited" status="Operational" 05 bands="GSM 900 / GSM 1800" brand="Airtel" cc="tz" country="Tanzania" operator="Bharti Airtel" status="Operational" 06 bands="CDMA" brand="Sasatel" cc="tz" country="Tanzania" operator="Dovetel Limited" status="Operational" 07 bands="CDMA 800" brand="TTCL Mobile" cc="tz" country="Tanzania" operator="Tanzania Telecommunication Company LTD (TTCL)" status="Operational" 08 bands="CDMA" brand="Benson Online (BOL)" cc="tz" country="Tanzania" operator="Benson Informatics Limited" status="Operational" 09 bands="???" brand="Hits" cc="tz" country="Tanzania" operator="ExcellentCom Tanzania Limited" status="Reserved" 11 bands="LTE 800" brand="SmileCom" cc="tz" country="Tanzania" operator="Smile Telecoms Holdings Ltd." status="Operational" 00-99 641 01 bands="GSM 900" brand="Airtel" cc="ug" country="Uganda" operator="Bharti Airtel" status="Operational" 10 bands="GSM 900 / LTE 2600" brand="MTN" cc="ug" country="Uganda" operator="MTN Uganda" status="Operational" 11 bands="GSM 900 / UMTS 2100" brand="UTL ( Telecom Limited)" cc="ug" country="Uganda" operator="Uganda Telecom Ltd." status="Operational" 14 bands="GSM 900 / GSM 1800 / LTE 800" brand="Orange" cc="ug" country="Uganda" operator="Orange Uganda" status="Operational" 22 bands="GSM 900 / GSM 1800" brand="Warid Telecom" cc="ug" country="Uganda" operator="Warid Telecom" status="Operational" 33 bands="LTE 800" brand="Smile" cc="ug" country="Uganda" operator="Smile Communications Uganda Limited" status="Operational" 44 bands="" brand="K2" cc="ug" country="Uganda" operator="K2 Telecom Ltd" status="" 66 bands="" brand="i-Tel" cc="ug" country="Uganda" operator="i-Tel Ltd" status="" 00-99 642 01 bands="GSM 900 / UMTS 2100" brand="Spacetel" cc="bi" country="Burundi" operator="Econet Wireless Burundi PLC" status="Operational" 02 bands="GSM 900" brand="Tempo" cc="bi" country="Burundi" operator="Africell PLC" status="Operational" 03 bands="GSM 900" brand="Onatel" cc="bi" country="Burundi" operator="Onatel" status="Operational" 07 bands="GSM 1800" brand="Smart Mobile" cc="bi" country="Burundi" operator="LACELL SU" status="Operational" 08 brand="HiTs Telecom" cc="bi" country="Burundi" operator="HiTs Telecom" status="Revoked" 82 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Leo" cc="bi" country="Burundi" operator="Orascom Telecom (a subsidiary of Vimplecom)" status="Operational" 00-99 643 01 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="mCel" cc="mz" country="Mozambique" operator="Mocambique Celular S.A." status="Operational" 03 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Movitel" cc="mz" country="Mozambique" operator="Movitel S.A." status="Operational" 04 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Vodacom" cc="mz" country="Mozambique" operator="Vodacom Mozambique, S.A." status="Operational" 00-99 645 01 bands="GSM 900" brand="Airtel" cc="zm" country="Zambia" operator="Bharti Airtel" status="Operational" 02 bands="GSM 900" brand="MTN" cc="zm" country="Zambia" operator="MTN Group" status="Operational" 03 bands="GSM 900" brand="ZAMTEL" cc="zm" country="Zambia" operator="Zambia Telecommunications Company Ltd" status="Operational" 00-99 646 01 bands="GSM 900 / GSM 1800" brand="Airtel" cc="mg" country="Madagascar" operator="Bharti Airtel" status="Operational" 02 bands="GSM 900" brand="Orange" cc="mg" country="Madagascar" operator="Orange Madagascar S.A." status="Operational" 03 bands="GSM 900" brand="Sacel" cc="mg" country="Madagascar" operator="Sacel Madagascar S.A." status="Operational" 04 bands="GSM 900" brand="Telma" cc="mg" country="Madagascar" operator="Telma Mobile S.A." status="Operational" 00-99 647 00 bands="GSM 900 / GSM 1800" brand="Orange" cc="re" country="Réunion (France)" operator="Orange La Réunion" status="Operational" 02 bands="GSM 900 / GSM 1800" brand="Outremer" cc="re" country="Réunion (France)" operator="Outremer Telecom" status="Operational" 10 bands="GSM 900" brand="SFR Reunion" cc="re" country="Réunion (France)" operator="Societe Reunionnaise de Radiotelephone" status="Operational" 00-99 648 01 bands="GSM 900" brand="Net*One" cc="zw" country="Zimbabwe" operator="Net*One Cellular (Pvt) Ltd" status="Operational" 03 bands="GSM 900" brand="Telecel" cc="zw" country="Zimbabwe" operator="Telecel Zimbabwe (PVT) Ltd" status="Operational" 04 bands="GSM 900 / GSM 1800 / UMTS 2100" brand="Econet" cc="zw" country="Zimbabwe" operator="Econet Wireless (Private) Limited" status="Operational" 00-99 649 01 bands="GSM 900 / GSM 1800 / LTE 1800" brand="MTC" cc="na" country="Namibia" operator="MTC Namibia" status="Operational" 02 bands="CDMA2000 800" brand="switch" cc="na" country="Namibia" operator="Telecom Namibia" status="Operational" 03 bands="GSM 900 / GSM 1800" brand="Leo" cc="na" country="Namibia" operator="Orascom Telecom Holding" status="Operational" 00-99 650 01 bands="GSM 900 / GSM 1800" brand="TNM" cc="mw" country="Malawi" operator="Telecom Network Malawi" status="Operational" 10 bands="GSM 900" brand="Airtel" cc="mw" country="Malawi" operator="Bharti Airtel Limited" status="Operational" 00-99 651 01 bands="GSM 900" brand="Vodacom" cc="ls" country="Lesotho" operator="Vodacom Lesotho (Pty) Ltd" status="Operational" 02 bands="" cc="ls" country="Lesotho" operator="Econet Ezi-cel" status="Operational" 00-99 652 01 bands="GSM 900" brand="Mascom" cc="bw" country="Botswana" operator="Mascom Wireless (Pty) Limited" status="Operational" 02 bands="GSM 900" brand="Orange" cc="bw" country="Botswana" operator="Orange (Botswana) Pty Limited" status="Operational" 04 bands="GSM 900 / GSM 1800" brand="BTC Mobile" cc="bw" country="Botswana" operator="Botswana Telecommunications Corporation" status="Operational" 00-99 653 10 bands="GSM 900" brand="Swazi MTN" cc="sz" country="Swaziland" operator="Swazi MTN Limited" status="Operational" 00-99 654 01 bands="" cc="km" country="Comoros" operator="HURI - SNPT" status="Operational" 00-99 655 01 bands="GSM 900 / GSM 1800 / UMTS 2100 / LTE 1800" brand="Vodacom" cc="za" country="South Africa" operator="Vodacom" status="Operational" 02 bands="GSM 1800 / UMTS 2100" brand="Telkom Mobile / 8.ta / Telekom SA" cc="za" country="South Africa" operator="MTN" status="Operational" 06 bands="" brand="Sentech" cc="za" country="South Africa" status="Operational" 07 bands="GSM 900 / GSM 1800 / UMTS 900 / LTE 2100" brand="Cell C" cc="za" country="South Africa" operator="Cell C" status="Operational" 10 bands="GSM 900 / UMTS 2100 / UMTS 900 / LTE 1800" brand="MTN" cc="za" country="South Africa" operator="MTN Group" status="Operational" 11 bands="TETRA 410" cc="za" country="South Africa" operator="South African Police Service Gauteng" status="Operational" 13 bands="CDMA2000 800" brand="Neotel" cc="za" country="South Africa" status="Operational" 19 bands="LTE" brand="iBurst" cc="za" country="South Africa" operator="Wireless Business Solutions (Pty) Ltd" status="Operational" 21 bands="TETRA 410" cc="za" country="South Africa" operator="Cape Town Metropolitan Council" status="Operational" 30 bands="" cc="za" country="South Africa" operator="Bokamoso Consortium" status="Operational" 31 bands="" cc="za" country="South Africa" operator="Karabo Telecoms (Pty) Ltd." status="Operational" 32 bands="" cc="za" country="South Africa" operator="Ilizwi Telecommunications" status="Operational" 33 bands="" cc="za" country="South Africa" operator="Thinta Thinta Telecommunications" status="Operational" 00-99 657 01 bands="GSM 900" brand="Eritel" cc="er" country="Eritrea" operator="Eritrea Telecommunications Services Corporation" status="Operational" 00-99 659 02 bands="GSM 900/1800, UMTS 2100" brand="MTN" country="South Sudan - SS" operator="MTN South Sudan" status="Operational" 03 bands="GSM 900/1800" brand="Gemtel" country="South Sudan - SS" operator="Gemtel" status="Operational" 04 bands="GSM 900/1800" brand="Vivacell" country="South Sudan - SS" operator="Network of the World (NOW)" status="Operational" 06 bands="GSM 900/1800" brand="Zain" country="South Sudan - SS" operator="Zain South Sudan" status="Operational" 07 bands="CDMA" brand="Sudani" country="South Sudan - SS" operator="Sudani" status="Operational" 00-99 702 67 bands="GSM 1900 / LTE 850 / LTE 1900" brand="DigiCell" cc="bz" country="Belize" operator="Belize Telemedia Ltd. (BTL)" status="Operational" 99 bands="CDMA2000" brand="Smart" cc="bz" country="Belize" operator="SpeedNet Communications Limited" status="Operational" 00-99 704 01 bands="CDMA2000 1900 / GSM 900 / GSM 1900 / UMTS/HSPA+ 1900" brand="Claro" cc="gt" country="Guatemala" operator="Telecomunicaciones de Guatemala, S.A." status="Operational" 02 bands="GSM 850 / TDMA 800 / UMTS/HSPA+ 850" brand="Tigo" cc="gt" country="Guatemala" operator="Millicom / Local partners" status="Operational" 03 bands="CDMA2000 1900 / GSM 1900 / UMTS/HSPA+ 1900" brand="movistar" cc="gt" country="Guatemala" operator="Telefónica Móviles Guatemala (Telefónica)" status="Operational" 00-99 706 01 bands="GSM 1900 / UMTS 1900" brand="Claro" cc="sv" country="El Salvador" operator="CTE Telecom Personal SA de CV América Móvil" status="Operational" 02 bands="GSM 900" brand="digicel" cc="sv" country="El Salvador" operator="Digicel Group" status="Operational" 03 bands="GSM 850" brand="Tigo" cc="sv" country="El Salvador" operator="Telemovil EL Salvador S.A." status="Operational" 04 bands="GSM 850" brand="movistar" cc="sv" country="El Salvador" operator="Telefónica Móviles El Salvador" status="Operational" 00-99 708 001 bands="GSM 1900" brand="Claro" cc="hn" country="Honduras" operator="Servicios de Comunicaciones de Honduras S.A. de C.V." status="Operational" 02 bands="CDMA2000 850 / GSM 850" brand="Tigo" cc="hn" country="Honduras" operator="Celtel / Tigo" status="Operational" 30 bands="GSM 1900" brand="Hondutel" cc="hn" country="Honduras" operator="Empresa Hondureña de Telecomunicaciones" status="Operational" 40 bands="GSM 1900" brand="DIGICEL" cc="hn" country="Honduras" operator="Digicel de Honduras" status="Operational" 000-999 710 21 bands="UMTS 850 / GSM 1900" brand="Claro" cc="ni" country="Nicaragua" operator="Empresa Nicaragüense de Telecomunicaciones, S.A. (ENITEL) (América Móvil)" status="Operational" 30 bands="UMTS 850 / GSM 850 / GSM 1900" brand="movistar" cc="ni" country="Nicaragua" operator="Telefonía Celular de Nicaragua, S.A. (Telefónica, S.A.)" status="Operational" 73 bands="UMTS 850 / GSM 1900" brand="SERCOM" cc="ni" country="Nicaragua" operator="Servicios de Comunicaciones S.A." status="Operational" 00-99 712 01 bands="GSM 1800 /LTE 2600, UMTS/HSPA+ 850" brand="Kolbi ICE" cc="cr" country="Costa Rica" operator="Instituto Costarricense de Electricidad" status="Operational" 017 bands="GSM 1800, UMTS/HSPA+ 850" brand="'full'móvil" cc="cr" country="Costa Rica" operator="Virtualis S.A." status="Operational" 02 bands="GSM 1800, UMTS/HSPA+ 850 / LTE 2600" brand="Kolbi ICE" cc="cr" country="Costa Rica" operator="Instituto Costarricense de Electricidad" status="Operational" 03 bands="GSM 1800 / UMTS 2100" brand="Claro" cc="cr" country="Costa Rica" operator="Claro CR Telecomunicaciones" status="Operational" 04 bands="GSM 1800, UMTS/HSPA+ 850/2100" brand="movistar" cc="cr" country="Costa Rica" operator="Telefónica Móviles Costa Rica" status="Operational" 00-99 714 01 bands="GSM 850 / UMTS 850" brand="Cable & Wireless" cc="pa" country="Panama" operator="Cable & Wireless Panama S.A." status="Operational" 02 bands="GSM 850 / UMTS 850 / UMTS 1900" brand="movistar" cc="pa" country="Panama" operator="Telefónica Moviles Panama S.A, Bell South Corp. (BSC)" status="Operational" 03 bands="GSM 1900 / UMTS 1900" brand="Claro" cc="pa" country="Panama" operator="América Móvil" status="Operational" 04 bands="GSM 1900 / UMTS 1900" brand="Digicel" cc="pa" country="Panama" operator="Digicel Group" status="Operational" 00-99 716 06 bands="CDMA2000 850 / GSM 850 / UMTS 850" brand="Movistar" cc="pe" country="Peru" operator="Telefónica Móviles Perú" status="Operational" 07 bands="iDEN / UMTS 1900" brand="NEXTEL" cc="pe" country="Peru" operator="Americatel Perú" status="Inactive" 10 bands="GSM 1900 / UMTS 850" brand="Claro (TIM)" cc="pe" country="Peru" operator="América Móvil Perú" status="Operational" 15 bands="GSM 1900 / UMTS 1900" brand="Viettel Mobile" cc="pe" country="Peru" operator="Viettel Peru S.A.C." status="Operational" 17 bands="iDEN / UMTS 1900" brand="NEXTEL" cc="pe" country="Peru" operator="Americatel Perú" status="Operational" 00-99 722 010 bands="GSM 850 / GSM 1900" brand="Movistar" cc="ar" country="Argentina" operator="Telefónica Móviles Argentina S.A." status="Operational" 020 bands="iDEN 800" brand="Nextel" cc="ar" country="Argentina" operator="NII Holdings" status="Operational" 040 bands="" brand="Globalstar" cc="ar" country="Argentina" operator="TE.SA.M Argentina S.A." status="Operational" 070 bands="GSM 1900" brand="Movistar" cc="ar" country="Argentina" operator="Telefónica Móviles Argentina S.A." status="Operational" 310 bands="GSM 1900" brand="Claro" cc="ar" country="Argentina" operator="AMX Argentina S.A." status="Operational" 320 bands="GSM 850 / GSM 1900" brand="Claro" cc="ar" country="Argentina" operator="AMX Argentina S.A." status="Operational" 330 bands="GSM 850 / GSM 1900" brand="Claro" cc="ar" country="Argentina" operator="AMX Argentina S.A." status="Operational" 340 bands="GSM 850 / GSM 1900" brand="Personal" cc="ar" country="Argentina" operator="Telecom Personal S.A." status="Operational" 350 bands="GSM 900" brand="PORT-HABLE" cc="ar" country="Argentina" operator="Hutchison Telecommunications Argentina S.A." status="Operational" 000-999 724 00 bands="IDEN 850" brand="Nextel" cc="br" country="Brazil" operator="NII Holdings, Inc." status="Operational" 02 bands="GSM 900 / GSM 1800 / UMTS 850 / UMTS 2100 / LTE 2600" brand="TIM" cc="br" country="Brazil" operator="Telecom Italia Mobile" status="Operational" 03 bands="GSM 900 / GSM 1800 / UMTS 850 / UMTS 2100 / LTE 2600" brand="TIM" cc="br" country="Brazil" operator="Telecom Italia Mobile" status="Operational" 04 bands="GSM 900 / GSM 1800 / UMTS 850 / UMTS 2100 / LTE 2600" brand="TIM" cc="br" country="Brazil" operator="Telecom Italia Mobile" status="Operational" 05 bands="GSM 900 / GSM 1800 / UMTS 850 / UMTS 2100 / LTE 2600" brand="Claro BR" cc="br" country="Brazil" operator="Claro" status="Operational" 055 bands="GSM 900 / GSM 1800 / UMTS 850" brand="Sercomtel" cc="br" country="Brazil" operator="Sercomtel Celular" status="Operational" 06 bands="GSM 850/900/1800/1900 / UMTS 850 / UMTS 2100 / LTE 2600" brand="Vivo" cc="br" country="Brazil" operator="Vivo S.A." status="Operational" 10 bands="GSM 850/900/1800/1900 / UMTS 850 / UMTS 2100 / LTE 2600" brand="Vivo" cc="br" country="Brazil" operator="Vivo S.A." status="Operational" 11 bands="GSM 850/900/1800/1900 / UMTS 850 / UMTS 2100 / LTE 2600" brand="Vivo" cc="br" country="Brazil" operator="Vivo S.A." status="Operational" 15 bands="GSM 900/1800 UMTS 850 / UMTS 2100mhz" brand="CTBC Celular" cc="br" country="Brazil" operator="CTBC Celular S.A." status="Operational" 16 bands="GSM 1800 / UMTS 2100" brand="Brasil Telecom GSM" cc="br" country="Brazil" operator="Brasil Telecom GSM" status="Phasing out" 23 bands="GSM 850/900/1800/1900 / UMTS 850 / UMTS 2100 / LTE 2600" brand="Vivo" cc="br" country="Brazil" operator="Vivo S.A." status="Operational" 31 bands="GSM 1800 / UMTS 2100 / LTE 2600" brand="Oi" cc="br" country="Brazil" operator="TNL PCS" status="Operational" 32 bands="GSM 900/1800 UMTS 850 / UMTS 2100mhz" brand="CTBC Celular" cc="br" country="Brazil" operator="CTBC Celular S.A." status="Operational" 33 bands="GSM 900/1800 UMTS 850 / UMTS 2100mhz" brand="CTBC Celular" cc="br" country="Brazil" operator="CTBC Celular S.A." status="Operational" 34 bands="GSM 900/1800 UMTS 850 / UMTS 2100mhz" brand="CTBC Celular" cc="br" country="Brazil" operator="CTBC Celular S.A." status="Operational" 39 bands="UMTS 2100" brand="Nextel" cc="br" country="Brazil" operator="NII Holdings, Inc." status="Deploying" 00-99 730 01 bands="GSM 1900 / UMTS 1900" brand="entel" cc="cl" country="Chile" operator="Entel PCS Telecomunicaciones S.A." status="Operational" 02 bands="GSM 850 / UMTS 850 / UMTS 1900" brand="movistar" cc="cl" country="Chile" operator="Telefónica Móvil de Chile" status="Operational" 03 bands="GSM 1900 / UMTS 1900 / UMTS 850 / LTE 2600" brand="Claro" cc="cl" country="Chile" operator="Claro Chile S.A." status="Operational" 04 bands="iDEN 800" brand="Nextel" cc="cl" country="Chile" operator="Centennial Cayman Corp. Chile" status="Operational" 07 bands="Same of movistar (virtual operator)" brand="Virgin Mobile" cc="cl" country="Chile" operator="Virgin Mobile" status="Operational" 08 bands="UMTS 1700/2100 (AWS) / UMTS 850" brand="VTR Móvil" cc="cl" country="Chile" operator="VTR S.A." status="Operational" 09 bands="UMTS 1700 / UMTS 2100" brand="Nextel" cc="cl" country="Chile" operator="Centennial Cayman Corp. Chile" status="Operational" 10 bands="GSM 1900 / UMTS 1900" brand="entel" cc="cl" country="Chile" operator="Entel Telefonía Móvil S.A." status="Operational" 99 bands="GSM 1900 / UMTS 1900 (Residential)." brand="Will" cc="cl" country="Chile" operator="WILL Telefonía" status="Operational" 00-99 732 001 bands="" cc="co" country="Colombia" operator="Colombia Telecomunicaciones S.A." status="Operational" 002 bands="" brand="Edatel" cc="co" country="Colombia" operator="Edatel S.A." status="Operational" 101 bands="GSM 850 / GSM 1900" brand="Claro" cc="co" country="Colombia" operator="Claro (Comcel)" status="Operational" 102 bands="GSM 850 / GSM 1900 / CDMA2000 850" brand="movistar" cc="co" country="Colombia" operator="Bellsouth Colombia" status="Operational" 103 bands="GSM 1900" brand="Tigo" cc="co" country="Colombia" operator="Colombia Móvil" status="Operational" 111 bands="GSM 1900" brand="Tigo" cc="co" country="Colombia" operator="Colombia Móvil" status="Operational" 123 bands="GSM 850 / GSM 1900 / CDMA2000 850" brand="movistar" cc="co" country="Colombia" operator="Telefónica Móviles Colombia" status="Operational" 000-999 734 01 bands="GSM 900 / UMTS 900" brand="Digitel" cc="ve" country="Venezuela" operator="Corporacion Digitel C.A." status="Operational" 02 bands="GSM 900 / UMTS 900 / LTE 1800" brand="Digitel GSM" cc="ve" country="Venezuela" operator="Corporacion Digitel C.A." status="Operational" 03 bands="GSM 900 / UMTS 900" brand="Digitel" cc="ve" country="Venezuela" operator="Corporacion Digitel C.A." status="Operational" 04 bands="CDMA2000 850 / GSM 850 / GSM 1900 / UMTS 1900" brand="movistar" cc="ve" country="Venezuela" operator="Telefónica Móviles Venezuela" status="Operational" 06 bands="CDMA2000 850 / GSM 850 / UMTS 1900" brand="Movilnet" cc="ve" country="Venezuela" operator="Telecomunicaciones Movilnet" status="Operational" 00-99 736 01 bands="GSM 1900" brand="Nuevatel" cc="bo" country="Bolivia" operator="Nuevatel PCS De Bolivia SA" status="Operational" 02 bands="GSM 1900" brand="Entel" cc="bo" country="Bolivia" operator="Entel SA" status="Operational" 03 bands="GSM 850" brand="Tigo" cc="bo" country="Bolivia" operator="Telefónica Celular De Bolivia S.A" status="Operational" 00-99 738 01 bands="GSM 900" brand="Digicel" cc="gy" country="Guyana" operator="U-Mobile (Cellular) Inc." status="Operational" 02 bands="GSM 900" brand="GT&T Cellink Plus" cc="gy" country="Guyana" operator="Guyana Telephone & Telegraph Co." status="Operational" 00-99 740 00 bands="GSM 850 / UMTS 900 / UMTS 1900" brand="Movistar" cc="ec" country="Ecuador" operator="Otecel S.A." status="Operational" 01 bands="GSM 850 / UMTS 850 / UMTS 1900" brand="Claro" cc="ec" country="Ecuador" operator="CONECEL S.A." status="Operational" 02 bands="GSM 850 / CDMA2000 1900" brand="CNT Mobile" cc="ec" country="Ecuador" operator="Corporación Nacional de Telecomunicaciones (CNT EP)" status="Operational" 00-99 744 01 bands="GSM 1900 / UMTS 900" brand="VOX" cc="py" country="Paraguay" operator="Hola Paraguay S.A" status="Operational" 02 bands="GSM 1900 / UMTS 1900" brand="Claro/Hutchison" cc="py" country="Paraguay" operator="AMX Paraguay S.A." status="Operational" 04 bands="GSM 850 / UMTS 850" brand="Tigo" cc="py" country="Paraguay" operator="Telefónica Celular Del Paraguay S.A. (Telecel)" status="Operational" 05 bands="GSM 850 / GSM 1900 / UMTS 850 / UMTS 1900 / LTE 1900" brand="Personal" cc="py" country="Paraguay" operator="Núcleo S.A(TIM)" status="Operational" 06 bands="GSM 1800 / LTE 1700" brand="Copaco" cc="py" country="Paraguay" operator="Copaco S.A." status="Operational" 00-99 746 02 bands="GSM 900 / GSM 1800" brand="Telesur" cc="sr" country="Suriname" operator="Telecommunications Company Suriname (Telesur)" status="Operational" 03 bands="GSM 900/ GSM 1800" brand="Digicel" cc="sr" country="Suriname" operator="Digicel Group Limited" status="Operational" 04 bands="GSM 900" brand="Uniqa" cc="sr" country="Suriname" operator="Intelsur N.V. / UTS N.V." status="Operational" 00-99 748 01 bands="GSM 900/1800/ UMTS 850/2100 / LTE 1700" brand="Antel" cc="uy" country="Uruguay" operator="Compania estatal (ANTEL)" status="Operational" 07 bands="GSM 850/1900 / UMTS 850" brand="Movistar" cc="uy" country="Uruguay" operator="Telefónica Móviles Uruguay" status="Operational" 10 bands="GSM/UMTS 1900" brand="Claro" cc="uy" country="Uruguay" operator="AM Wireless Uruguay S.A." status="Operational" 00-99 901 01 bands="Satellite" brand="ICO" country="International" operator="ICO Satellite Management" status="Operational" 02 bands="" country="International" operator="Unassigned" status="Returned spare" 03 bands="Satellite" brand="Iridium" country="International" status="Operational" 04 bands="Satellite" country="International" operator="Unassigned" status="Returned spare" 05 bands="Satellite" country="International" operator="Thuraya RMSS Network" status="Operational" 06 bands="Satellite" country="International" operator="Thuraya Satellite Telecommunications Company" status="Operational" 07 bands="" country="International" operator="Unassigned" status="Returned spare" 08 bands="" country="International" operator="Unassigned" status="Returned spare" 09 bands="" country="International" operator="Unassigned" status="Returned spare" 10 bands="Satellite" brand="ACeS" country="International" status="Operational" 11 bands="Satellite" brand="Inmarsat" country="International" status="Operational" 12 bands="GSM 1800" brand="Telenor" country="International" operator="Maritime Communications Partner AS" status="Operational" 13 bands="GSM 1800" brand="GSM.AQ" country="International" operator="Global Networks Switzerland Inc." status="Operational" 14 bands="GSM 1800" country="International" operator="AeroMobile AS" status="" 15 bands="GSM 1800" brand="OnAir" country="International" operator="OnAir Switzerland Sarl" status="Operational" 16 bands="" country="International" operator="Jasper Systems" status="Operational" 17 bands="GSM 1800" brand="Navitas" country="International" status="Operational" 18 bands="GSM 900 / GSM 1900 / CDMA2000 1900" brand="Cellular @Sea" country="International" operator="AT&T Mobility" status="Operational" 19 bands="" country="International" operator="Vodafone Malta Maritime" status="Operational" 20 bands="" country="International" operator="Intermatica" status="" 21 bands="" country="International" operator="Unassigned" status="Returned spare" 22 bands="" country="International" operator="MediaLincc Ltd" status="" 23 bands="" country="International" operator="Unassigned" status="Returned spare" 24 bands="" brand="iNum" country="International" operator="Voxbone" status="" 25 bands="" country="International" operator="Unassigned" status="Returned spare" 26 bands="" brand="TIM" country="International" operator="Telecom Italia" status="Operational" 27 bands="" brand="OnAir" country="International" operator="OnAir" status="Operational" 28 bands="Roaming SIM" brand="Vodafone" country="International" operator="GDSP (Vodafone's Global Data Service Platform)" status="Operational" 29 bands="" brand="Telenor" country="International" status="" 30 bands="" country="International" operator="Unassigned" status="Returned spare" 31 bands="GSM 900" brand="Orange" country="International" operator="Orange S.A." status="Operational" 32 bands="GSM 900" brand="Sky High" country="International" operator="MegaFon" status="Operational" 33 bands="" country="International" operator="Smart Communications" status="" 34 bands="" country="International" operator="tyntec GmbH" status="" 35 bands="" country="International" operator="Globecomm Network Services" status="" 36 bands="GSM 1800" country="International" operator="Azerfon" status="Operational" 88 bands="" country="International" operator="UN Office for the Coordination of Humanitarian Affairs (OCHA)" status="" 00-99 python-stdnum-0.9/stdnum/at/0000755000000000000000000000000012260536561016075 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/at/uid.py0000644000000000000000000000462712154624370017237 0ustar rootroot00000000000000# vat.py - functions for handling Austrian VAT numbers # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """UID (Umsatzsteuer-Identifikationsnummer, Austrian VAT number). The Austrian UID is a 9-digit number that starts with a U (optionally preceded with AT). The last digit is a check digit. >>> validate('AT U13585627') 'U13585627' >>> calc_check_digit('U1358562') '7' >>> validate('U13585626') # incorrect check digit Traceback (most recent call last): ... InvalidChecksum: ... """ from stdnum import luhn from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, ' -./').upper().strip() if number.startswith('AT'): number = number[2:] return number def calc_check_digit(number): """Calculate the check digit. The number passed should not have the check digit included.""" return str((6 - luhn.checksum(number[1:])) % 10) def validate(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" number = compact(number) if number[:1] != 'U' or not number[1:].isdigit(): raise InvalidFormat() if len(number) != 9: raise InvalidLength() if calc_check_digit(number[:-1]) != number[-1]: raise InvalidChecksum() return number def is_valid(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/at/__init__.py0000644000000000000000000000164211720140727020204 0ustar rootroot00000000000000# __init__.py - collection of Austrian numbers # coding: utf-8 # # Copyright (C) 2012 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of Austrian numbers.""" # provide vat as an alias from stdnum.at import uid as vat python-stdnum-0.9/stdnum/gb/0000755000000000000000000000000012260536561016061 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/gb/__init__.py0000644000000000000000000000156211720140726020170 0ustar rootroot00000000000000# __init__.py - collection of United Kingdom numbers # coding: utf-8 # # Copyright (C) 2012 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of United Kingdom numbers.""" python-stdnum-0.9/stdnum/gb/vat.py0000644000000000000000000001036012260400322017206 0ustar rootroot00000000000000# vat.py - functions for handling United Kingdom VAT numbers # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """VAT (United Kingdom (and Isle of Man) VAT registration number). The VAT number can either be a 9-digit standard number, a 12-digit standard number followed by a 3-digit branch identifier, a 5-digit number for government departments (first two digits are GD) or a 5-digit number for health authorities (first two digits are HA). The 9-digit variants use a weighted checksum. >>> validate('GB 980 7806 84') '980780684' >>> validate('802311781') # invalid check digit Traceback (most recent call last): ... InvalidChecksum: ... >>> format('980780684') '980 7806 84' """ from stdnum.util import clean from stdnum.exceptions import * def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, ' -.').upper().strip() if number.startswith('GB'): number = number[2:] return number def checksum(number): """Calculate the checksum. The checksum is only used for the 9 digits of the number and the result can either be 0 or 42.""" weights = (8, 7, 6, 5, 4, 3, 2, 10, 1) return sum(weights[i] * int(n) for i, n in enumerate(number)) % 97 def validate(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" number = compact(number) if len(number) == 5: if not number[2:].isdigit(): raise InvalidFormat() if number.startswith('GD') and int(number[2:]) < 500: # government department pass elif number.startswith('HA') and int(number[2:]) >= 500: # health authority pass else: raise InvalidComponent() elif len(number) == 11 and number[0:6] in ('GD8888', 'HA8888'): if not number[6:].isdigit(): raise InvalidFormat() if number.startswith('GD') and int(number[6:9]) < 500: # government department pass elif number.startswith('HA') and int(number[6:9]) >= 500: # health authority pass else: raise InvalidComponent() if int(number[6:9]) % 97 != int(number[9:11]): raise InvalidChecksum() elif len(number) in (9, 12): if not number.isdigit(): raise InvalidFormat() # standard number: nnn nnnn nn # branch trader: nnn nnnn nn nnn (ignore the last thee digits) # restarting: 100 nnnn nn if int(number[:3]) >= 100: if checksum(number[:9]) not in (0, 42, 55): raise InvalidChecksum() else: if checksum(number[:9]) != 0: raise InvalidChecksum() else: raise InvalidLength() return number def is_valid(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False def format(number): """Reformat the passed number to the standard format.""" number = compact(number) if len(number) == 5: # government department or health authority return number if len(number) == 12: # includes branch number return number[:3] + ' ' + number[3:7] + ' ' + number[7:9] + ' ' + number[9:] # standard number: nnn nnnn nn return number[:3] + ' ' + number[3:7] + ' ' + number[7:] python-stdnum-0.9/stdnum/isil.py0000644000000000000000000000552012154624370017003 0ustar rootroot00000000000000# isil.py - functions for handling identifiers for libraries and related # organizations # # Copyright (C) 2011, 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """ISIL (International Standard Identifier for Libraries). The ISIL is the International Standard Identifier for Libraries and Related Organizations. >>> validate('IT-RM0267') 'IT-RM0267' >>> validate('OCLC-DLC') 'OCLC-DLC' >>> validate('WW-RM0267') # unregistered country code Traceback (most recent call last): ... InvalidComponent: ... >>> validate('WW-RM026712423345334534512334534545') # too long Traceback (most recent call last): ... InvalidLength: ... >>> format('it-RM0267') 'IT-RM0267' """ from stdnum.exceptions import * from stdnum.util import clean # the valid characters in an ISIL _alphabet = set('0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz-:/') def compact(number): """Convert the ISIL to the minimal representation. This strips surrounding whitespace.""" return clean(number, '').strip() def _known_agency(agency): """Checks whether the specified agency is valid.""" # look it up in the db from stdnum import numdb results = numdb.get('isil').info(agency.upper() + '$') # there should be only one part and it should have properties return len(results) == 1 and bool(results[0][1]) def validate(number): """Checks to see if the number provided is a valid isil (or isilSV) number.""" number = compact(number) for n in number: if n not in _alphabet: raise InvalidFormat() if len(number) > 15: raise InvalidLength() if not _known_agency(number.split('-')[0]): raise InvalidComponent() return number def is_valid(number): """Checks to see if the number provided is a valid isil (or isilSV) number.""" try: return bool(validate(number)) except ValidationError: return False def format(number): """Reformat the passed number to the standard format.""" number = compact(number) parts = number.split('-') if len(parts) > 1 and _known_agency(parts[0]): parts[0] = parts[0].upper() return '-'.join(parts) python-stdnum-0.9/stdnum/nl/0000755000000000000000000000000012260536561016102 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/nl/bsn.py0000644000000000000000000000521112154624371017234 0ustar rootroot00000000000000# bsn.py - functions for handling BSNs # # Copyright (C) 2010, 2011, 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """BSN (Burgerservicenummer, Dutch national identification number). The BSN is a number with up to 9 digits (the leading 0's are commonly left out) which is used as the Dutch national identification number. >>> validate('1112.22.333') '111222333' >>> validate('1112.52.333') Traceback (most recent call last): ... InvalidChecksum: ... >>> validate('1112223334') Traceback (most recent call last): ... InvalidLength: ... >>> format('111222333') '1112.22.333' """ from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, ' -.').strip() # pad with leading zeroes return (9 - len(number)) * '0' + number def checksum(number): """Calculate the checksum over the number. A valid number should have a check digit of 0.""" return (sum((9 - i) * int(n) for i, n in enumerate(number[:-1])) - int(number[-1])) % 11 def validate(number): """Checks to see if the number provided is a valid BSN. This checks the length and whether the check digit is correct.""" number = compact(number) if not number.isdigit() or int(number) <= 0: raise InvalidFormat() if len(number) != 9: raise InvalidLength() if checksum(number) != 0: raise InvalidChecksum() return number def is_valid(number): """Checks to see if the number provided is a valid BSN. This checks the length and whether the check digit is correct.""" try: return bool(validate(number)) except ValidationError: return False def format(number): """Reformat the passed number to the standard format.""" number = compact(number) return number[:4] + '.' + number[4:6] + '.' + number[6:] python-stdnum-0.9/stdnum/nl/postcode.py0000644000000000000000000000445412237755523020310 0ustar rootroot00000000000000# postcode.py - functions for handling Dutch postal codes # # Copyright (C) 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Postcode (Dutch postal code). The Dutch postal code consists of four numbers followed by two letters. >>> validate('2601 DC') '2601 DC' >>> validate('NL-2611ET') '2611 ET' >>> validate('26112 ET') Traceback (most recent call last): ... InvalidFormat: ... >>> validate('2611 SS') # a few letter combinations are banned Traceback (most recent call last): ... InvalidComponent: ... """ import re from stdnum.exceptions import * from stdnum.util import clean _postcode_re = re.compile(r'^(?P[1-9][0-9]{3})(?P[A-Z]{2})$') _postcode_blacklist = ('SA', 'SD' ,'SS') def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, ' -').upper().strip() if number.startswith('NL'): number = number[2:] return number def validate(number): """Checks to see if the number provided is in the correct format. This currently does not check whether the code corresponds to a real address.""" number = compact(number) match = _postcode_re.search(number) if not match: raise InvalidFormat() if match.group('pt2') in _postcode_blacklist: raise InvalidComponent() return '%s %s' % (match.group('pt1'), match.group('pt2')) def is_valid(number): """Checks to see if the number provided is a valid postal code.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/nl/onderwijsnummer.py0000644000000000000000000000451312237446523021711 0ustar rootroot00000000000000# onderwijsnummer.py - functions for handling onderwijsnummers # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Onderwijsnummer (Dutch student school number). The onderwijsnummers (education number) is very similar to the BSN (Dutch national identification number) for students without a BSN. It uses a checksum mechanism similar to the BSN. >>> validate('1012.22.331') '101222331' >>> validate('100252333') Traceback (most recent call last): ... InvalidChecksum: ... >>> validate('1012.22.3333') Traceback (most recent call last): ... InvalidLength: ... >>> validate('2112.22.337') # number must start with 10 Traceback (most recent call last): ... InvalidFormat: ... """ from stdnum.exceptions import * from stdnum.nl.bsn import compact, checksum __all__ = ['compact', 'validate', 'is_valid'] def validate(number): """Checks to see if the number provided is a valid onderwijsnummer. This checks the length and whether the check digit is correct and whether it starts with the right sequence.""" number = compact(number) if not number.isdigit() or int(number) <= 0: raise InvalidFormat() if not number.startswith('10'): raise InvalidFormat() if len(number) != 9: raise InvalidLength() if checksum(number) != 5: raise InvalidChecksum() return number def is_valid(number): """Checks to see if the number provided is a valid onderwijsnummer. This checks the length and whether the check digit is correct and whether it starts with the right sequence.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/nl/__init__.py0000644000000000000000000000171112237755523020220 0ustar rootroot00000000000000# __init__.py - collection of Dutch numbers # coding: utf-8 # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of Dutch numbers.""" # provide aliases from stdnum.nl import btw as vat from stdnum.nl import postcode as postcal_code python-stdnum-0.9/stdnum/nl/brin.py0000644000000000000000000000513512237446563017420 0ustar rootroot00000000000000# brin.py - functions for handling Brin numbers # # Copyright (C) 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Brin number (Dutch number for schools). The Brin (Basis Registratie Instellingen) is a number to identify schools and related institutions. The number consists of four alphanumeric characters, sometimes extended with two digits to indicate the site (this complete code is called the vestigingsnummer). The register of these numbers can be downloaded from: http://www.duo.nl/organisatie/open_onderwijsdata/databestanden/default.asp >>> validate('05 KO') '05KO' >>> validate('07NU 00') '07NU00' >>> validate('12KB1') Traceback (most recent call last): ... InvalidLength: ... >>> validate('30AJ0A') # location code has letter Traceback (most recent call last): ... InvalidFormat: ... """ import re from stdnum.exceptions import * from stdnum.util import clean # this regular expression is based on what was found in the online # database: the first two digits are always numeric, followed by two # letters and an optional two letter location identifier _brin_re = re.compile(r'^(?P[0-9]{2}[A-Z]{2})(?P[0-9]{2})?$') def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" return clean(number, ' -.').upper().strip() def validate(number): """Checks to see if the number provided is in the correct format. This currently does not check whether the number points to a registered school.""" number = compact(number) if len(number) not in (4, 6): raise InvalidLength() match = _brin_re.search(number) if not match: raise InvalidFormat() return number def is_valid(number): """Checks to see if the number provided is a valid Brin number.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/nl/btw.py0000644000000000000000000000443212260526656017257 0ustar rootroot00000000000000# btw.py - functions for handling Dutch VAT numbers # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """BTW-nummer (Omzetbelastingnummer, the Dutch VAT number). The BTW-nummer is the Dutch number for VAT. It consists of a RSIN or BSN followed by a B and two digits that identify the unit within the organisation (usually 01). >>> validate('004495445B01') '004495445B01' >>> validate('NL4495445B01') '004495445B01' >>> validate('123456789B90') Traceback (most recent call last): ... InvalidChecksum: ... """ from stdnum.exceptions import * from stdnum.nl import bsn from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, ' -.').upper().strip() if number.startswith('NL'): number = number[2:] return bsn.compact(number[:-3]) + number[-3:] def validate(number): """Checks to see if the number provided is a valid BTW number. This checks the length, formatting and check digit.""" number = compact(number) if not number[10:].isdigit() or int(number[10:]) <= 0: raise InvalidFormat() if len(number) != 12: raise InvalidLength() if number[9] != 'B': raise InvalidFormat() bsn.validate(number[:9]) return number def is_valid(number): """Checks to see if the number provided is a valid BTW number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/exceptions.py0000644000000000000000000000420512154624370020223 0ustar rootroot00000000000000# exceptions.py - collection of stdnum exceptions # coding: utf-8 # # Copyright (C) 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of exceptions. The validation functions of stdnum should raise one of the below exceptions when validation of the number fails. """ class ValidationError(Exception): """Top-level error for validating numbers. This exception should normally not be raised, only subclasses of this exception.""" def __str__(self): return getattr(self, 'message', '') class InvalidFormat(ValidationError): """Something is wrong with the format of the number. This generally means characters or delimiters that are not allowed are part of the number or required parts are missing.""" message = 'The number has an invalid format.' class InvalidChecksum(ValidationError): """The number's internal checksum or check digit does not match.""" message = "The number's checksum or check digit is invalid." class InvalidLength(InvalidFormat): """The length of the number is wrong.""" message = 'The number has an invalid length.' class InvalidComponent(ValidationError): """One of the parts of the number has an invalid reference. Some part of the number refers to some external entity like a country code, a date or a predefined collection of values. The number contains some invalid reference.""" message = 'One of the parts of the number are invalid or unknown.' python-stdnum-0.9/stdnum/de/0000755000000000000000000000000012260536561016061 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/de/__init__.py0000644000000000000000000000154211720140724020164 0ustar rootroot00000000000000# __init__.py - collection of German numbers # coding: utf-8 # # Copyright (C) 2012 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of German numbers.""" python-stdnum-0.9/stdnum/de/vat.py0000644000000000000000000000417012154624370017225 0ustar rootroot00000000000000# vat.py - functions for handling German VAT numbers # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Ust ID Nr. (Umsatzsteur Identifikationnummer, German VAT number). The number is 10 digits long and uses the ISO 7064 Mod 11, 10 check digit algorithm. >>> compact('DE 136,695 976') '136695976' >>> validate('DE136695976') '136695976' >>> validate('136695978') Traceback (most recent call last): ... InvalidChecksum: ... """ from stdnum.exceptions import * from stdnum.iso7064 import mod_11_10 from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, ' -./,').upper().strip() if number.startswith('DE'): number = number[2:] return number def validate(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" number = compact(number) if not number.isdigit() or number[0] == '0': raise InvalidFormat() if len(number) != 9: raise InvalidLength() mod_11_10.validate(number) return number def is_valid(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/se/0000755000000000000000000000000012260536561016100 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/se/__init__.py0000644000000000000000000000154411720140730020202 0ustar rootroot00000000000000# __init__.py - collection of Swedish numbers # coding: utf-8 # # Copyright (C) 2012 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of Swedish numbers.""" python-stdnum-0.9/stdnum/se/vat.py0000644000000000000000000000432212154624371017244 0ustar rootroot00000000000000# vat.py - functions for handling Swedish VAT numbers # coding: utf-8 # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """VAT (Moms, Mervärdesskatt, Swedish VAT number). The Momsregistreringsnummer is used for VAT (Moms, Mervärdesskatt) purposes and consists of 12 digits of which the last two should be 01. The first 10 digits should have a valid Luhn checksum. >>> validate('SE 123456789701') '123456789701' >>> validate('123456789101') # invalid check digits Traceback (most recent call last): ... InvalidChecksum: ... """ from stdnum import luhn from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, ' -.').upper().strip() if number.startswith('SE'): number = number[2:] return number def validate(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" number = compact(number) if not number.isdigit() or number[-2:] != '01': raise InvalidFormat() if len(number) != 12: raise InvalidLength() luhn.validate(number[:-2]) return number def is_valid(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/isbn.dat0000644000000000000000000003411512260533041017110 0ustar rootroot00000000000000# generated from RangeMessage.xml, downloaded from # http://www.isbn-international.org/agency?rmxml=1 # file serial be2e8e46-b368-41c0-8603-5938a5e7e0f7 # file date Mon, 25 Nov 2013 09:51:28 GMT 978 0-5,600-649,7-7,80-94,950-989,9900-9989,99900-99999 0 agency="English language" 00-19,200-699,7000-8499,85000-89999,900000-949999,9500000-9999999 1 agency="English language" 00-09,100-399,4000-5499,55000-86979,869800-998999,9990000-9999999 2 agency="French language" 00-19,200-349,35000-39999,400-699,7000-8399,84000-89999,900000-949999 9500000-9999999 3 agency="German language" 00-02,030-033,0340-0369,03700-03999,04-19,200-699,7000-8499,85000-89999 900000-949999,9500000-9539999,95400-96999,9700000-9899999,99000-99499 99500-99999 4 agency="Japan" 00-19,200-699,7000-8499,85000-89999,900000-949999,9500000-9999999 5 agency="Russian Federation and former USSR" 00000-00499,0050-0099,01-19,200-420,4210-4299,430-430,4310-4399,440-440 4410-4499,450-699,7000-8499,85000-89999,900000-909999,91000-91999 9200-9299,93000-94999,9500000-9500999,9501-9799,98000-98999 9900000-9909999,9910-9999 600 agency="Iran" 00-09,100-499,5000-8999,90000-99999 601 agency="Kazakhstan" 00-19,200-699,7000-7999,80000-84999,85-99 602 agency="Indonesia" 00-10,1100-1199,1200-1399,14000-14999,1500-1699,17000-17999,18000-18999 19000-19999,200-749,7500-7999,8000-9499,95000-99999 603 agency="Saudi Arabia" 00-04,05-49,500-799,8000-8999,90000-99999 604 agency="Vietnam" 0-4,50-89,900-979,9800-9999 605 agency="Turkey" 01-09,100-399,4000-5999,60000-89999,90-99 606 agency="Romania" 0-0,10-49,500-799,8000-9199,92000-99999 607 agency="Mexico" 00-39,400-749,7500-9499,95000-99999 608 agency="Macedonia" 0-0,10-19,200-449,4500-6499,65000-69999,7-9 609 agency="Lithuania" 00-39,400-799,8000-9499,95000-99999 611 agency="Thailand" 612 agency="Peru" 00-29,300-399,4000-4499,45000-49999,50-99 613 agency="Mauritius" 0-9 614 agency="Lebanon" 00-39,400-799,8000-9499,95000-99999 615 agency="Hungary" 00-09,100-499,5000-7999,80000-89999 616 agency="Thailand" 00-19,200-699,7000-8999,90000-99999 617 agency="Ukraine" 00-49,500-699,7000-8999,90000-99999 618 agency="Greece" 00-19,200-499,5000-7999,80000-99999 619 agency="Bulgaria" 00-14,150-699,7000-8999,90000-99999 620 agency="Mauritius" 0-9 621 agency="Philippines" 00-29,400-599,8000-8999,95000-99999 7 agency="China, People's Republic" 00-09,100-499,5000-7999,80000-89999,900000-999999 80 agency="Czech Republic and Slovakia" 00-19,200-699,7000-8499,85000-89999,900000-999999 81 agency="India" 00-19,200-699,7000-8499,85000-89999,900000-999999 82 agency="Norway" 00-19,200-699,7000-8999,90000-98999,990000-999999 83 agency="Poland" 00-19,200-599,60000-69999,7000-8499,85000-89999,900000-999999 84 agency="Spain" 00-13,140-149,15000-19999,200-699,7000-8499,85000-89999,9000-9199 920000-923999,92400-92999,930000-949999,95000-96999,9700-9999 85 agency="Brazil" 00-19,200-599,60000-69999,7000-8499,85000-89999,900000-979999,98000-99999 86 agency="Serbia (shared)" 00-29,300-599,6000-7999,80000-89999,900000-999999 87 agency="Denmark" 00-29,400-649,7000-7999,85000-94999,970000-999999 88 agency="Italy" 00-19,200-599,6000-8499,85000-89999,900000-909999,910-929,9300-9399 940000-949999,95000-99999 89 agency="Korea, Republic" 00-24,250-549,5500-8499,85000-94999,950000-969999,97000-98999,990-999 90 agency="Netherlands" 00-19,200-499,5000-6999,70000-79999,800000-849999,8500-8999,90-90,94-94 91 agency="Sweden" 0-1,20-49,500-649,7000-7999,85000-94999,970000-999999 92 agency="International NGO Publishers and EC Organizations" 0-5,60-79,800-899,9000-9499,95000-98999,990000-999999 93 agency="India" 00-09,100-499,5000-7999,80000-94999,950000-999999 94 agency="Netherlands" 000-599,6000-8999,90000-99999 950 agency="Argentina" 00-49,500-899,9000-9899,99000-99999 951 agency="Finland" 0-1,20-54,550-889,8900-9499,95000-99999 952 agency="Finland" 00-19,200-499,5000-5999,60-65,6600-6699,67000-69999,7000-7999,80-94 9500-9899,99000-99999 953 agency="Croatia" 0-0,10-14,150-509,51-54,55000-59999,6000-9499,95000-99999 954 agency="Bulgaria" 00-28,2900-2999,300-799,8000-8999,90000-92999,9300-9999 955 agency="Sri Lanka" 0000-1999,20-40,41000-43999,44000-44999,4500-4999,50000-54999,550-799 8000-9499,95000-99999 956 agency="Chile" 00-19,200-699,7000-9999 957 agency="Taiwan" 00-02,0300-0499,05-19,2000-2099,21-27,28000-30999,31-43,440-819 8200-9699,97000-99999 958 agency="Colombia" 00-56,57000-59999,600-799,8000-9499,95000-99999 959 agency="Cuba" 00-19,200-699,7000-8499,85000-99999 960 agency="Greece" 00-19,200-659,6600-6899,690-699,7000-8499,85000-92999,93-93,9400-9799 98000-99999 961 agency="Slovenia" 00-19,200-599,6000-8999,90000-94999 962 agency="Hong Kong, China" 00-19,200-699,7000-8499,85000-86999,8700-8999,900-999 963 agency="Hungary" 00-19,200-699,7000-8499,85000-89999,9000-9999 964 agency="Iran" 00-14,150-249,2500-2999,300-549,5500-8999,90000-96999,970-989,9900-9999 965 agency="Israel" 00-19,200-599,7000-7999,90000-99999 966 agency="Ukraine" 00-12,130-139,14-14,1500-1699,170-199,2000-2789,279-289,2900-2999 300-699,7000-8999,90000-90999,910-949,95000-97999,980-999 967 agency="Malaysia" 00-00,0100-0999,10000-19999,300-499,5000-5999,60-89,900-989,9900-9989 99900-99999 968 agency="Mexico" 01-39,400-499,5000-7999,800-899,9000-9999 969 agency="Pakistan" 0-1,20-39,400-799,8000-9999 970 agency="Mexico" 01-59,600-899,9000-9099,91000-96999,9700-9999 971 agency="Philippines" 000-015,0160-0199,02-02,0300-0599,06-49,500-849,8500-9099,91000-95999 9600-9699,97-98,9900-9999 972 agency="Portugal" 0-1,20-54,550-799,8000-9499,95000-99999 973 agency="Romania" 0-0,100-169,1700-1999,20-54,550-759,7600-8499,85000-88999,8900-9499 95000-99999 974 agency="Thailand" 00-19,200-699,7000-8499,85000-89999,90000-94999,9500-9999 975 agency="Turkey" 00000-01999,02-24,250-599,6000-9199,92000-98999,990-999 976 agency="Caribbean Community" 0-3,40-59,600-799,8000-9499,95000-99999 977 agency="Egypt" 00-19,200-499,5000-6999,700-849,85000-89999,90-99 978 agency="Nigeria" 000-199,2000-2999,30000-79999,8000-8999,900-999 979 agency="Indonesia" 000-099,1000-1499,15000-19999,20-29,3000-3999,400-799,8000-9499 95000-99999 980 agency="Venezuela" 00-19,200-599,6000-9999 981 agency="Singapore" 00-11,17000-19999,200-289,290-299,3000-3099,310-399,4000-9999 982 agency="South Pacific" 00-09,100-699,70-89,9000-9799,98000-99999 983 agency="Malaysia" 00-01,020-199,2000-3999,40000-44999,45-49,50-79,800-899,9000-9899 99000-99999 984 agency="Bangladesh" 00-39,400-799,8000-8999,90000-99999 985 agency="Belarus" 00-39,400-599,6000-8999,90000-99999 986 agency="Taiwan" 00-11,120-559,5600-7999,80000-99999 987 agency="Argentina" 00-09,1000-1999,20000-29999,30-35,3600-3999,40-44,45000-49999,500-899 9000-9499,95000-99999 988 agency="Hong Kong, China" 00-11,12000-14999,15000-16999,17000-19999,200-799,8000-9699,97000-99999 989 agency="Portugal" 0-1,20-54,550-799,8000-9499,95000-99999 9927 agency="Qatar" 00-09,100-399,4000-4999 9928 agency="Albania" 00-09,100-399,4000-4999 9929 agency="Guatemala" 0-3,40-54,550-799,8000-9999 9930 agency="Costa Rica" 00-49,500-939,9400-9999 9931 agency="Algeria" 00-29,300-899,9000-9999 9932 agency="Lao People's Democratic Republic" 00-39,400-849,8500-9999 9933 agency="Syria" 0-0,10-39,400-899,9000-9999 9934 agency="Latvia" 0-0,10-49,500-799,8000-9999 9935 agency="Iceland" 0-0,10-39,400-899,9000-9999 9936 agency="Afghanistan" 0-1,20-39,400-799,8000-9999 9937 agency="Nepal" 0-2,30-49,500-799,8000-9999 9938 agency="Tunisia" 00-79,800-949,9500-9999 9939 agency="Armenia" 0-4,50-79,800-899,9000-9999 9940 agency="Montenegro" 0-1,20-49,500-899,9000-9999 9941 agency="Georgia" 0-0,10-39,400-899,9000-9999 9942 agency="Ecuador" 00-84,8500-8999,900-984,9850-9999 9943 agency="Uzbekistan" 00-29,300-399,4000-9999 9944 agency="Turkey" 0000-0999,100-499,5000-5999,60-69,700-799,80-89,900-999 9945 agency="Dominican Republic" 00-00,010-079,08-39,400-569,57-57,580-849,8500-9999 9946 agency="Korea, P.D.R." 0-1,20-39,400-899,9000-9999 9947 agency="Algeria" 0-1,20-79,800-999 9948 agency="United Arab Emirates" 00-39,400-849,8500-9999 9949 agency="Estonia" 0-0,10-39,400-899,9000-9999 9950 agency="Palestine" 00-29,300-849,8500-9999 9951 agency="Kosova" 00-39,400-849,8500-9999 9952 agency="Azerbaijan" 0-1,20-39,400-799,8000-9999 9953 agency="Lebanon" 0-0,10-39,400-599,60-89,9000-9999 9954 agency="Morocco" 0-1,20-39,400-799,8000-9999 9955 agency="Lithuania" 00-39,400-929,9300-9999 9956 agency="Cameroon" 0-0,10-39,400-899,9000-9999 9957 agency="Jordan" 00-39,400-699,70-84,8500-8799,88-99 9958 agency="Bosnia and Herzegovina" 00-03,040-089,0900-0999,10-18,1900-1999,20-49,500-899,9000-9999 9959 agency="Libya" 0-1,20-79,800-949,9500-9699,970-979,98-99 9960 agency="Saudi Arabia" 00-59,600-899,9000-9999 9961 agency="Algeria" 0-2,30-69,700-949,9500-9999 9962 agency="Panama" 00-54,5500-5599,56-59,600-849,8500-9999 9963 agency="Cyprus" 0-1,2000-2499,250-279,2800-2999,30-54,550-734,7350-7499,7500-9999 9964 agency="Ghana" 0-6,70-94,950-999 9965 agency="Kazakhstan" 00-39,400-899,9000-9999 9966 agency="Kenya" 000-149,1500-1999,20-69,7000-7499,750-959,9600-9999 9967 agency="Kyrgyz Republic" 00-39,400-899,9000-9999 9968 agency="Costa Rica" 00-49,500-939,9400-9999 9970 agency="Uganda" 00-39,400-899,9000-9999 9971 agency="Singapore" 0-5,60-89,900-989,9900-9999 9972 agency="Peru" 00-09,1-1,200-249,2500-2999,30-59,600-899,9000-9999 9973 agency="Tunisia" 00-05,060-089,0900-0999,10-69,700-969,9700-9999 9974 agency="Uruguay" 0-2,30-54,550-749,7500-9499,95-99 9975 agency="Moldova" 0-0,100-399,4000-4499,45-89,900-949,9500-9999 9976 agency="Tanzania" 0-5,60-89,900-989,9900-9999 9977 agency="Costa Rica" 00-89,900-989,9900-9999 9978 agency="Ecuador" 00-29,300-399,40-94,950-989,9900-9999 9979 agency="Iceland" 0-4,50-64,650-659,66-75,760-899,9000-9999 9980 agency="Papua New Guinea" 0-3,40-89,900-989,9900-9999 9981 agency="Morocco" 00-09,100-159,1600-1999,20-79,800-949,9500-9999 9982 agency="Zambia" 00-79,800-989,9900-9999 9983 agency="Gambia" 80-94,950-989,9900-9999 9984 agency="Latvia" 00-49,500-899,9000-9999 9985 agency="Estonia" 0-4,50-79,800-899,9000-9999 9986 agency="Lithuania" 00-39,400-899,9000-9399,940-969,97-99 9987 agency="Tanzania" 00-39,400-879,8800-9999 9988 agency="Ghana" 0-2,30-54,550-749,7500-9999 9989 agency="Macedonia" 0-0,100-199,2000-2999,30-59,600-949,9500-9999 99901 agency="Bahrain" 00-49,500-799,80-99 99902 agency="Gabon (reserved)" 99903 agency="Mauritius" 0-1,20-89,900-999 99904 agency="Netherlands Antilles and Aruba" 0-5,60-89,900-999 99905 agency="Bolivia" 0-3,40-79,800-999 99906 agency="Kuwait" 0-2,30-59,600-699,70-89,90-94,950-999 99908 agency="Malawi" 0-0,10-89,900-999 99909 agency="Malta" 0-3,40-94,950-999 99910 agency="Sierra Leone" 0-2,30-89,900-999 99911 agency="Lesotho" 00-59,600-999 99912 agency="Botswana" 0-3,400-599,60-89,900-999 99913 agency="Andorra" 0-2,30-35,600-604 99914 agency="Suriname" 0-4,50-89,900-999 99915 agency="Maldives" 0-4,50-79,800-999 99916 agency="Namibia" 0-2,30-69,700-999 99917 agency="Brunei Darussalam" 0-2,30-89,900-999 99918 agency="Faroe Islands" 0-3,40-79,800-999 99919 agency="Benin" 0-2,300-399,40-69,70-79,800-849,850-899,900-999 99920 agency="Andorra" 0-4,50-89,900-999 99921 agency="Qatar" 0-1,20-69,700-799,8-8,90-99 99922 agency="Guatemala" 0-3,40-69,700-999 99923 agency="El Salvador" 0-1,20-79,800-999 99924 agency="Nicaragua" 0-1,20-79,800-999 99925 agency="Paraguay" 0-3,40-79,800-999 99926 agency="Honduras" 0-0,10-59,600-899,90-99 99927 agency="Albania" 0-2,30-59,600-999 99928 agency="Georgia" 0-0,10-79,800-999 99929 agency="Mongolia" 0-4,50-79,800-999 99930 agency="Armenia" 0-4,50-79,800-999 99931 agency="Seychelles" 0-4,50-79,800-999 99932 agency="Malta" 0-0,10-59,600-699,7-7,80-99 99933 agency="Nepal" 0-2,30-59,600-999 99934 agency="Dominican Republic" 0-1,20-79,800-999 99935 agency="Haiti" 0-2,30-59,600-699,7-8,90-99 99936 agency="Bhutan" 0-0,10-59,600-999 99937 agency="Macau" 0-1,20-59,600-999 99938 agency="Srpska, Republic of" 0-1,20-59,600-899,90-99 99939 agency="Guatemala" 0-5,60-89,900-999 99940 agency="Georgia" 0-0,10-69,700-999 99941 agency="Armenia" 0-2,30-79,800-999 99942 agency="Sudan" 0-4,50-79,800-999 99943 agency="Albania" 0-2,30-59,600-999 99944 agency="Ethiopia" 0-4,50-79,800-999 99945 agency="Namibia" 0-5,60-89,900-999 99946 agency="Nepal" 0-2,30-59,600-999 99947 agency="Tajikistan" 0-2,30-69,700-999 99948 agency="Eritrea" 0-4,50-79,800-999 99949 agency="Mauritius" 0-1,20-89,900-999 99950 agency="Cambodia" 0-4,50-79,800-999 99951 agency="Congo, The Democratic Republic" 99952 agency="Mali" 0-4,50-79,800-999 99953 agency="Paraguay" 0-2,30-79,800-939,94-99 99954 agency="Bolivia" 0-2,30-69,700-879,88-99 99955 agency="Srpska, Republic of" 0-1,20-59,600-799,80-99 99956 agency="Albania" 00-59,600-859,86-99 99957 agency="Malta" 0-1,20-79,800-999 99958 agency="Bahrain" 0-4,50-94,950-999 99959 agency="Luxembourg" 0-2,30-59,600-999 99960 agency="Malawi" 0-0,10-94,950-999 99961 agency="El Salvador" 0-3,40-89,900-999 99962 agency="Mongolia" 0-4,50-79,800-999 99963 agency="Cambodia" 00-49,500-999 99964 agency="Nicaragua" 0-1,20-79,800-999 99965 agency="Macau" 0-3,40-69,700-999 99966 agency="Kuwait" 0-2,30-69,700-799 99967 agency="Paraguay" 0-1,20-59,600-899 99968 agency="Botswana" 0-3,400-599,60-89,900-999 99969 agency="Oman" 0-4,50-79,800-999 99970 agency="Haiti" 0-4,50-89,900-999 99971 agency="Myanmar" 0-5,60-84,850-999 99972 agency="Faroe Islands" 0-4,50-89,900-999 99973 agency="Mongolia" 0-3,40-79,800-999 99974 agency="Bolivia" 40-79,800-999 99975 agency="Tajikistan" 0-3,40-79,800-999 979 10-11 10 agency="France" 00-19,200-699,7000-8999,90000-97599,976000-999999 11 agency="Korea, Republic" 00-24,250-549,5500-8499,85000-94999,950000-999999 python-stdnum-0.9/stdnum/verhoeff.py0000644000000000000000000000611712154624371017653 0ustar rootroot00000000000000# verhoeff.py - functions for performing the Verhoeff checksum # # Copyright (C) 2010, 2011, 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """The Verhoeff algorithm. The Verhoeff algorithm uses two tables for permutations and multiplications to calculate a checksum. >>> validate('1234') Traceback (most recent call last): ... InvalidChecksum: ... >>> checksum('1234') 1 >>> calc_check_digit('1234') '0' >>> validate('12340') '12340' """ from stdnum.exceptions import * # These are the multiplication and permutation tables used in the # Verhoeff algorithm. _multiplication_table = ( [0, 1, 2, 3, 4, 5, 6, 7, 8, 9], [1, 2, 3, 4, 0, 6, 7, 8, 9, 5], [2, 3, 4, 0, 1, 7, 8, 9, 5, 6], [3, 4, 0, 1, 2, 8, 9, 5, 6, 7], [4, 0, 1, 2, 3, 9, 5, 6, 7, 8], [5, 9, 8, 7, 6, 0, 4, 3, 2, 1], [6, 5, 9, 8, 7, 1, 0, 4, 3, 2], [7, 6, 5, 9, 8, 2, 1, 0, 4, 3], [8, 7, 6, 5, 9, 3, 2, 1, 0, 4], [9, 8, 7, 6, 5, 4, 3, 2, 1, 0]) _permutation_table = ( (0, 1, 2, 3, 4, 5, 6, 7, 8, 9), (1, 5, 7, 6, 2, 8, 3, 0, 9, 4), (5, 8, 0, 3, 7, 9, 6, 1, 4, 2), (8, 9, 1, 6, 0, 4, 3, 5, 2, 7), (9, 4, 5, 3, 1, 2, 6, 8, 7, 0), (4, 2, 8, 6, 5, 7, 3, 9, 0, 1), (2, 7, 9, 3, 8, 0, 6, 4, 1, 5), (7, 0, 4, 6, 9, 1, 3, 2, 5, 8)) def checksum(number): """Calculate the Verhoeff checksum over the provided number. The checksum is returned as an int. Valid numbers should have a checksum of 0.""" # transform number list number = tuple(int(n) for n in reversed(str(number))) # calculate checksum check = 0 for i, n in enumerate(number): check = _multiplication_table[check][_permutation_table[i % 8][n]] return check def validate(number): """Checks to see if the number provided passes the Verhoeff checksum.""" if not bool(number): raise InvalidFormat() try: valid = checksum(number) == 0 except: raise InvalidFormat() if not valid: raise InvalidChecksum() return number def is_valid(number): """Checks to see if the number provided passes the Verhoeff checksum.""" try: return bool(validate(number)) except ValidationError: return False def calc_check_digit(number): """With the provided number, calculate the extra digit that should be appended to make it pass the Verhoeff checksum.""" return str(_multiplication_table[checksum(str(number) + '0')].index(0)) python-stdnum-0.9/stdnum/cy/0000755000000000000000000000000012260536561016104 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/cy/__init__.py0000644000000000000000000000154411720140730020206 0ustar rootroot00000000000000# __init__.py - collection of Cypriot numbers # coding: utf-8 # # Copyright (C) 2012 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of Cypriot numbers.""" python-stdnum-0.9/stdnum/cy/vat.py0000644000000000000000000000527212154624370017254 0ustar rootroot00000000000000# vat.py - functions for handling Cypriot VAT numbers # coding: utf-8 # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Αριθμός Εγγραφής Φ.Π.Α. (Cypriot VAT number). The Cypriot Αριθμός Εγγραφής Φ.Π.Α. (VAT) number consists of 9 digits where the last one is a is a letter and functions as a check digit. >>> compact('CY-10259033P') '10259033P' >>> validate('CY-10259033P ') '10259033P' >>> validate('CY-10259033Z') # invalid check digit Traceback (most recent call last): ... InvalidChecksum: ... """ from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, ' -').upper().strip() if number.startswith('CY'): number = number[2:] return number def calc_check_digit(number): """Calculate the check digit. The number passed should not have the check digit included.""" translation = { '0': 1, '1': 0, '2': 5, '3': 7, '4': 9, '5': 13, '6': 15, '7': 17, '8': 19, '9': 21, } return 'ABCDEFGHIJKLMNOPQRSTUVWXYZ'[( sum(translation[x] for x in number[::2]) + sum(int(x) for x in number[1::2]) ) % 26] def validate(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" number = compact(number) if not number[:-1].isdigit(): raise InvalidFormat() if len(number) != 9: raise InvalidLength() if number[0:2] == '12': raise InvalidComponent() if number[-1] != calc_check_digit(number[:-1]): raise InvalidChecksum() return number def is_valid(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/hu/0000755000000000000000000000000012260536561016105 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/hu/__init__.py0000644000000000000000000000164511720140726020216 0ustar rootroot00000000000000# __init__.py - collection of Hungarian numbers # coding: utf-8 # # Copyright (C) 2012 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of Hungarian numbers.""" # provide vat as an alias from stdnum.hu import anum as vat python-stdnum-0.9/stdnum/hu/anum.py0000644000000000000000000000453612154624370017425 0ustar rootroot00000000000000# anum.py - functions for handling Hungarian VAT numbers # coding: utf-8 # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """ANUM (Közösségi adószám, Hungarian VAT number). The ANUM is the Hungarian VAT (Közösségi adószám) number. It is an 8-digit taxpayer registration number that includes a weighted checksum. >>> validate('HU-12892312') '12892312' >>> validate('HU-12892313') # invalid check digit Traceback (most recent call last): ... InvalidChecksum: ... """ from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, ' -').upper().strip() if number.startswith('HU'): number = number[2:] return number def checksum(number): """Calculate the checksum. Valid numbers should have a checksum of 0.""" weights = (9, 7, 3, 1, 9, 7, 3, 1) return sum(weights[i] * int(n) for i, n in enumerate(number)) % 10 def validate(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" number = compact(number) if not number.isdigit(): raise InvalidFormat() if len(number) != 8: raise InvalidLength() if checksum(number) != 0: raise InvalidChecksum() return number def is_valid(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/ie/0000755000000000000000000000000012260536561016066 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/ie/pps.py0000644000000000000000000000441312154624370017242 0ustar rootroot00000000000000# pps.py - functions for handling Irish PPS numbers # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """PPS No (Personal Public Service Number, Irish personal number). The Personal Public Service number consists of 8 digits. The first seven are numeric and the last is the check character. The number is sometimes be followed by an extra letter that can be a 'W', 'T' or an 'X' and is ignored for the check algorithm. >>> validate('6433435F') '6433435F' >>> validate('6433435E') # incorrect check digit Traceback (most recent call last): ... InvalidChecksum: ... """ import re from stdnum.exceptions import * from stdnum.ie import vat from stdnum.util import clean pps_re = re.compile('^\d{7}[A-W][WTX]?$') """Regular expression used to check syntax of PPS numbers.""" def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" return clean(number, ' -').upper().strip() def validate(number): """Checks to see if the number provided is a valid PPS number. This checks the length, formatting and check digit.""" number = compact(number) if not pps_re.match(number): raise InvalidFormat() if number[7] != vat.calc_check_digit(number[:7]): raise InvalidChecksum() return number def is_valid(number): """Checks to see if the number provided is a valid PPS number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/ie/__init__.py0000644000000000000000000000154011720140727020172 0ustar rootroot00000000000000# __init__.py - collection of Irish numbers # coding: utf-8 # # Copyright (C) 2012 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of Irish numbers.""" python-stdnum-0.9/stdnum/ie/vat.py0000644000000000000000000000555212154624370017237 0ustar rootroot00000000000000# vat.py - functions for handling Irish VAT numbers # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """VAT (Irish VAT number). The Irish VAT number consists of 8 digits. The last digit is a check letter, the second digit may be a number, a letter, "+" or "*". >>> validate('IE 6433435F') '6433435F' >>> validate('6433435E') # incorrect check digit Traceback (most recent call last): ... InvalidChecksum: ... >>> validate('8D79739I') # old style number '8D79739I' >>> validate('8?79739J') # incorrect old style Traceback (most recent call last): ... InvalidFormat: ... """ from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, ' -').upper().strip() if number.startswith('IE'): number = number[2:] return number def calc_check_digit(number): """Calculate the check digit. The number passed should not have the check digit included.""" alphabet = 'WABCDEFGHIJKLMNOPQRSTUV' number = (7 - len(number)) * '0' + number return alphabet[sum((8 - i) * int(n) for i, n in enumerate(number)) % 23] def validate(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" number = compact(number) if not number[:1].isdigit() or not number[2:7].isdigit(): raise InvalidFormat() if len(number) != 8: raise InvalidLength() if number[:7].isdigit(): # new system if number[-1] != calc_check_digit(number[:-1]): raise InvalidChecksum() elif number[1] in 'ABCDEFGHIJKLMNOPQRSTUVWXYZ+*': # old system if number[-1] != calc_check_digit(number[2:-1] + number[0]): raise InvalidChecksum() else: raise InvalidFormat() return number def is_valid(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/lv/0000755000000000000000000000000012260536561016112 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/lv/__init__.py0000644000000000000000000000164011720140726020216 0ustar rootroot00000000000000# __init__.py - collection of Latvian numbers # coding: utf-8 # # Copyright (C) 2012 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of Latvian numbers.""" # provide vat as an alias from stdnum.lv import pvn as vat python-stdnum-0.9/stdnum/lv/pvn.py0000644000000000000000000000756012154624371017276 0ustar rootroot00000000000000# pvn.py - functions for handling Latvian PVN (VAT) numbers # coding: utf-8 # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """PVN (Pievienotās vērtības nodokļa, Latvian VAT number). The PVN is a 11-digit number that can either be a reference to a legal entity (in which case the first digit > 3) or a natural person (in which case it should be the same as the personal code (personas kods)). Personal codes start with 6 digits to denote the birth date in the form ddmmyy. >>> validate('LV 4000 3521 600') '40003521600' >>> validate('40003521601') # invalid check digit Traceback (most recent call last): ... InvalidChecksum: ... >>> validate('161175-19997') # personal code '16117519997' >>> validate('161375-19997') # invalid date Traceback (most recent call last): ... InvalidComponent: ... """ import datetime from stdnum.exceptions import * from stdnum.util import clean # validation functions are available on-line but it is not allowed # to perform automated queries: # http://www6.vid.gov.lv/VID_PDB?aspxerrorpath=/vid_pdb/pvn.asp def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, ' -').upper().strip() if number.startswith('LV'): number = number[2:] return number def checksum(number): """Calculate the checksum for legal entities.""" weights = (9, 1, 4, 8, 3, 10, 2, 5, 7, 6, 1) return sum(weights[i] * int(n) for i, n in enumerate(number)) % 11 def calc_check_digit_pers(number): """Calculate the check digit for personal codes. The number passed should not have the check digit included.""" # note that this algorithm has not been confirmed by an independent source weights = (10, 5, 8, 4, 2, 1, 6, 3, 7, 9) check = 1 + sum(weights[i] * int(n) for i, n in enumerate(number)) return str(check % 11 % 10) def get_birth_date(number): """Split the date parts from the number and return the birth date.""" day = int(number[0:2]) month = int(number[2:4]) year = int(number[4:6]) year += 1800 + int(number[6]) * 100 try: return datetime.date(year, month, day) except ValueError: raise InvalidComponent() def validate(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" number = compact(number) if not number.isdigit(): raise InvalidFormat() if len(number) != 11: raise InvalidLength() if number[0] > '3': # legal entity if checksum(number) != 3: raise InvalidChecksum() else: # natural resident, check if birth date is valid birth_date = get_birth_date(number) # TODO: check that the birth date is not in the future if calc_check_digit_pers(number[:-1]) != number[-1]: raise InvalidChecksum() return number def is_valid(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/be/0000755000000000000000000000000012260536561016057 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/be/__init__.py0000644000000000000000000000154411720140724020164 0ustar rootroot00000000000000# __init__.py - collection of Belgian numbers # coding: utf-8 # # Copyright (C) 2012 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of Belgian numbers.""" python-stdnum-0.9/stdnum/be/vat.py0000644000000000000000000000443412154624370017226 0ustar rootroot00000000000000# vat.py - functions for handling Belgian VAT numbers # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """BTW, TVA, NWSt (Belgian VAT number). >>> compact('BE403019261') '0403019261' >>> compact('(0)403019261') '0403019261' >>> validate('BE 428759497') '0428759497' >>> validate('BE431150351') Traceback (most recent call last): ... InvalidChecksum: ... """ from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, ' -./').upper().strip() if number.startswith('BE'): number = number[2:] if number.startswith('(0)'): number = '0' + number[3:] if len(number) == 9: number = '0' + number # old format had 9 digits return number def checksum(number): """Calculate the checksum.""" return (int(number[:-2]) + int(number[-2:])) % 97 def validate(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" number = compact(number) if not number.isdigit(): raise InvalidFormat() if len(number) != 10: raise InvalidLength() if checksum(number) != 0: raise InvalidChecksum() return number def is_valid(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/hr/0000755000000000000000000000000012260536561016102 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/hr/__init__.py0000644000000000000000000000154611721244726020221 0ustar rootroot00000000000000# __init__.py - collection of Croatian numbers # coding: utf-8 # # Copyright (C) 2012 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of Croatian numbers.""" python-stdnum-0.9/stdnum/hr/oib.py0000644000000000000000000000436612154624370017234 0ustar rootroot00000000000000# cnp.py - functions for handling Croatian OIB numbers # coding: utf-8 # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """OIB (Osobni identifikacijski broj, Croatian identification number). The personal identification number is used to identify persons and legal entities in Croatia. It has 11 digits (sometimes prefixed by HR), contains no personal information and uses the ISO 7064 Mod 11, 10 checksum algorithm. >>> validate('HR 33392005961') '33392005961' >>> validate('33392005962') # invalid check digit Traceback (most recent call last): ... InvalidChecksum: ... """ from stdnum.exceptions import * from stdnum.iso7064 import mod_11_10 from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, ' -').upper().strip() if number.startswith('HR'): number = number[2:] return number def validate(number): """Checks to see if the number provided is a valid OIB number. This checks the length, formatting and check digit.""" number = compact(number) if not number.isdigit(): raise InvalidFormat() if len(number) != 11: raise InvalidLength() mod_11_10.validate(number) return number def is_valid(number): """Checks to see if the number provided is a valid OIB number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/isil.dat0000644000000000000000000000731512260517277017134 0ustar rootroot00000000000000# generated from ISIL Registration Authority, downloaded from # http://biblstandard.dk/isil/ AR$ country="Argentine Republic" ra_url="http://www.iram.org.ar" ra="Argentine Standardization and Certification Institute (IRAM)" AT$ country="Austria" ra_url="http://www.obvsg.at" ra="Die Österreichische Bibliothekenverbund und Service GmbH" AU$ country="Australia" ra_url="http://www.nla.gov.au/ilrs" ra="National Library of Australia" BE$ country="Belgium" ra_url="http://www.kbr.be" ra="Royal Library of Belgium" BY$ country="Belarus" ra_url="http://www.nlb.by/portal/page/portal/index?lang=en" ra="National Library of Belarus" CA$ country="Canada" ra_url="http://www.collectionscanada.ca/ill/s16-206-e.html#3.2.2" ra="Library and Archives Canada" CH$ country="Switzerland" ra_url="http://www.nb.admin.ch/slb/slb_professionnel/01540/index.html?lang=en" ra="Swiss National Library" CY$ country="Cyprus" ra_url="http://www.cut.ac.cy/library/english/isil_reg_agent.htm" ra="Cyprus University of Technology Library" DE$ country="Germany" ra_url="http://sigel.staatsbibliothek-berlin.de/" ra="Staatsbibliothek zu Berlin" DK$ country="Denmark" ra_url="http://www.bibliotekogmedier.dk/engelsk/library/national-solutions/standards/danish-library-number/" ra="Danish Agency for Culture" EG$ country="Egypt" ra_url="http://www.sti.sci.eg/focal_point.htm" ra="Egyptian National Scientific and Technical Information Network (ENSTINET)" FI$ country="Finland" ra_url="http://www.lib.helsinki.fi/english/libraries/standards/ISIL.htm" ra="The National Library of Finland" FR$ country="France" ra_url="http://www.abes.fr" ra="Agence Bibliographique de l'Enseignement Superieur" GB$ country="United Kingdom" ra_url="http://www.bl.uk/bibliographic/isilagency.html" ra="British Library" GL$ country="Greenland" ra_url="http://www.katak.gl/ISIL/Greenlandic_library_identifiers.html" ra="Central and Public Library of Greenland" IL$ country="Israel" ra_url="http://nli.org.il/eng" ra="National Library of Israel" IR$ country="Islamic Republic of Iran" ra_url="http://www.nlai.ir/special_services/stds/isil.htm" ra="National Library and Archives of Islamic Republic of Iran of Iran" IT$ country="Italy" ra_url="http://www.iccu.sbn.it/genera.jsp?id=78&l=en" ra="Istituto Centrale per il Catalogo Unico delle biblioteche italiane e per le informazioni bibliografiche" JP$ country="Japan" ra_url="http://www.ndl.go.jp/en/library/isil/index.html" ra="National Diet Library" KR$ country="Republic of Korea" ra_url="http://www.nl.go.kr/isil/" ra="The National Library of Korea" LU$ country="Luxembourg" ra_url="http://www.anlux.lu" ra="Archives nationales de Luxembourg" NL$ country="The Netherlands" ra_url="http://www.kb.nl/expertise/voor-bibliotheken/interbibliotheciar-leenverkeer/internationale-standard-identifier-for-libraries-isil" ra="Koninklijke Bibliotheek, National Library of the Netherlands" NO$ country="Norway" ra_url="http://www.nb.no/html/tildeling_av_nasjonalt_bibliot.html" ra="National Library of Norway" NZ$ country="New Zealand" ra_url="http://www.natlib.govt.nz/en/services/6docsupply.html#sect1" ra="National Library of New Zealand Te Puna Mātauranga o Aotearoa" RU$ country="Russian Federation" ra_url="http://english.gpntb.ru/" ra="Russian National Public Library for Science and Technology" SI$ country="The Republic of Slovenia" ra_url="http://www.nuk.uni-lj.si/nukeng3.asp?id=311364382" ra="National and University Library" US$ country="United States of America" ra="Library of Congress - under registration" M$ country="Library of Congress - outside US" ra="Library of Congress - under registration" O$ ra="See OCLC" OCLC$ country="WorldCat Symbol" ra_url="http://www.oclc.org" ra="OCLC" ZDB$ country="Staatsbibliothek zu Berlin - Zeitschriftendatenbank" ra="Staatsbibliothek zu Berlin" python-stdnum-0.9/stdnum/meid.py0000644000000000000000000001470712260533040016757 0ustar rootroot00000000000000# meid.py - functions for handling Mobile Equipment Identifiers (MEIDs) # # Copyright (C) 2010, 2011, 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """MEID (Mobile Equipment Identifier). The Mobile Equipment Identifier is used to identify a physical piece of CDMA mobile station equipment. >>> validate('AF 01 23 45 0A BC DE C') 'AF0123450ABCDE' >>> validate('29360 87365 0070 3710 0') 'AF0123450ABCDE' >>> validate('29360 87365 0070 3710 1') Traceback (most recent call last): ... InvalidChecksum: ... >>> format('af0123450abcDEC', add_check_digit=True) 'AF 01 23 45 0A BC DE C' >>> format('af0123450abcDEC', format='dec', add_check_digit=True) '29360 87365 0070 3710 0' """ from stdnum.exceptions import * from stdnum.util import clean _hex_alphabet = '0123456789ABCDEF' def _cleanup(number): """Remove any grouping information from the number and removes surrounding whitespace.""" return clean(str(number), ' -').strip().upper() def _ishex(number): for x in number: if x not in _hex_alphabet: return False return True def _parse(number): number = _cleanup(number) if len(number) in (14, 15): # 14 or 15 digit hex representation if not _ishex(number): raise InvalidFormat() return number[0:14], number[14:] elif len(number) in (18, 19): # 18-digit decimal representation if not number.isdigit(): raise InvalidFormat() return number[0:18], number[18:] else: raise InvalidLength() def calc_check_digit(number): """Calculate the check digit for the number. The number should not already have a check digit.""" # both the 18-digit decimal format and the 14-digit hex format # containing only decimal digits should use the decimal Luhn check from stdnum import luhn if number.isdigit(): return luhn.calc_check_digit(number) else: return luhn.calc_check_digit(number, alphabet=_hex_alphabet) def compact(number, strip_check_digit=True): """Convert the MEID number to the minimal (hexadecimal) representation. This strips grouping information, removes surrounding whitespace and converts to hexadecimal if needed. If the check digit is to be preserved and conversion is done a new check digit is recalculated.""" # first parse the number number, cd = _parse(number) # strip check digit if needed if strip_check_digit: cd = '' # convert to hex if needed if len(number) == 18: number = '%08X%06X' % (int(number[0:10]), int(number[10:18])) if cd: cd = calc_check_digit(number) # put parts back together again return number + cd def validate(number, strip_check_digit=True): """Checks to see if the number provided is a valid MEID number. This converts the representation format of the number (if it is decimal it is not converted to hexadecimal).""" from stdnum import luhn # first parse the number number, cd = _parse(number) if len(number) == 18: # decimal format can be easily determined if cd: luhn.validate(number + cd) # convert to hex number = '%08X%06X' % (int(number[0:10]), int(number[10:18])) cd = calc_check_digit(number) elif number.isdigit(): # if the remaining hex format is fully decimal it is an IMEI number from stdnum import imei imei.validate(number + cd) else: # normal hex Luhn validation if cd: luhn.validate(number + cd, alphabet=_hex_alphabet) if strip_check_digit: cd = '' return number + cd def is_valid(number): """Checks to see if the number provided is a valid MEID number.""" try: return bool(validate(number)) except ValidationError: return False def format(number, separator=' ', format=None, add_check_digit=False): """Reformat the passed number to the standard format. The separator used can be provided. If the format is specified (either 'hex' or 'dec') the number is reformatted in that format, otherwise the current representation is kept. If add_check_digit is True a check digit will be added if it is not present yet.""" # first parse the number number, cd = _parse(number) # format conversions if needed if format == 'dec' and len(number) == 14: # convert to decimal number = '%010d%08d' % (int(number[0:8], 16), int(number[8:14], 16)) if cd: cd = calc_check_digit(number) elif format == 'hex' and len(number) == 18: # convert to hex number = '%08X%06X' % (int(number[0:10]), int(number[10:18])) if cd: cd = calc_check_digit(number) # see if we need to add a check digit if add_check_digit and not cd: cd = calc_check_digit(number) # split number according to format if len(number) == 14: number = [number[i * 2:i * 2 + 2] for i in range(7)] + [cd] else: number = (number[:5], number[5:10], number[10:14], number[14:], cd) return separator.join(x for x in number if x) def to_binary(number): """Convert the number to it's binary representation (without the check digit).""" import sys number = compact(number, strip_check_digit=True) if sys.version > '3': # pragma: no cover (Python 2/3 specific code) return bytes.fromhex(number) else: # pragma: no cover (Python 2/3 specific code) return number.decode('hex') def to_pseudo_esn(number): """Convert the provided MEID to a pseudo ESN (pESN). The ESN is returned in compact hexadecimal representation.""" import hashlib # return the last 6 digits of the SHA1 hash prefixed with the reserved # manufacturer code return '80' + hashlib.sha1(to_binary(number)).hexdigest()[-6:].upper() python-stdnum-0.9/stdnum/iban.py0000644000000000000000000000746012154624370016761 0ustar rootroot00000000000000# iban.py - functions for handling International Bank Account Numbers (IBANs) # # Copyright (C) 2011, 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """IBAN (International Bank Account Number). The IBAN is used to identify bank accounts across national borders. The first two letters are a country code. The next two digits are check digits for the ISO 7064 Mod 97, 10 checksum. Each country uses it's own format for the remainder of the number. Some countries may also use checksum algorithms within their number but this is currently not checked by this number. >>> validate('GR16 0110 1050 0000 1054 7023 795') 'GR1601101050000010547023795' >>> validate('BE31435411161155') 'BE31435411161155' >>> compact('GR16 0110 1050 0000 1054 7023 795') 'GR1601101050000010547023795' >>> format('GR1601101050000010547023795') 'GR16 0110 1050 0000 1054 7023 795' """ import re from stdnum import numdb from stdnum.exceptions import * from stdnum.iso7064 import mod_97_10 from stdnum.util import clean # our open copy of the IBAN database _ibandb = numdb.get('iban') # the valid characters we have _alphabet = '0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ' # regular expression to check IBAN structure _struct_re = re.compile('([1-9][0-9]*)!([nac])') def compact(number): """Convert the iban number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" return clean(number, ' -').strip().upper() def _to_base10(number): """Prepare the number to it's base10 representation (also moving the check digits to the end) so it can be checked with the ISO 7064 Mod 97, 10 algorithm.""" # TODO: find out whether this should be in the mod_97_10 module return ''.join(str(_alphabet.index(x)) for x in number[4:] + number[:4]) def _struct_to_re(structure): """Convert an IBAN structure to a refular expression that can be used to validate the number.""" def conv(match): chars = { 'n': '[0-9]', 'a': '[A-Z]', 'c': '[A-Za-z0-9]', }[match.group(2)] return '%s{%s}' % (chars, match.group(1)) return re.compile('^%s$' % _struct_re.sub(conv, structure)) def validate(number): """Checks to see if the number provided is a valid IBAN.""" number = compact(number) try: test_number = _to_base10(number) except: raise InvalidFormat() # ensure that checksum is valid mod_97_10.validate(test_number) # look up the number info = _ibandb.info(number) # check if the bban part of number has the correct structure bban = number[4:] if not _struct_to_re(info[0][1].get('bban', '')).match(bban): raise InvalidFormat() # return the compact representation return number def is_valid(number): """Checks to see if the number provided is a valid IBAN.""" try: return bool(validate(number)) except ValidationError: return False def format(number, separator=' '): """Reformat the passed number to the space-separated format.""" number = compact(number) return separator.join(number[i:i + 4] for i in range(0, len(number), 4)) python-stdnum-0.9/stdnum/imei.py0000644000000000000000000000657512154624370017001 0ustar rootroot00000000000000# imei.py - functions for handling International Mobile Equipment Identity # (IMEI) numbers # # Copyright (C) 2010, 2011, 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """IMEI (International Mobile Equipment Identity). The IMEI is used to identify mobile phones. The IMEI may optionally include a check digit which is validated using the Luhn algorithm. >>> validate('35686800-004141-20') '3568680000414120' >>> validate('35-417803-685978-1') Traceback (most recent call last): ... InvalidChecksum: ... >>> compact('35686800-004141-20') '3568680000414120' >>> format('354178036859789') '35-417803-685978-9' >>> format('35686800-004141', add_check_digit=True) '35-686800-004141-8' >>> imei_type('35686800-004141-20') 'IMEISV' >>> split('35686800-004141') ('35686800', '004141', '') """ from stdnum import luhn from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the IMEI number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" return clean(number, ' -').strip().upper() def validate(number): """Checks to see if the number provided is a valid IMEI (or IMEISV) number.""" number = compact(number) if not number.isdigit(): raise InvalidFormat() if len(number) == 15: # only 15 digit IMEI has check digit luhn.validate(number) elif len(number) not in (14, 16): # neither IMEI without check digit or IMEISV (which doesn't have one) raise InvalidLength() return number def imei_type(number): """Check the passed number and returns 'IMEI', 'IMEISV' or None (for invalid) for checking the type of number passed.""" try: number = validate(number) except: return None if len(number) in (14, 15): return 'IMEI' elif len(number) == 16: return 'IMEISV' def is_valid(number): """Checks to see if the number provided is a valid IMEI (or IMEISV) number.""" try: return bool(validate(number)) except ValidationError: return False def split(number): """Split the number into a Type Allocation Code (TAC), serial number and either the checksum (for IMEI) or the software version number (for IMEISV).""" number = compact(number) return (number[:8], number[8:14], number[14:]) def format(number, separator='-', add_check_digit=False): """Reformat the passed number to the standard format.""" number = compact(number) if len(number) == 14 and add_check_digit: number += luhn.calc_check_digit(number) number = (number[:2], number[2:8], number[8:14], number[14:]) return separator.join(x for x in number if x) python-stdnum-0.9/stdnum/my/0000755000000000000000000000000012260536561016116 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/my/bp.dat0000644000000000000000000001411012260517306017202 0ustar rootroot00000000000000# generated from National Registration Department of Malaysia, downloaded from # http://www.jpn.gov.my/en/informasi/states-code # http://www.jpn.gov.my/en/informasi/country-code 01 state="Johor" country="Malaysia" countries="Malaysia" 02 state="Kedah" country="Malaysia" countries="Malaysia" 03 state="Kelantan" country="Malaysia" countries="Malaysia" 04 state="Melaka" country="Malaysia" countries="Malaysia" 05 state="Negeri Sembilan" country="Malaysia" countries="Malaysia" 06 state="Pahang" country="Malaysia" countries="Malaysia" 07 state="Pulau Pinang" country="Malaysia" countries="Malaysia" 08 state="Perak" country="Malaysia" countries="Malaysia" 09 state="Perlis" country="Malaysia" countries="Malaysia" 10 state="Selangor" country="Malaysia" countries="Malaysia" 11 state="Terengganu" country="Malaysia" countries="Malaysia" 12 state="Sabah" country="Malaysia" countries="Malaysia" 13 state="Sarawak" country="Malaysia" countries="Malaysia" 14 state="Wilayah Persekutuan (Kuala Lumpur)" country="Malaysia" countries="Malaysia" 15 state="Wilayah Persekutuan (Labuan)" country="Malaysia" countries="Malaysia" 16 state="Wilayah Persekutuan (Putrajaya)" country="Malaysia" countries="Malaysia" 21 state="Johor" country="Malaysia" countries="Malaysia" 22 state="Johor" country="Malaysia" countries="Malaysia" 23 state="Johor" country="Malaysia" countries="Malaysia" 24 state="Johor" country="Malaysia" countries="Malaysia" 25 state="Kedah" country="Malaysia" countries="Malaysia" 26 state="Kedah" country="Malaysia" countries="Malaysia" 27 state="Kedah" country="Malaysia" countries="Malaysia" 28 state="Kelantan" country="Malaysia" countries="Malaysia" 29 state="Kelantan" country="Malaysia" countries="Malaysia" 30 state="Melaka" country="Malaysia" countries="Malaysia" 31 state="Negeri Sembilan" country="Malaysia" countries="Malaysia" 32 state="Pahang" country="Malaysia" countries="Malaysia" 33 state="Pahang" country="Malaysia" countries="Malaysia" 34 state="Pulau Pinang" country="Malaysia" countries="Malaysia" 35 state="Pulau Pinang" country="Malaysia" countries="Malaysia" 36 state="Perak" country="Malaysia" countries="Malaysia" 37 state="Perak" country="Malaysia" countries="Malaysia" 38 state="Perak" country="Malaysia" countries="Malaysia" 39 state="Perak" country="Malaysia" countries="Malaysia" 40 state="Perlis" country="Malaysia" countries="Malaysia" 41 state="Selangor" country="Malaysia" countries="Malaysia" 42 state="Selangor" country="Malaysia" countries="Malaysia" 43 state="Selangor" country="Malaysia" countries="Malaysia" 44 state="Selangor" country="Malaysia" countries="Malaysia" 45 state="Terengganu" country="Malaysia" countries="Malaysia" 46 state="Terengganu" country="Malaysia" countries="Malaysia" 47 state="Sabah" country="Malaysia" countries="Malaysia" 48 state="Sabah" country="Malaysia" countries="Malaysia" 49 state="Sabah" country="Malaysia" countries="Malaysia" 50 state="Sarawak" country="Malaysia" countries="Malaysia" 51 state="Sarawak" country="Malaysia" countries="Malaysia" 52 state="Sarawak" country="Malaysia" countries="Malaysia" 53 state="Sarawak" country="Malaysia" countries="Malaysia" 54 state="Wilayah Persekutuan (Kuala Lumpur)" country="Malaysia" countries="Malaysia" 55 state="Wilayah Persekutuan (Kuala Lumpur)" country="Malaysia" countries="Malaysia" 56 state="Wilayah Persekutuan (Kuala Lumpur)" country="Malaysia" countries="Malaysia" 57 state="Wilayah Persekutuan (Kuala Lumpur)" country="Malaysia" countries="Malaysia" 58 state="Wilayah Persekutuan (Labuan)" country="Malaysia" countries="Malaysia" 59 state="Negeri Sembilan" country="Malaysia" countries="Malaysia" 60 country="Brunei" countries="Brunei" 61 country="Indonesia" countries="Indonesia" 62 countries="Cambodia, Kampuchea" 63 country="Laos" countries="Laos" 64 country="Mynmar" countries="Mynmar" 65 country="Filipina" countries="Filipina" 66 country="Singapura" countries="Singapura" 67 country="Thailand" countries="Thailand" 68 country="Vietnam" countries="Vietnam" 74 country="China" countries="China" 75 country="India" countries="India" 76 country="Pakistan" countries="Pakistan" 77 country="Arab Saudi" countries="Arab Saudi" 78 country="Sri Lanka" countries="Sri Lanka" 79 country="Bangladesh" countries="Bangladesh" 82 state="Negeri Tidak Diketahui" country="Malaysia" countries="Malaysia" 83 countries="Australia, American Samoa, Macedonia, New Zealand, New Caledonia, Papua New Gurney, Fiji, Timor Leste" 84 countries="Argentina, Anguilla, Aruba, Bolivia, Brazil, Paraguay, Peru, Chile, Colombia, Equador, Uruguay, Venezuela" 85 countries="Algeria, Angola, Kenya, Afrika Tengah, Liberia, Afrika Selatan, Mali, Mauritania, Morocco, Malawi, Botswana, Mozambique, Burundi, Nigeria, Namibia, Cameroon, Chad, Rwanda, Senegal, Sierra Leone, Somalia, Djibouti, Sudan, Egypt, Ethopia, Swaziland, Eritrea, Gambia, Ghana, Tunisia, Tanzania, Tonga, Togo, Uganda, Zaire, Zambia, Zimbabwe" 86 countries="Austria, Luxembourg, Armenia, Malta, Monaco, Belgium, Nitherlands, Norway, Cyprus, Portugal, Denmark, Sweeden, Spain, Switzerland, France, Finland, Slovakia, Slovenia, Greece, Germany, Holy See (Vatican City), Italy" 87 countries="Britain, Ireland" 88 countries="Jordan, Kuwait, Lebanon, Bahrain, Oman, Qatar, Syria, Turkey, United Arab Emirate, Iran, Iraq, Israel, Yemen" 89 countries="Japan, Korea Selatan, Korea Utara, Taiwan" 90 countries="Jamaica, Bahamas, Barbados, Belize, Mexico, Nicaragua, Panama, Puerto Rico, Costa Rica, Cuba, Dominica, El Salvador, Grenada, Guatemala, Trinidad&Tobado, Haiti, Honduras" 91 countries="Canada, Greenland, United State" 92 countries="Albania, Albania, Latvia, Lithuania, Bulgaria, Byelorussia, Bosnia, Belarus, Poland, Romania, Russia, Czechoslovakia, Crotia, Esthonia, Serbia, Georgia, Hungary, Ukraine" 93 countries="Afghanistan, Antigua & Barbuda, Kazakhstan, Andorra/Andora, Libya, Arzebaijan, Antartica, Maldives, Madagascar, Mauritius, Mongolia, Benin, Maghribi, Bhutan, Macau, Nepal, Bermuda, Burkina faso/Burkina, Bora-bora, Bouvet Island, Palestine, Cape Verde, Comoros, Seychelles, Soloman Islands, Samoa, San Marino, Guinea, Gibraltar, Tajikistan, Tukmenistan, Hong Kong, Uzbekistan, Ivory Coast, Vanuatu, Iceland, Yugoslavia" python-stdnum-0.9/stdnum/my/__init__.py0000644000000000000000000000155012154632227020226 0ustar rootroot00000000000000# __init__.py - collection of Malaysian numbers # coding: utf-8 # # Copyright (C) 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of Malaysian numbers.""" python-stdnum-0.9/stdnum/my/nric.py0000644000000000000000000000715112204002711017406 0ustar rootroot00000000000000# nric.py - functions for handling NRIC numbers # # Copyright (C) 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """NRIC No. (Malaysian National Registration Identity Card Number). The NRIC No. is the unique identifier for issued to Malaysian citizens and permanent residents. The number consist of 12 digits in three sections. The first 6 digits represent the birth date, followed by two digits represeting the birth place and finally four digits. The gender of a person can be derived from the last digit: odd numbers for males and even numbers for females. >>> validate('770305-02-1234') '770305021234' >>> validate('771305-02-1234') # invalid date Traceback (most recent call last): ... InvalidComponent: ... >>> validate('770305-99-1234') # unknown birth place code Traceback (most recent call last): ... InvalidComponent: ... >>> format('770305021234') '770305-02-1234' """ import datetime from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" return clean(number, ' -*').strip() def get_birth_date(number): """Split the date parts from the number and return the birth date. Note that in some cases it may return the registration date instead of the birth date and it may be a century off.""" number = compact(number) year = int(number[0:2]) month = int(number[2:4]) day = int(number[4:6]) # this is a bit broken but it's easy try: return datetime.date(year + 1900, month, day) except ValueError: pass try: return datetime.date(year + 2000, month, day) except ValueError: raise InvalidComponent() def get_birth_place(number): """Use the number to look up the place of birth of the person. This can either be a state or federal territory within Malaysia or a country outside of Malaysia.""" from stdnum import numdb number = compact(number) results = numdb.get('my/bp').info(number[6:8])[0][1] if not results: raise InvalidComponent() return results def validate(number): """Checks to see if the number provided is a valid NRIC numbers. This checks the length, formatting and birth date and place.""" number = compact(number) if len(number) != 12: raise InvalidLength() if not number.isdigit(): raise InvalidFormat() get_birth_date(number) get_birth_place(number) return number def is_valid(number): """Checks to see if the number provided is a valid NRIC numbers. This checks the length, formatting and birth date and place.""" try: return bool(validate(number)) except ValidationError: return False def format(number): """Reformat the passed number to the standard format.""" number = compact(number) return number[:6] + '-' + number[6:8] + '-' + number[8:] python-stdnum-0.9/stdnum/lt/0000755000000000000000000000000012260536561016110 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/lt/pvm.py0000644000000000000000000000577612154624371017302 0ustar rootroot00000000000000# pvm.py - functions for handling Lithuanian VAT numbers # coding: utf-8 # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """PVM (Pridėtinės vertės mokestis mokėtojo kodas, Lithuanian VAT number). The PVM is used for VAT purposes in Lithuania. It is 9 digits (for legal entities) or 12 digits long (for temporarily registered taxpayers). This module does not check the format of Lithuanian personal codes (Asmens kodas). >>> validate('119511515') # organisation '119511515' >>> validate('LT 100001919017') # temporarily registered '100001919017' >>> validate('100001919018') # invalid check digit Traceback (most recent call last): ... InvalidChecksum: ... >>> validate('100004801610') # second step in check digit calculation '100004801610' """ from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, ' -').upper().strip() if number.startswith('LT'): number = number[2:] return number def calc_check_digit(number): """Calculate the check digit. The number passed should not have the check digit included.""" check = sum((1 + i % 9) * int(n) for i, n in enumerate(number)) % 11 if check == 10: check = sum((1 + (i + 2) % 9) * int(n) for i, n in enumerate(number)) return str(check % 11 % 10) def validate(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" number = compact(number) if not number.isdigit(): raise InvalidFormat() if len(number) == 9: # legal entities if number[7] != '1': raise InvalidComponent() elif len(number) == 12: # temporary tax payers and natural persons if number[10] != '1': raise InvalidComponent() else: raise InvalidLength() if calc_check_digit(number[:-1]) != number[-1]: raise InvalidChecksum() return number def is_valid(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/lt/__init__.py0000644000000000000000000000164611720140726020222 0ustar rootroot00000000000000# __init__.py - collection of Lithuanian numbers # coding: utf-8 # # Copyright (C) 2012 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of Lithuanian numbers.""" # provide vat as an alias from stdnum.lt import pvm as vat python-stdnum-0.9/stdnum/iban.dat0000644000000000000000000000541012260533041017062 0ustar rootroot00000000000000# generated from IBAN_Registry.txt, downloaded from # http://www.swift.com/dsp/resources/documents/IBAN_Registry.txt AL country="Albania" bban="8!n16!c" AD country="Andorra" bban="4!n4!n12!c" AT country="Austria" bban="5!n11!n" AZ country="Republic of Azerbaijan" bban="4!a20!c" BH country="Bahrain (Kingdom of)" bban="4!a14!c" BE country="Belgium" bban="3!n7!n2!n" BA country="Bosnia and Herzegovina" bban="3!n3!n8!n2!n" BR country="Brazil" bban="8!n5!n10!n1!a1!c" BG country="Bulgaria" bban="4!a4!n2!n8!c" CR country="Costa Rica" bban="3!n14!n" HR country="Croatia" bban="7!n10!n" CY country="Cyprus" bban="3!n5!n16!c" CZ country="Czech Republic" bban="4!n6!n10!n" DK country="Denmark" bban="4!n9!n1!n" FO country="Denmark" bban="4!n9!n1!n" GL country="Denmark" bban="4!n9!n1!n" DO country="Dominican Republic" bban="4!c20!n" EE country="Estonia" bban="2!n2!n11!n1!n" FI country="Finland" bban="6!n7!n1!n" FR country="France" bban="5!n5!n11!c2!n" GE country="Georgia" bban="2!a16!n" DE country="Germany" bban="8!n10!n" GI country="Gibraltar" bban="4!a15!c" GR country="Greece" bban="3!n4!n16!c" GT country="Guatemala" bban="4!c20!c" HU country="Hungary" bban="3!n4!n1!n15!n1!n" IS country="Iceland" bban="4!n2!n6!n10!n" IE country="Ireland" bban="4!a6!n8!n" IL country="Israel" bban="3!n3!n13!n" IT country="Italy" bban="1!a5!n5!n12!c" KW country="Kuwait" bban="4!a22!c" KZ country="Kazakhstan" bban="3!n13!c" LV country="Latvia" bban="4!a13!c" LB country="Lebanon" bban="4!n20!c" LI country="Liechtenstein (Principality of)" bban="5!n12!c" LT country="Lithuania" bban="5!n11!n" LU country="Luxembourg" bban="3!n13!c" MK country="Macedonia, Former Yugoslav Republic of" bban="3!n10!c2!n" MT country="Malta" bban="4!a5!n18!c" MR country="Mauritania" bban="5!n5!n11!n2!n" MU country="Mauritius" bban="4!a2!n2!n12!n3!n3!a" MD country="Republic of Moldova" bban="2!c18!c" MC country="Monaco" bban="5!n5!n11!c2!n" ME country="Montenegro" bban="3!n13!n2!n" NL country="The Netherlands" bban="4!a10!n" NO country="Norway" bban="4!n6!n1!n" PK country="Pakistan" bban="4!a16!c" PS country="Palestine, State of" bban="4!a21!c" PL country="Poland" bban="8!n16!n" PT country="Portugal" bban="4!n4!n11!n2!n" QA country="Qatar" bban="4!a21!c" RO country="Romania" bban="4!a16!c" SM country="San Marino" bban="1!a5!n5!n12!c" SA country="Saudi Arabia" bban="2!n18!c" RS country="Serbia" bban="3!n13!n2!n" SK country="Slovak Republic" bban="4!n6!n10!n" SI country="Slovenia" bban="5!n8!n2!n" ES country="Spain" bban="4!n4!n1!n1!n10!n" SE country="Sweden" bban="3!n16!n1!n" CH country="Switzerland" bban="5!n12!c" TN country="Tunisia" bban="2!n3!n13!n2!n" TR country="Turkey" bban="5!n1!c16!c" AE country="United Arab Emirates" bban="3!n16!n" GB country="United Kingdom" bban="4!a6!n8!n" VG country="Virgin Islands, British" bban="4!a16!n" python-stdnum-0.9/stdnum/ismn.py0000644000000000000000000001035212154624370017010 0ustar rootroot00000000000000# ismn.py - functions for handling ISMNs # # Copyright (C) 2010, 2011, 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """ISMN (International Standard Music Number). The ISMN (International Standard Music Number) is used to identify sheet music. This module handles both numbers in the 10-digit 13-digit format. >>> validate('979-0-3452-4680-5') '9790345246805' >>> validate('9790060115615') '9790060115615' >>> ismn_type(' M-2306-7118-7') 'ISMN10' >>> validate('9790060115614') Traceback (most recent call last): ... InvalidChecksum: ... >>> compact(' 979-0-3452-4680-5') '9790345246805' >>> format('9790060115615') '979-0-060-11561-5' >>> format('M230671187') '979-0-2306-7118-7' >>> to_ismn13('M230671187') '9790230671187' """ from stdnum import ean from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the ISMN to the minimal representation. This strips the number of any valid ISMN separators and removes surrounding whitespace.""" return clean(number, ' -.').strip().upper() def validate(number): """Checks to see if the number provided is a valid ISMN (either a legacy 10-digit one or a 13-digit one). This checks the length and the check bit but does not check if the publisher is known.""" number = compact(number) if len(number) == 10: if number[0] != 'M': raise InvalidFormat() ean.validate('9790' + number[1:]) else: ean.validate(number) return number def ismn_type(number): """Check the type of ISMN number passed and return 'ISMN13', 'ISMN10' or None (for invalid).""" try: number = validate(number) except ValidationError: return None if len(number) == 10: return 'ISMN10' elif len(number) == 13: return 'ISMN13' def is_valid(number): """Checks to see if the number provided is a valid ISMN (either a legacy 10-digit one or a 13-digit one). This checks the length and the check bit but does not check if the publisher is known.""" try: return bool(validate(number)) except ValidationError: return False def to_ismn13(number): """Convert the number to ISMN13 (EAN) format.""" number = number.strip() min_number = compact(number) if len(min_number) == 13: return number # nothing to do, already 13 digit format # add prefix and strip the M if ' ' in number: return '979 0' + number[1:] elif '-' in number: return '979-0' + number[1:] else: return '9790' + number[1:] # these are the ranges allocated to publisher codes _ranges = ( (3, '000', '099'), (4, '1000', '3999'), (5, '40000', '69999'), (6, '700000', '899999'), (7, '9000000', '9999999')) def split(number): """Split the specified ISMN into a bookland prefix (979), an ISMN prefix (0), a publisher element (3 to 7 digits), an item element (2 to 6 digits) and a check digit.""" # clean up number number = to_ismn13(compact(number)) # rind the correct range and split the number for length, low, high in _ranges: if low <= number[4:4 + length] <= high: return (number[:3], number[3], number[4:4 + length], number[4 + length:-1], number[-1]) def format(number, separator='-'): """Reformat the passed number to the standard format with the prefixes, the publisher element, the item element and the check-digit separated by the specified separator. The number is converted to the 13-digit format silently.""" return separator.join(x for x in split(number) if x) python-stdnum-0.9/stdnum/ee/0000755000000000000000000000000012260536561016062 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/ee/kmkr.py0000644000000000000000000000431112154624370017375 0ustar rootroot00000000000000# kmkr.py - functions for handling Estonian VAT numbers # coding: utf-8 # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """KMKR (Käibemaksukohuslase, Estonian VAT number). >>> compact('EE 100 931 558') '100931558' >>> validate('100594102') '100594102' >>> validate('100594103') # incorrect check digit Traceback (most recent call last): ... InvalidChecksum: ... """ from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, ' ').upper().strip() if number.startswith('EE'): number = number[2:] return number def checksum(number): """Calculate the checksum.""" weights = (3, 7, 1, 3, 7, 1, 3, 7, 1) return sum(weights[i] * int(n) for i, n in enumerate(number)) % 10 def validate(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" number = compact(number) if not number.isdigit(): raise InvalidFormat() if len(number) != 9: raise InvalidLength() if checksum(number) != 0: raise InvalidChecksum() return number def is_valid(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/ee/__init__.py0000644000000000000000000000164311720140727020172 0ustar rootroot00000000000000# __init__.py - collection of Estonian numbers # coding: utf-8 # # Copyright (C) 2012 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of Estonian numbers.""" # provide vat as an alias from stdnum.ee import kmkr as vat python-stdnum-0.9/stdnum/gr/0000755000000000000000000000000012260536561016101 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/gr/__init__.py0000644000000000000000000000154011720140730020177 0ustar rootroot00000000000000# __init__.py - collection of Greek numbers # coding: utf-8 # # Copyright (C) 2012 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of Greek numbers.""" python-stdnum-0.9/stdnum/gr/vat.py0000644000000000000000000000471312154624370017250 0ustar rootroot00000000000000# vat.py - functions for handling Greek VAT numbers # coding: utf-8 # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """FPA, ΦΠΑ (Foros Prostithemenis Aksias, the Greek VAT number). The FPA is a 9-digit number with a simple checksum. >>> compact('GR 23456783') '023456783' >>> validate('EL 094259216 ') '094259216' >>> validate('EL 123456781') Traceback (most recent call last): ... InvalidChecksum: ... """ from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, ' -./:').upper().strip() if number.startswith('EL') or number.startswith('GR'): number = number[2:] if len(number) == 8: number = '0' + number # old format had 8 digits return number def calc_check_digit(number): """Calculate the check digit. The number passed should not have the check digit included.""" checksum = 0 for n in number: checksum = checksum * 2 + int(n) return str(checksum * 2 % 11 % 10) def validate(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" number = compact(number) if not number.isdigit(): raise InvalidFormat() if len(number) != 9: raise InvalidLength() if calc_check_digit(number[:-1]) != number[-1]: raise InvalidChecksum() return number def is_valid(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/__init__.py0000644000000000000000000001304312260533244017576 0ustar rootroot00000000000000# __init__.py - main module # coding: utf-8 # # Copyright (C) 2010, 2011, 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Parse, validate and reformat standard numbers and codes. This library offers functions for parsing, validating and reformatting standard numbers and codes in various formats. Currently this package supports the following formats: * at.uid: UID (Umsatzsteuer-Identifikationsnummer, Austrian VAT number) * be.vat: BTW, TVA, NWSt (Belgian VAT number) * bg.egn: EGN (ЕГН, Единен граждански номер, Bulgarian personal identity codes) * bg.pnf: PNF (ЛНЧ, Личен номер на чужденец, Bulgarian number of a foreigner) * bg.vat: VAT (Идентификационен номер по ДДС, Bulgarian VAT number) * br.cpf: CPF (Cadastro de Pessoas Físicas, Brazillian national identifier) * cy.vat: Αριθμός Εγγραφής Φ.Π.Α. (Cypriot VAT number) * cz.dic: DIČ (Daňové identifikační číslo, Czech VAT number) * cz.rc: RČ (Rodné číslo, the Czech birth number) * de.vat: Ust ID Nr. (Umsatzsteur Identifikationnummer, German VAT number) * dk.cpr: CPR (personnummer, the Danish citizen number) * dk.cvr: CVR (Momsregistreringsnummer, Danish VAT number) * ean: EAN (International Article Number) * ee.kmkr: KMKR (Käibemaksukohuslase, Estonian VAT number) * es.cif: CIF (Certificado de Identificación Fiscal, Spanish company tax number) * es.dni: DNI (Documento nacional de identidad, Spanish personal identity codes) * es.nie: NIE (Número de Identificación de Extranjeros, Spanish foreigner number) * es.nif: NIF (Número de Identificación Fiscal, Spanish VAT number) * eu.vat: VAT (European Union VAT number) * fi.alv: ALV nro (Arvonlisäveronumero, Finnish VAT number) * fi.hetu: HETU (Henkilötunnus, Finnish personal identity code) * fr.siren: SIREN (a French company identification number) * fr.tva: n° TVA (taxe sur la valeur ajoutée, French VAT number) * gb.vat: VAT (United Kingdom (and Isle of Man) VAT registration number) * gr.vat: FPA, ΦΠΑ (Foros Prostithemenis Aksias, the Greek VAT number) * grid: GRid (Global Release Identifier) * hr.oib: OIB (Osobni identifikacijski broj, Croatian identification number) * hu.anum: ANUM (Közösségi adószám, Hungarian VAT number) * iban: IBAN (International Bank Account Number) * ie.pps: PPS No (Personal Public Service Number, Irish personal number) * ie.vat: VAT (Irish VAT number) * imei: IMEI (International Mobile Equipment Identity) * imsi: IMSI (International Mobile Subscriber Identity) * isan: ISAN (International Standard Audiovisual Number) * isbn: ISBN (International Standard Book Number) * isil: ISIL (International Standard Identifier for Libraries) * ismn: ISMN (International Standard Music Number) * issn: ISSN (International Standard Serial Number) * it.iva: Partita IVA (Italian VAT number) * lt.pvm: PVM (Pridėtinės vertės mokestis mokėtojo kodas, Lithuanian VAT number) * lu.tva: TVA (taxe sur la valeur ajoutée, Luxembourgian VAT number) * lv.pvn: PVN (Pievienotās vērtības nodokļa, Latvian VAT number) * meid: MEID (Mobile Equipment Identifier) * mt.vat: VAT (Maltese VAT number) * my.nric: NRIC No. (Malaysian National Registration Identity Card Number) * nl.brin: Brin number (Dutch number for schools) * nl.bsn: BSN (Burgerservicenummer, Dutch national identification number) * nl.btw: BTW-nummer (Omzetbelastingnummer, the Dutch VAT number) * nl.onderwijsnummer: Onderwijsnummer (Dutch student school number) * nl.postcode: Postcode (Dutch postal code) * pl.nip: NIP (Numer Identyfikacji Podatkowej, Polish VAT number) * pt.nif: NIF (Número de identificação fiscal, Portuguese VAT number) * ro.cf: CF (Cod de înregistrare în scopuri de TVA, Romanian VAT number) * ro.cnp: CNP (Cod Numeric Personal, Romanian Numerical Personal Code) * se.vat: VAT (Moms, Mervärdesskatt, Swedish VAT number) * si.ddv: ID za DDV (Davčna številka, Slovenian VAT number) * sk.dph: IČ DPH (IČ pre daň z pridanej hodnoty, Slovak VAT number) * sk.rc: RČ (Rodné číslo, the Slovak birth number) * us.atin: ATIN (U.S. Adoption Taxpayer Identification Number) * us.ein: EIN (U.S. Employer Identification Number) * us.itin: ITIN (U.S. Individual Taxpayer Identification Number) * us.ptin: PTIN (U.S. Preparer Tax Identification Number) * us.ssn: SSN (U.S. Social Security Number) * us.tin: TIN (U.S. Taxpayer Identification Number) Furthermore a number of generic check digit algorithms are available: * iso7064.mod_11_10: The ISO 7064 Mod 11, 10 algorithm * iso7064.mod_11_2: The ISO 7064 Mod 11, 2 algorithm * iso7064.mod_37_2: The ISO 7064 Mod 37, 2 algorithm * iso7064.mod_37_36: The ISO 7064 Mod 37, 36 algorithm * iso7064.mod_97_10: The ISO 7064 Mod 97, 10 algorithm * luhn: The Luhn and Luhn mod N algorithms * verhoeff: The Verhoeff algorithm """ # the version number of the library __version__ = '0.9' python-stdnum-0.9/stdnum/numdb.py0000644000000000000000000001456712260526664017170 0ustar rootroot00000000000000# numdb.py - module for handling hierarchically organised numbers # # Copyright (C) 2010, 2011, 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Query structured number format files with number properties. This module contains functions for reading and querying a database that stores numbers that use a hierarchical format (e.g. ISBN, IBAN, phone numbers, etc). To read a database from a file: >>> dbfile = read(open('numdb-test.dat', 'r')) To split a number: >>> dbfile.split('01006') ['0', '100', '6'] >>> dbfile.split('902006') ['90', '20', '06'] >>> dbfile.split('909856') ['90', '985', '6'] To split the number and get properties for each part: >>> dbfile.info('01006') == [ ... ('0', {'prop1': 'foo'}), ... ('100', {'prop2': 'bar'}), ... ('6', {}), ... ] True >>> dbfile.info('02006') == [ ... ('0', {'prop1': 'foo'}), ... ('200', {'prop2': 'bar', 'prop3': 'baz'}), ... ('6', {}), ... ] True >>> dbfile.info('03456') == [ ... ('0', {'prop1': 'foo'}), ... ('345', {'prop2': 'bar', 'prop3': 'baz'}), ... ('6', {}), ... ] True >>> dbfile.info('902006') == [ ... ('90', {'prop1': 'booz'}), ... ('20', {'prop2': 'foo'}), ... ('06', {}), ... ] True >>> dbfile.info('909856') == [ ... ('90', {'prop1': 'booz'}), ... ('985', {'prop2': 'fooz'}), ... ('6', {}), ... ] True >>> dbfile.info('9889') == [ ... ('98', {'prop1': 'booz'}), ... ('89', {'prop2': 'foo'}), ... ] True >>> dbfile.info('633322') == [ ... ('6', {'prop1': 'boo'}), ... ('333', {'prop2': 'bar', 'prop3': 'baz'}), ... ('22', {}), ... ] True """ import re from pkg_resources import resource_stream _line_re = re.compile('^(?P *)(?P([^-,\s]+(-[^-,\s]+)?)(,[^-,\s]+(-[^-,\s]+)?)*)\s*(?P.*)$') _prop_re = re.compile('(?P[0-9a-zA-Z-_]+)="(?P[^"]*)"') # this is a cache of open databases _open_databases = {} # the prefixes attribute of NumDB is structured as follows: # prefixes = [ # [ length, low, high, props, children ] # ... # ] # where children is a prefixes structure in it's own right # (there is no expected ordering within the list) class NumDB(object): def __init__(self): self.prefixes = [] @staticmethod def _merge(results): """Merge the provided list of possible results into a single result list (this is a generator).""" # expand the results to all have the same length ml = max(len(x) for x in results) results = [x + (ml - len(x)) * [None] for x in results] # go over each part for parts in zip(*results): # regroup parts into parts list and properties list partlist, proplist = list(zip(*(x for x in parts if x))) part = min(partlist, key=len) props = {} for p in proplist: props.update(p) yield part, props @staticmethod def _find(number, prefixes): """Lookup the specified number in the list of prefixes, this will return basically what info() should return but works recursively.""" if not number: return [] results = [] if prefixes: for length, low, high, props, children in prefixes: if low <= number[:length] <= high and len(number) >= length: results.append([(number[:length], props)] + NumDB._find(number[length:], children)) # not-found fallback if not results: return [(number, {})] # merge the results into a single result return list(NumDB._merge(results)) def info(self, number): """Split the provided number in components and associate properties with each component. This returns a tuple of tuples. Each tuple consists of a string (a part of the number) and a dict of properties. """ return NumDB._find(number, self.prefixes) def split(self, number): """Split the provided number in components. This returns a tuple with the number of components identified.""" return [part for part, props in self.info(number)] def _parse(fp): """Read lines of text from the file pointer and generate indent, length, low, high, properties tuples.""" for line in fp: # ignore comments if line[0] == '#' or line.strip() == '': continue # pragma: no cover (optimisation takes it out) # any other line should parse match = _line_re.search(line) indent = len(match.group('indent')) ranges = match.group('ranges') props = dict(_prop_re.findall(match.group('props'))) for rnge in ranges.split(','): if '-' in rnge: low, high = rnge.split('-') else: low, high = rnge, rnge yield indent, len(low), low, high, props def read(fp): """Return a new database with the data read from the specified file.""" last_indent = 0 db = NumDB() stack = {0: db.prefixes} for indent, length, low, high, props in _parse(fp): if indent > last_indent: # populate the children field of the last indent if stack[last_indent][-1][4] is None: stack[last_indent][-1][4] = [] stack[indent] = stack[last_indent][-1][4] stack[indent].append([length, low, high, props, None]) last_indent = indent return db def get(name): """Opens a database with the specified name to perform queries on.""" if name not in _open_databases: import codecs reader = codecs.getreader('utf-8') _open_databases[name] = read(reader(resource_stream(__name__, name + '.dat'))) return _open_databases[name] python-stdnum-0.9/stdnum/issn.py0000644000000000000000000000561612154624371017026 0ustar rootroot00000000000000# issn.py - functions for handling ISSNs # # Copyright (C) 2010, 2011, 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """ISSN (International Standard Serial Number). The ISSN (International Standard Serial Number) is the standard code to identify periodical publications. It has a checksum similar to ISBN-10. >>> validate('0024-9319') '00249319' >>> validate('0032147X') Traceback (most recent call last): ... InvalidChecksum: ... >>> validate('003214712') Traceback (most recent call last): ... InvalidLength: ... >>> compact('0032-1478') '00321478' >>> format('00249319') '0024-9319' >>> to_ean('0264-3596') '9770264359008' """ from stdnum import ean from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the ISSN to the minimal representation. This strips the number of any valid ISSN separators and removes surrounding whitespace.""" return clean(number, ' -').strip().upper() def calc_check_digit(number): """Calculate the ISSN check digit for 10-digit numbers. The number passed should not have the check bit included.""" check = (11 - sum((8 - i) * int(n) for i, n in enumerate(number))) % 11 return 'X' if check == 10 else str(check) def validate(number): """Checks to see if the number provided is a valid ISSN. This checks the length and whether the check digit is correct.""" number = compact(number) if not number[:-1].isdigit(): raise InvalidFormat() if len(number) != 8: raise InvalidLength() if calc_check_digit(number[:-1]) != number[-1]: raise InvalidChecksum() return number def is_valid(number): """Checks to see if the number provided is a valid ISSN. This checks the length and whether the check digit is correct.""" try: return bool(validate(number)) except ValidationError: return False def format(number): """Reformat the passed number to the standard format.""" number = compact(number) return number[:4] + '-' + number[4:] def to_ean(number, issue_code='00'): """Convert the number to EAN-13 format.""" number = '977' + validate(number)[:-1] + issue_code return number + ean.calc_check_digit(number) python-stdnum-0.9/stdnum/es/0000755000000000000000000000000012260536561016100 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/es/nie.py0000644000000000000000000000457112154624370017232 0ustar rootroot00000000000000# nie.py - functions for handling Spanish foreigner identity codes # coding: utf-8 # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """NIE (Número de Identificación de Extranjeros, Spanish foreigner number). The NIE is an identification number for foreigners. It is a 9 digit number where the first digit is either X, Y or Z and last digit is a checksum letter. >>> validate('x-2482300w') 'X2482300W' >>> validate('x-2482300a') # invalid check digit Traceback (most recent call last): ... InvalidChecksum: ... >>> validate('X2482300') # digit missing Traceback (most recent call last): ... InvalidLength: ... """ from stdnum.es import dni from stdnum.exceptions import * __all__ = ['compact', 'is_valid'] # use the same compact function as DNI compact = dni.compact def calc_check_digit(number): """Calculate the check digit. The number passed should not have the check digit included.""" # replace XYZ with 012 number = str('XYZ'.index(number[0])) + number[1:] return dni.calc_check_digit(number) def validate(number): """Checks to see if the number provided is a valid NIE. This checks the length, formatting and check digit.""" number = compact(number) if not number[1:-1].isdigit() or number[:1] not in 'XYZ': raise InvalidFormat() if len(number) != 9: raise InvalidLength() if calc_check_digit(number[:-1]) != number[-1]: raise InvalidChecksum() return number def is_valid(number): """Checks to see if the number provided is a valid NIE. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/es/__init__.py0000644000000000000000000000164011720140730020177 0ustar rootroot00000000000000# __init__.py - collection of Spanish numbers # coding: utf-8 # # Copyright (C) 2012 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of Spanish numbers.""" # provide vat as an alias from stdnum.es import nif as vat python-stdnum-0.9/stdnum/es/nif.py0000644000000000000000000000531712154624370017232 0ustar rootroot00000000000000# nif.py - functions for handling Spanish NIF (VAT) numbers # coding: utf-8 # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """NIF (Número de Identificación Fiscal, Spanish VAT number). The Spanish VAT number is a 9-digit number where either the first, last digits or both can be letters. The number is either a DNI (Documento nacional de identidad, for Spaniards), a NIE (Número de Identificación de Extranjeros, for foreigners) or a CIF (Certificado de Identificación Fiscal, for legal entities and others). >>> compact('ES B-58378431') 'B58378431' >>> validate('B64717838') 'B64717838' >>> validate('B64717839') # invalid check digit Traceback (most recent call last): ... InvalidChecksum: ... >>> validate('54362315K') # resident '54362315K' >>> validate('X-5253868-R') # foreign person 'X5253868R' """ from stdnum.es import dni, nie, cif from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, ' -').upper().strip() if number.startswith('ES'): number = number[2:] return number def validate(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" number = compact(number) if not number[1:-1].isdigit(): raise InvalidFormat() if len(number) != 9: raise InvalidLength() if number[0].isdigit(): # natural resident dni.validate(number) elif number[0] in 'XYZ': # foreign natural person nie.validate(number) else: # otherwise it has to be a valid CIF cif.validate(number) return number def is_valid(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/es/dni.py0000644000000000000000000000475312154624370017233 0ustar rootroot00000000000000# dni.py - functions for handling Spanish personal identity codes # coding: utf-8 # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """DNI (Documento nacional de identidad, Spanish personal identity codes). The DNI is a 9 digit number used to identify Spanish citizens. The last digit is a checksum letter. Foreign nationals, since 2010 are issued an NIE (Número de Identificación de Extranjeros, Foreigner's Identity Number) instead. >>> validate('54362315-K') '54362315K' >>> validate('54362315Z') # invalid check digit Traceback (most recent call last): ... InvalidChecksum: ... >>> validate('54362315') # digit missing Traceback (most recent call last): ... InvalidLength: ... """ from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" return clean(number, ' -').upper().strip() def calc_check_digit(number): """Calculate the check digit. The number passed should not have the check digit included.""" return 'TRWAGMYFPDXBNJZSQVHLCKE'[int(number) % 23] def validate(number): """Checks to see if the number provided is a valid DNI number. This checks the length, formatting and check digit.""" number = compact(number) if not number[:-1].isdigit(): raise InvalidFormat() if len(number) != 9: raise InvalidLength() if calc_check_digit(number[:-1]) != number[-1]: raise InvalidChecksum() return number def is_valid(number): """Checks to see if the number provided is a valid DNI number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/es/cif.py0000644000000000000000000000723212154624370017215 0ustar rootroot00000000000000# cif.py - functions for handling Spanish fiscal numbers # coding: utf-8 # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """CIF (Certificado de Identificación Fiscal, Spanish company tax number). The CIF is a tax identification number for legal entities. It has 9 digits where the first digit is a letter (denoting the type of entity) and the last is a check digit (which may also be a letter). >>> validate('J99216582') 'J99216582' >>> validate('J99216583') # invalid check digit Traceback (most recent call last): ... InvalidChecksum: ... >>> validate('J992165831') # too long Traceback (most recent call last): ... InvalidLength: ... >>> validate('M-1234567-L') 'M1234567L' >>> validate('O-1234567-L') # invalid first character Traceback (most recent call last): ... InvalidFormat: ... >>> split('A13 585 625') ('A', '13', '58562', '5') """ from stdnum import luhn from stdnum.es import dni from stdnum.exceptions import * __all__ = ['compact', 'validate', 'is_valid', 'split'] # use the same compact function as DNI compact = dni.compact def calc_check_digits(number): """Calculate the check digits for the specified number. The number passed should not have the check digit included. This function returns both the number and character check digit candidates.""" check = luhn.calc_check_digit(number[1:]) return check + 'JABCDEFGHI'[int(check)] def validate(number): """Checks to see if the number provided is a valid DNI number. This checks the length, formatting and check digit.""" number = compact(number) if not number[1:-1].isdigit(): raise InvalidFormat() if len(number) != 9: raise InvalidLength() if number[0] in 'KLM': # K: Spanish younger than 14 year old # L: Spanish living outside Spain without DNI # M: granted the tax to foreigners who have no NIE # these use the old checkdigit algorithm (the DNI one) if number[-1] != dni.calc_check_digit(number[1:-1]): raise InvalidChecksum() elif number[0] in 'ABCDEFGHJNPQRSUVW': # there seems to be conflicting information on which organisation types # should have which type of check digit (alphabetic or numeric) so # we support either here if number[-1] not in calc_check_digits(number[:-1]): raise InvalidChecksum() else: # anything else is invalid raise InvalidFormat() return number def is_valid(number): """Checks to see if the number provided is a valid DNI number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False def split(number): """Split the provided number into a letter to define the type of organisation, two digits that specify a province, a 5 digit sequence number within the province and a check digit.""" number = compact(number) return number[0], number[1:3], number[3:8], number[8:] python-stdnum-0.9/stdnum/isan.py0000644000000000000000000001412112260533040016761 0ustar rootroot00000000000000# isan.py - functions for handling International Standard Audiovisual Numbers # (ISANs) # # Copyright (C) 2010, 2011, 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """ISAN (International Standard Audiovisual Number). The ISAN (International Standard Audiovisual Number) is used to identify audiovisual works. The number is hexadecimal and can consists of at least a root identifier, and an episode or part. After that an optional check digit, optional version and optionally another check digit can be provided. The check digits are validated using the ISO 7064 Mod 37, 36 algorithm. >>> validate('000000018947000000000000') '000000018947000000000000' >>> compact('0000-0000-D07A-0090-Q-0000-0000-X') '00000000D07A009000000000' >>> validate('0000-0001-8CFA-0000-I-0000-0000-K') '000000018CFA0000I00000000K' >>> validate('0000-0001-8CFA-0000-A-0000-0000-K') Traceback (most recent call last): ... InvalidChecksum: ... >>> format('000000018947000000000000') '0000-0001-8947-0000-8-0000-0000-D' >>> to_urn('00000000D07A009000000000') 'URN:ISAN:0000-0000-D07A-0090-Q-0000-0000-X' >>> to_xml('1881-66C7-3420-6541-Y-9F3A-0245-O') '' """ from stdnum.exceptions import * from stdnum.iso7064 import mod_37_36 from stdnum.util import clean def split(number): """Splits the number into a root, an episode or part, a check digit a version and another check digit. If any of the parts are missing an empty string is returned.""" number = clean(number, ' -').strip().upper() if len(number) == 17 or len(number) == 26: return number[0:12], number[12:16], number[16], number[17:25], number[25:] elif len(number) > 16: return number[0:12], number[12:16], '', number[16:24], number[24:] else: return number[0:12], number[12:16], number[16:], '', '' def compact(number, strip_check_digits=True): """Convert the ISAN to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace. The check digits are removed by default.""" number = list(split(number)) number[2] = number[4] = '' return ''.join(number) def validate(number, strip_check_digits=False, add_check_digits=False): """Checks to see if the number provided is a valid ISAN. If check digits are present in the number they are validated. If strip_check_digits is True any existing check digits will be removed (after checking). If add_check_digits is True the check digit will be added if they are not present yet.""" (root, episode, check1, version, check2) = split(number) # check digits used for x in root + episode + version: if x not in '0123456789ABCDEF': raise InvalidFormat() # check length of all components if len(root) != 12 or len(episode) != 4 or len(check1) not in (0, 1) or \ len(version) not in (0, 8) or len(check1) not in (0, 1): raise InvalidLength() # check check digits if check1: mod_37_36.validate(root + episode + check1) if check2: mod_37_36.validate(root + episode + version + check2) # remove or add check digits if strip_check_digits: check1 = check2 = '' if add_check_digits and not check1: check1 = mod_37_36.calc_check_digit(root + episode) if add_check_digits and not check2 and version: check2 = mod_37_36.calc_check_digit(root + episode + version) return root + episode + check1 + version + check2 def is_valid(number): """Checks to see if the number provided is a valid ISAN. If check digits are present in the number they are validated.""" try: return bool(validate(number)) except ValidationError: return False def format(number, separator='-', strip_check_digits=False, add_check_digits=True): """Reformat the passed number to the standard format. If add_check_digits is True the check digit will be added if they are not present yet. If both strip_check_digits and add_check_digits are True the check digits will be recalculated.""" (root, episode, check1, version, check2) = split(number) if strip_check_digits: check1 = check2 = '' if add_check_digits and not check1: check1 = mod_37_36.calc_check_digit(root + episode) if add_check_digits and not check2 and version: check2 = mod_37_36.calc_check_digit(root + episode + version) number = [root[i:i + 4] for i in range(0, 12, 4)] + [episode] if check1: number.append(check1) if version: number.extend((version[0:4], version[4:])) if check2: number.append(check2) return separator.join(number) def to_binary(number): """Convert the number to it's binary representation (without the check digits).""" import sys number = compact(number, strip_check_digits=True) if sys.version > '3': # pragma: no cover (Python 2/3 specific code) return bytes.fromhex(number) else: # pragma: no cover (Python 2/3 specific code) return number.decode('hex') def to_xml(number): """Returns the XML form of the ISAN as a string.""" number = format(number, strip_check_digits=True, add_check_digits=False) return '' % ( number[0:14], number[15:19], number[20:]) def to_urn(number): """Returns the URN representation of the ISAN.""" return 'URN:ISAN:' + format(number, add_check_digits=True) python-stdnum-0.9/stdnum/bg/0000755000000000000000000000000012260536561016061 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/bg/egn.py0000644000000000000000000000652412154624370017211 0ustar rootroot00000000000000# egn.py - functions for handling Bulgarian national identification numbers # coding: utf-8 # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """EGN (ЕГН, Единен граждански номер, Bulgarian personal identity codes). It is a 10-digit number of which the first 6 digits denote the person's birth date, the next three digits represent a birth order number from which the person's gender can be determined and the last digit is a check digit. >>> compact('752316 926 3') '7523169263' >>> validate('8032056031') '8032056031' >>> get_birth_date('7542011030') datetime.date(2075, 2, 1) >>> validate('7552A10004') # invalid digit Traceback (most recent call last): ... InvalidFormat: ... >>> validate('8019010008') # invalid date Traceback (most recent call last): ... InvalidComponent: ... """ import datetime from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" return clean(number, ' -.').upper().strip() def calc_check_digit(number): """Calculate the check digit. The number passed should not have the check digit included.""" weights = (2, 4, 8, 5, 10, 9, 7, 3, 6) return str(sum(weights[i] * int(n) for i, n in enumerate(number)) % 11 % 10) def get_birth_date(number): """Split the date parts from the number and return the birth date.""" year = int(number[0:2]) + 1900 month = int(number[2:4]) day = int(number[4:6]) if month > 40: year += 100 month -= 40 elif month > 20: year -= 100 month -= 20 try: return datetime.date(year, month, day) except ValueError: raise InvalidComponent() def validate(number): """Checks to see if the number provided is a valid national identification number. This checks the length, formatting, embedded date and check digit.""" number = compact(number) if not number.isdigit(): raise InvalidFormat() if len(number) != 10: raise InvalidLength() # check if birth date is valid birth_date = get_birth_date(number) # TODO: check that the birth date is not in the future # check the check digit if calc_check_digit(number[:-1]) != number[-1]: raise InvalidChecksum() return number def is_valid(number): """Checks to see if the number provided is a valid national identification number. This checks the length, formatting, embedded date and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/bg/__init__.py0000644000000000000000000000155011720140724020163 0ustar rootroot00000000000000# __init__.py - collection of Bulgarian numbers # coding: utf-8 # # Copyright (C) 2012 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of Bulgarian numbers.""" python-stdnum-0.9/stdnum/bg/pnf.py0000644000000000000000000000505112154624370017215 0ustar rootroot00000000000000# pnf.py - functions for handling Bulgarian personal number of a foreigner # coding: utf-8 # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """PNF (ЛНЧ, Личен номер на чужденец, Bulgarian number of a foreigner). The personal number of a foreigner is a 10-digit number where the last digit is the result of a weighted checksum. >>> validate('7111 042 925') '7111042925' >>> validate('7111042922') # invalid check digit Traceback (most recent call last): ... InvalidChecksum: ... >>> validate('71110A2922') # invalid digit Traceback (most recent call last): ... InvalidFormat: ... """ from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" return clean(number, ' -.').upper().strip() def calc_check_digit(number): """Calculate the check digit. The number passed should not have the check digit included.""" weights = (21, 19, 17, 13, 11, 9, 7, 3, 1) return str(sum(weights[i] * int(n) for i, n in enumerate(number)) % 10) def validate(number): """Checks to see if the number provided is a valid national identification number. This checks the length, formatting, embedded date and check digit.""" number = compact(number) if not number.isdigit(): raise InvalidFormat() if len(number) != 10: raise InvalidLength() if calc_check_digit(number[:-1]) != number[-1]: raise InvalidChecksum() return number def is_valid(number): """Checks to see if the number provided is a valid national identification number. This checks the length, formatting, embedded date and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/bg/vat.py0000644000000000000000000000646412154624370017235 0ustar rootroot00000000000000# vat.py - functions for handling Bulgarian VAT numbers # coding: utf-8 # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """VAT (Идентификационен номер по ДДС, Bulgarian VAT number). The Bulgarian VAT (Данък върху добавената стойност) number is either 9 (for legal entities) or 10 digits (for physical persons, foreigners and others) long. Each type of number has it's own check digit algorithm. >>> compact('BG 175 074 752') '175074752' >>> validate('175074752') '175074752' >>> validate('175074751') # invalid check digit Traceback (most recent call last): ... InvalidChecksum: ... """ from stdnum.bg import egn, pnf from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, ' -.').upper().strip() if number.startswith('BG'): number = number[2:] return number def calc_check_digit_legal(number): """Calculate the check digit for legal entities. The number passed should not have the check digit included.""" check = sum((i + 1) * int(n) for i, n in enumerate(number)) % 11 if check == 10: check = sum((i + 3) * int(n) for i, n in enumerate(number)) % 11 return str(check % 10) def calc_check_digit_other(number): """Calculate the check digit for others. The number passed should not have the check digit included.""" weights = (4, 3, 2, 7, 6, 5, 4, 3, 2) return str((11 - sum(weights[i] * int(n) for i, n in enumerate(number))) % 11) def validate(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" number = compact(number) if not number.isdigit(): raise InvalidFormat() if len(number) == 9: # 9 digit numbers are for legal entities if number[-1] != calc_check_digit_legal(number[:-1]): raise InvalidChecksum() elif len(number) == 10: # 10 digit numbers are for physical persons, foreigners and others if not egn.is_valid(number) and not pnf.is_valid(number) and \ number[-1] != calc_check_digit_other(number[:-1]): raise InvalidChecksum() else: raise InvalidLength() return number def is_valid(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/fi/0000755000000000000000000000000012260536561016067 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/fi/hetu.py0000644000000000000000000000711212154624370017405 0ustar rootroot00000000000000# hetu.py - functions for handling Finnish personal identity codes # coding: utf-8 # # Copyright (C) 2011 Jussi Judin # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """HETU (Henkilötunnus, Finnish personal identity code). Module for handling Finnish personal identity codes (HETU, Henkilötunnus). See http://www.vaestorekisterikeskus.fi/default.aspx?id=45 for checksum calculation details and http://tarkistusmerkit.teppovuori.fi/tarkmerk.htm#hetu1 for historical details. >>> validate('131052-308T') '131052-308T' >>> validate('131052-308U') Traceback (most recent call last): ... InvalidChecksum: ... >>> validate('310252-308Y') Traceback (most recent call last): ... InvalidComponent: ... >>> compact('131052a308t') '131052A308T' """ import re import datetime from stdnum.exceptions import * from stdnum.util import clean _century_codes = { '+': 1800, '-': 1900, 'A': 2000, } # Finnish personal identity codes are composed of date part, century # indicating sign, individual number and control character. # ddmmyyciiiC _hetu_re = re.compile(r'^(?P[0123]\d)(?P[01]\d)(?P\d\d)' r'(?P[-+A])(?P\d\d\d)' r'(?P[0-9ABCDEFHJKLMNPRSTUVWXY])$') def compact(number): """Convert the HETU to the minimal representation. This strips surrounding whitespace and converts it to upper case.""" return clean(number, '').upper().strip() def _calc_checksum(number): return '0123456789ABCDEFHJKLMNPRSTUVWXY'[int(number) % 31] def validate(number): """Checks to see if the number provided is a valid HETU. It checks the format, whether a valid date is given and whether the check digit is correct.""" number = compact(number) match = _hetu_re.search(number) if not match: raise InvalidFormat() day = int(match.group('day')) month = int(match.group('month')) year = int(match.group('year')) century = _century_codes[match.group('century')] individual = int(match.group('individual')) # check if birth date is valid try: datetime.date(century + year, month, day) except ValueError: raise InvalidComponent() # for historical reasons individual IDs start from 002 if individual < 2: raise InvalidComponent() checkable_number = '%02d%02d%02d%03d' % (day, month, year, individual) if match.group('control') != _calc_checksum(checkable_number): raise InvalidChecksum() return number def is_valid(number): """Checks to see if the number provided is a valid HETU. It checks the format, whether a valid date is given and whether the check digit is correct.""" try: return bool(validate(number)) except ValidationError: return False # This is here just for completeness as there are no different length forms # of Finnish personal identity codes: format = compact python-stdnum-0.9/stdnum/fi/__init__.py0000644000000000000000000000164011720140724020171 0ustar rootroot00000000000000# __init__.py - collection of Finnish numbers # coding: utf-8 # # Copyright (C) 2012 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of Finnish numbers.""" # provide vat as an alias from stdnum.fi import alv as vat python-stdnum-0.9/stdnum/fi/alv.py0000644000000000000000000000433012154624370017221 0ustar rootroot00000000000000# vat.py - functions for handling Finnish VAT numbers # coding: utf-8 # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """ALV nro (Arvonlisäveronumero, Finnish VAT number). The number is an 8-digit code with a weighted checksum. >>> validate('FI 20774740') '20774740' >>> validate('FI 20774741') # invalid check digit Traceback (most recent call last): ... InvalidChecksum: ... """ from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, ' -').upper().strip() if number.startswith('FI'): number = number[2:] return number def checksum(number): """Calculate the checksum.""" weights = (7, 9, 10, 5, 8, 4, 2, 1) return sum(weights[i] * int(n) for i, n in enumerate(number)) % 11 def validate(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" number = compact(number) if not number.isdigit(): raise InvalidFormat() if len(number) != 8: raise InvalidLength() if checksum(number) != 0: raise InvalidChecksum() return number def is_valid(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/util.py0000644000000000000000000001421412260533040017007 0ustar rootroot00000000000000# util.py - common utility functions # coding: utf-8 # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Common utility functions for other stdnum modules. This module is meant for internal use by stdnum modules and is not guaranteed to remain stable and as such not part of the public API of stdnum. """ import pkgutil import pydoc import re import sys import unicodedata from stdnum.exceptions import * _strip_doctest_re = re.compile('^>>> .*\Z', re.DOTALL | re.MULTILINE) def _mk_char_map(mapping): """Transform a dictionary with comma separated uniode chracter names to tuples with unicode characters as key.""" for key, value in mapping.items(): for char in key.split(','): try: yield (unicodedata.lookup(char), value) except KeyError: # pragma: no cover (does not happen on Python3) pass # build mapping of Unicode characters to equivalent ASCII characters _char_map = dict(_mk_char_map({ 'HYPHEN-MINUS,ARMENIAN HYPHEN,HEBREW PUNCTUATION MAQAF,HYPHEN,' 'NON-BREAKING HYPHEN,FIGURE DASH,EN DASH,EM DASH,HORIZONTAL BAR,' 'SMALL HYPHEN-MINUS,FULLWIDTH HYPHEN-MINUS,MONGOLIAN NIRUGU,OVERLINE,' 'HYPHEN BULLET,MACRON,MODIFIER LETTER MINUS SIGN,FULLWIDTH MACRON,' 'OGHAM SPACE MARK,SUPERSCRIPT MINUS,SUBSCRIPT MINUS,MINUS SIGN,' 'HORIZONTAL LINE EXTENSION,HORIZONTAL SCAN LINE-1,HORIZONTAL SCAN LINE-3,' 'HORIZONTAL SCAN LINE-7,HORIZONTAL SCAN LINE-9,STRAIGHTNESS': '-', 'ASTERISK,ARABIC FIVE POINTED STAR,SYRIAC HARKLEAN ASTERISCUS,' 'FLOWER PUNCTUATION MARK,VAI FULL STOP,SMALL ASTERISK,FULLWIDTH ASTERISK,' 'ASTERISK OPERATOR,STAR OPERATOR,HEAVY ASTERISK,LOW ASTERISK,' 'OPEN CENTRE ASTERISK,EIGHT SPOKED ASTERISK,SIXTEEN POINTED ASTERISK,' 'TEARDROP-SPOKED ASTERISK,OPEN CENTRE TEARDROP-SPOKED ASTERISK,' 'HEAVY TEARDROP-SPOKED ASTERISK,EIGHT TEARDROP-SPOKED PROPELLER ASTERISK,' 'HEAVY EIGHT TEARDROP-SPOKED PROPELLER ASTERISK,' 'ARABIC FIVE POINTED STAR': '*', 'COMMA,ARABIC COMMA,SINGLE LOW-9 QUOTATION MARK,IDEOGRAPHIC COMMA,' 'ARABIC DECIMAL SEPARATOR,ARABIC THOUSANDS SEPARATOR,PRIME,RAISED COMMA,' 'PRESENTATION FORM FOR VERTICAL COMMA,SMALL COMMA,' 'SMALL IDEOGRAPHIC COMMA,FULLWIDTH COMMA,CEDILLA': ',', 'FULL STOP,MIDDLE DOT,GREEK ANO TELEIA,ARABIC FULL STOP,' 'IDEOGRAPHIC FULL STOP,SYRIAC SUPRALINEAR FULL STOP,' 'SYRIAC SUBLINEAR FULL STOP,SAMARITAN PUNCTUATION NEQUDAA,' 'TIBETAN MARK INTERSYLLABIC TSHEG,TIBETAN MARK DELIMITER TSHEG BSTAR,' 'RUNIC SINGLE PUNCTUATION,BULLET,ONE DOT LEADER,HYPHENATION POINT,' 'WORD SEPARATOR MIDDLE DOT,RAISED DOT,KATAKANA MIDDLE DOT,' 'SMALL FULL STOP,FULLWIDTH FULL STOP,HALFWIDTH KATAKANA MIDDLE DOT,' 'AEGEAN WORD SEPARATOR DOT,PHOENICIAN WORD SEPARATOR,' 'KHAROSHTHI PUNCTUATION DOT,DOT ABOVE,ARABIC SYMBOL DOT ABOVE,' 'ARABIC SYMBOL DOT BELOW,BULLET OPERATOR,DOT OPERATOR': '.', 'SOLIDUS,SAMARITAN PUNCTUATION ARKAANU,FULLWIDTH SOLIDUS,DIVISION SLASH,' 'MATHEMATICAL RISING DIAGONAL,BIG SOLIDUS,FRACTION SLASH': '/', 'COLON,ETHIOPIC WORDSPACE,RUNIC MULTIPLE PUNCTUATION,MONGOLIAN COLON,' 'PRESENTATION FORM FOR VERTICAL COLON,FULLWIDTH COLON,' 'PRESENTATION FORM FOR VERTICAL TWO DOT LEADER,SMALL COLON': ':', 'SPACE,NO-BREAK SPACE,EN QUAD,EM QUAD,EN SPACE,EM SPACE,' 'THREE-PER-EM SPACE,FOUR-PER-EM SPACE,SIX-PER-EM SPACE,FIGURE SPACE,' 'PUNCTUATION SPACE,THIN SPACE,HAIR SPACE,NARROW NO-BREAK SPACE,' 'MEDIUM MATHEMATICAL SPACE,IDEOGRAPHIC SPACE': ' ', })) def _clean_chars(number): """Replace various Unicode characters with their ASCII counterpart.""" return ''.join(_char_map.get(x, x) for x in number) def clean(number, deletechars=''): """Remove the specified characters from the supplied number. >>> clean('123-456:78 9', ' -:') '123456789' >>> clean('1–2—3―4') '1-2-3-4' """ try: number = ''.join(x for x in number) except: raise InvalidFormat() if sys.version < '3' and isinstance(number, str): # pragma: no cover (Python 2/3 specific code) try: number = _clean_chars(number.decode()).encode() except UnicodeError: try: number = _clean_chars(number.decode('utf-8')).encode('utf-8') except UnicodeError: pass else: # pragma: no cover (Python 2/3 specific code) number = _clean_chars(number) return ''.join(x for x in number if x not in deletechars) def get_number_modules(base='stdnum'): """Yield all the module and package names under the specified module.""" __import__(base) module = sys.modules[base] for loader, name, is_pkg in pkgutil.walk_packages( module.__path__, module.__name__ + '.', onerror=lambda x: None ): __import__(name) module = sys.modules[name] if hasattr(module, 'validate'): yield module def get_module_name(module): """Return the short description of the number.""" return pydoc.splitdoc(pydoc.getdoc(module))[0].strip('.') def get_module_description(module): """Return a description of the number.""" doc = pydoc.splitdoc(pydoc.getdoc(module))[1] # remove the doctests return _strip_doctest_re.sub('', doc[1]).strip(), def get_module_list(): for module in get_number_modules(): yield ' * %s: %s' % ( module.__name__.replace('stdnum.', ''), get_module_name(module), ) python-stdnum-0.9/stdnum/pt/0000755000000000000000000000000012260536561016114 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/pt/__init__.py0000644000000000000000000000164611720140726020226 0ustar rootroot00000000000000# __init__.py - collection of Portuguese numbers # coding: utf-8 # # Copyright (C) 2012 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of Portuguese numbers.""" # provide vat as an alias from stdnum.pt import nif as vat python-stdnum-0.9/stdnum/pt/nif.py0000644000000000000000000000467712154624371017257 0ustar rootroot00000000000000# nif.py - functions for handling Portuguese VAT numbers # coding: utf-8 # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """NIF (Número de identificação fiscal, Portuguese VAT number). The NIF (Número de identificação fiscal, NIPC, Número de Identificação de Pessoa Colectiva) is used for VAT purposes. It is a 9-digit number with a simple checksum. >>> validate('PT 501 964 843') '501964843' >>> validate('PT 501 964 842') # invalid check digits Traceback (most recent call last): ... InvalidChecksum: ... """ from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, ' -.').upper().strip() if number.startswith('PT'): number = number[2:] return number def calc_check_digit(number): """Calculate the check digit. The number passed should not have the check digit included.""" return str((11 - sum((9 - i) * int(n) for i, n in enumerate(number)) ) % 11 % 10) def validate(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" number = compact(number) if not number.isdigit() or number[0] == '0': raise InvalidFormat() if len(number) != 9: raise InvalidLength() if calc_check_digit(number[:-1]) != number[-1]: raise InvalidChecksum() return number def is_valid(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/iso7064/0000755000000000000000000000000012260536561016604 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/iso7064/mod_37_2.py0000644000000000000000000000475312154624370020476 0ustar rootroot00000000000000# mod_37_2.py - functions for performing the ISO 7064 Mod 37, 2 algorithm # # Copyright (C) 2010, 2011, 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """The ISO 7064 Mod 37, 2 algorithm. The Mod 37, 2 checksum can be used for alphanumeric numbers and the check digit may also be numeric, a letter or '*'. >>> calc_check_digit('G123489654321') 'Y' >>> validate('G123489654321Y') 'G123489654321Y' >>> checksum('G123489654321Y') 1 By changing the alphabet this can be turned into any Mod x, 2 algorithm. For example Mod 11, 2: >>> calc_check_digit('079', alphabet='0123456789X') 'X' >>> validate('079X', alphabet='0123456789X') '079X' >>> checksum('079X', alphabet='0123456789X') 1 """ from stdnum.exceptions import * def checksum(number, alphabet='0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ*'): """Calculate the checksum. A valid number should have a checksum of 1.""" modulus = len(alphabet) check = 0 for n in number: check = (2 * check + alphabet.index(n)) % modulus return check def calc_check_digit(number, alphabet='0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ*'): """With the provided number, calculate the extra digit that should be appended to make it a valid number.""" modulus = len(alphabet) return alphabet[(1 - 2 * checksum(number, alphabet)) % modulus] def validate(number, alphabet='0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ*'): """Checks whether the check digit is valid.""" try: valid = checksum(number, alphabet) == 1 except: raise InvalidFormat() if not valid: raise InvalidChecksum() return number def is_valid(number, alphabet='0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ*'): """Checks whether the check digit is valid.""" try: return bool(validate(number, alphabet)) except ValidationError: return False python-stdnum-0.9/stdnum/iso7064/mod_37_36.py0000644000000000000000000000504112154624370020554 0ustar rootroot00000000000000# mod_37_36.py - functions for performing the ISO 7064 Mod 37, 36 algorithm # # Copyright (C) 2010, 2011, 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """The ISO 7064 Mod 37, 36 algorithm. The Mod 37, 36 algorithm uses an alphanumeric check digit and the number itself may also contain letters. >>> checksum('A12425GABC1234002M') 1 >>> calc_check_digit('A12425GABC1234002') 'M' >>> validate('A12425GABC1234002M') 'A12425GABC1234002M' By changing the alphabet this can be turned into any Mod x+1, x algorithm. For example Mod 11, 10: >>> calc_check_digit('00200667308', alphabet='0123456789') '5' >>> validate('002006673085', alphabet='0123456789') '002006673085' """ from stdnum.exceptions import * def checksum(number, alphabet='0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ'): """Calculate the checksum. A valid number should have a checksum of 1.""" modulus = len(alphabet) check = modulus // 2 for n in number: check = (((check or modulus) * 2) % (modulus + 1) + alphabet.index(n)) % modulus return check def calc_check_digit(number, alphabet='0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ'): """With the provided number, calculate the extra digit that should be appended to make it a valid number.""" modulus = len(alphabet) return alphabet[(1 - ((checksum(number, alphabet) or modulus) * 2) % (modulus + 1)) % modulus] def validate(number, alphabet='0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ'): """Checks whether the check digit is valid.""" try: valid = checksum(number, alphabet) == 1 except: raise InvalidFormat() if not valid: raise InvalidChecksum() return number def is_valid(number, alphabet='0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ'): """Checks whether the check digit is valid.""" try: return bool(validate(number, alphabet)) except ValidationError: return False python-stdnum-0.9/stdnum/iso7064/__init__.py0000644000000000000000000000252312141257173020714 0ustar rootroot00000000000000# __init__.py - functions for performing the ISO 7064 algorithms # # Copyright (C) 2010, 2012 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of the ISO 7064 algorithms. This package provides a number of modules for calculation and verification of numbers using one of the ISO 7064 algorithms. Note that these functions were not implemented using the ISO text itself because the text is not available for free. These functions were implemented based on information on the algorithms found online and some reverse engineering. If anyone can provide a legal copy of the ISO/IEC 7064 standard these functions can be validated and perhaps improved. """ python-stdnum-0.9/stdnum/iso7064/mod_11_10.py0000644000000000000000000000410712154624370020536 0ustar rootroot00000000000000# mod_11_10.py - functions for performing the ISO 7064 Mod 11, 10 algorithm # # Copyright (C) 2010, 2011, 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """The ISO 7064 Mod 11, 10 algorithm. The Mod 11, 10 algorithm uses a number of calculations modulo 11 and 10 to determine a checksum. For a module that can do generic Mod x+1, x calculations see the :mod:`stdnum.iso7064.mod_37_36` module. >>> calc_check_digit('79462') '3' >>> validate('794623') '794623' >>> calc_check_digit('00200667308') '5' >>> validate('002006673085') '002006673085' """ from stdnum.exceptions import * def checksum(number): """Calculate the checksum. A valid number should have a checksum of 1.""" check = 5 for n in number: check = (((check or 10) * 2) % 11 + int(n)) % 10 return check def calc_check_digit(number): """With the provided number, calculate the extra digit that should be appended to make it a valid number.""" return str((1 - ((checksum(number) or 10) * 2) % 11) % 10) def validate(number): """Checks whether the check digit is valid.""" try: valid = checksum(number) == 1 except: raise InvalidFormat() if not valid: raise InvalidChecksum() return number def is_valid(number): """Checks whether the check digit is valid.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/iso7064/mod_97_10.py0000644000000000000000000000407612154624371020562 0ustar rootroot00000000000000# mod_97_10.py - functions for performing the ISO 7064 Mod 97, 10 algorithm # # Copyright (C) 2010, 2011, 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """The ISO 7064 Mod 97, 10 algorithm. The Mod 97, 10 algorithm evaluates the whole number as an integer which is valid if the number modulo 97 is 1. As such it has two check digits. >>> calc_check_digits('99991234567890121414') '90' >>> validate('9999123456789012141490') '9999123456789012141490' >>> calc_check_digits('4354111611551114') '31' >>> validate('08686001256515001121751') '08686001256515001121751' >>> calc_check_digits('22181321402534321446701611') '35' """ from stdnum.exceptions import * def checksum(number): """Calculate the checksum. A valid number should have a checksum of 1.""" return int(number) % 97 def calc_check_digits(number): """With the provided number, calculate the extra digits that should be appended to make it a valid number.""" return '%02d' % ((98 - 100 * checksum(number)) % 97) def validate(number): """Checks whether the check digit is valid.""" try: valid = checksum(number) == 1 except: raise InvalidFormat() if not valid: raise InvalidChecksum() return number def is_valid(number): """Checks whether the check digit is valid.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/iso7064/mod_11_2.py0000644000000000000000000000414312154624370020457 0ustar rootroot00000000000000# mod_11_2.py - functions for performing the ISO 7064 Mod 11, 2 algorithm # # Copyright (C) 2010, 2011, 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """The ISO 7064 Mod 11, 2 algorithm. The Mod 11, 2 algorithm is a simple module 11 checksum where the check digit can be an X to make the number valid. For a module that can do generic Mod x, 2 calculations see the :mod:`stdnum.iso7064.mod_37_2` module. >>> calc_check_digit('0794') '0' >>> validate('07940') '07940' >>> calc_check_digit('079') 'X' >>> validate('079X') '079X' >>> checksum('079X') 1 """ from stdnum.exceptions import * def checksum(number): """Calculate the checksum. A valid number should have a checksum of 1.""" check = 0 for n in number: check = (2 * check + int(10 if n == 'X' else n)) % 11 return check def calc_check_digit(number): """With the provided number, calculate the extra digit that should be appended to make it a valid number.""" c = (1 - 2 * checksum(number)) % 11 return 'X' if c == 10 else str(c) def validate(number): """Checks whether the check digit is valid.""" try: valid = checksum(number) == 1 except: raise InvalidFormat() if not valid: raise InvalidChecksum() return number def is_valid(number): """Checks whether the check digit is valid.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/br/0000755000000000000000000000000012260536561016074 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/br/__init__.py0000644000000000000000000000155211720140725020201 0ustar rootroot00000000000000# __init__.py - collection of Brazillian numbers # coding: utf-8 # # Copyright (C) 2012 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of Brazillian numbers.""" python-stdnum-0.9/stdnum/br/cpf.py0000644000000000000000000000513212154624370017215 0ustar rootroot00000000000000# cpf.py - functions for handling CPF numbers # coding: utf-8 # # Copyright (C) 2011, 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """CPF (Cadastro de Pessoas Físicas, Brazillian national identifier). >>> validate('390.533.447-05') '39053344705' >>> validate('231.002.999-00') Traceback (most recent call last): ... InvalidChecksum: ... >>> validate('390.533.447=0') # invalid delimiter Traceback (most recent call last): ... InvalidFormat: ... >>> format('23100299900') '231.002.999-00' """ from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" return clean(number, ' -.').strip() def _calc_check_digits(number): """Calculate the check digits for the number.""" d1 = sum((10 - i) * int(number[i]) for i in range(9)) d1 = (11 - d1) % 11 % 10 d2 = sum((11 - i) * int(number[i]) for i in range(9)) + 2 * d1 d2 = (11 - d2) % 11 % 10 return '%d%d' % (d1, d2) def validate(number): """Checks to see if the number provided is a valid CPF. This checks the length and whether the check digit is correct.""" number = compact(number) if not number.isdigit() or int(number) <= 0: raise InvalidFormat() if len(number) != 11: raise InvalidLength() if _calc_check_digits(number) != number[-2:]: raise InvalidChecksum() return number def is_valid(number): """Checks to see if the number provided is a valid CPF. This checks the length and whether the check digit is correct.""" try: return bool(validate(number)) except ValidationError: return False def format(number): """Reformat the passed number to the standard format.""" number = compact(number) return number[:3] + '.' + number[3:6] + '.' + number[6:-2] + '-' + number[-2:] python-stdnum-0.9/stdnum/eu/0000755000000000000000000000000012260536561016102 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/eu/__init__.py0000644000000000000000000000156211720140716020210 0ustar rootroot00000000000000# __init__.py - collection of European Union numbers # coding: utf-8 # # Copyright (C) 2012 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of European Union numbers.""" python-stdnum-0.9/stdnum/eu/vat.py0000644000000000000000000001110512260400322017225 0ustar rootroot00000000000000# vat.py - functions for handling European VAT numbers # coding: utf-8 # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """VAT (European Union VAT number). The European Union VAT number consists of a 2 letter country code (ISO 3166-1, except Greece which uses EL) followed by a number that is allocated per country. The exact format of the numbers varies per country and a country-specific check is performed on the number using the VAT module that is relevant for that country. >>> compact('ATU 57194903') 'ATU57194903' >>> validate('BE697449992') 'BE0697449992' >>> validate('FR 61 954 506 077') 'FR61954506077' >>> guess_country('00449544B01') ['nl'] """ from stdnum.exceptions import * from stdnum.util import clean country_codes = set([ 'at', 'be', 'bg', 'cy', 'cz', 'de', 'dk', 'ee', 'es', 'fi', 'fr', 'gb', 'gr', 'hu', 'ie', 'it', 'lt', 'lu', 'lv', 'mt', 'nl', 'pl', 'pt', 'ro', 'se', 'si', 'sk' ]) """The collection of country codes that are queried. Greece is listed with a country code of gr while for VAT purposes el is used instead.""" _country_modules = dict() vies_wsdl = 'http://ec.europa.eu/taxation_customs/vies/checkVatService.wsdl' """The WSDL URL of the VAT Information Exchange System (VIES).""" # a cached version of the suds client for VIES _vies_client = None def _get_cc_module(cc): """Get the VAT number module based on the country code.""" # Greece uses a "wrong" country code cc = cc.lower() if cc == 'el': cc = 'gr' if cc not in country_codes: return if cc not in _country_modules: # do `from stdnum.CC import vat` instead of `import stdnum.CC.vat` # to handle the case where vat is an alias _country_modules[cc] = __import__( 'stdnum.%s' % cc, globals(), locals(), ['vat']).vat return _country_modules[cc] def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, '').upper().strip() module = _get_cc_module(number[:2]) if not module: raise InvalidComponent() return number[:2] + module.compact(number[2:]) def validate(number): """Checks to see if the number provided is a valid VAT number. This performs the country-specific check for the number.""" number = clean(number, '').upper().strip() module = _get_cc_module(number[:2]) if not module: raise InvalidComponent() return number[:2] + module.validate(number[2:]) def is_valid(number): """Checks to see if the number provided is a valid VAT number. This performs the country-specific check for the number.""" try: return bool(validate(number)) except ValidationError: return False def guess_country(number): """Guess the country code based on the provided number. This checks the provided number against each of the validation routines and returns the list of countries for which it is valid. This returns lower case codes and returns gr (not el) for Greece.""" return [cc for cc in country_codes if _get_cc_module(cc).is_valid(number)] def check_vies(number): # pragma: no cover (no tests for this function) """Queries the online European Commission VAT Information Exchange System (VIES) for validity of the provided number. Note that the service has usage limitations (see the VIES website for details). This returns a dict-like object.""" # this function isn't automatically tested because it would require # network access for the tests and unnecessarily load the VIES website number = compact(number) global _vies_client if not _vies_client: from suds.client import Client from urllib import getproxies _vies_client = Client(vies_wsdl, proxy=getproxies()) return _vies_client.service.checkVat(number[:2], number[2:]) python-stdnum-0.9/stdnum/us/0000755000000000000000000000000012260536562016121 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/us/ein.py0000644000000000000000000000550712237446535017261 0ustar rootroot00000000000000# ein.py - functions for handling EINs # # Copyright (C) 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """EIN (U.S. Employer Identification Number). The Employer Identification Number, also known as Federal Employer Identification Number (FEIN), is used to identify a business entity in the United States. It is issued to anyone that has to pay withholding taxes on employees. >>> validate('91-1144442') '911144442' >>> get_campus('04-2103594') == 'Brookhaven' True >>> validate('911-14-4442') # dash in the wrong place Traceback (most recent call last): ... InvalidFormat: ... >>> validate('07-1144442') # wrong prefix Traceback (most recent call last): ... InvalidComponent: ... >>> format('042103594') '04-2103594' """ import re from stdnum.exceptions import * from stdnum.util import clean # regular expression for matching EINs _ein_re = re.compile('^(?P[0-9]{2})-?(?P[0-9]{7})$') def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" return clean(number, '-').strip() def get_campus(number): """Determine the Campus or other location that issued the EIN.""" from stdnum import numdb number = compact(number) results = numdb.get('us/ein').info(number)[0][1] if not results: raise InvalidComponent() return results['campus'] def validate(number): """Checks to see if the number provided is a valid EIN. This checks the length, groups and formatting if it is present.""" match = _ein_re.search(clean(number, '').strip()) if not match: raise InvalidFormat() get_campus(number) # raises exception for unknown campus return compact(number) def is_valid(number): """Checks to see if the number provided is a valid EIN. This checks the length, groups and formatting if it is present.""" try: return bool(validate(number)) except ValidationError: return False def format(number): """Reformat the passed number to the standard format.""" if len(number) == 9: number = number[:2] + '-' + number[2:] return number python-stdnum-0.9/stdnum/us/tin.py0000644000000000000000000000570712237446535017302 0ustar rootroot00000000000000# tin.py - functions for handling TINs # # Copyright (C) 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """TIN (U.S. Taxpayer Identification Number). The Taxpayer Identification Number is used used for tax purposes in the United States. A TIN may be: * a Social Security Number (SSN) * an Individual Taxpayer Identification Number (ITIN) * an Employer Identification Number (EIN) * a Preparer Tax Identification Number (PTIN) * an Adoption Taxpayer Identification Number (ATIN) >>> compact('123-45-6789') '123456789' >>> validate('123-45-6789') '123456789' >>> validate('07-3456789') Traceback (most recent call last): ... InvalidFormat: ... >>> guess_type('536-90-4399') ['ssn', 'atin'] >>> guess_type('04-2103594') ['ein'] >>> guess_type('042103594') ['ssn', 'ein', 'atin'] >>> format('042103594') '042-10-3594' >>> format('123-456') # invalid numbers are not reformatted '123-456' """ from stdnum.exceptions import * from stdnum.us import ssn, itin, ein, ptin, atin from stdnum.util import clean _tin_modules = (ssn, itin, ein, ptin, atin) def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" return clean(number, '-').strip() def validate(number): """Checks to see if the number provided is a valid TIN. This searches for the proper sub-type and validates using that.""" for mod in _tin_modules: try: return mod.validate(number) except ValidationError: pass # try next module # fallback raise InvalidFormat() def is_valid(number): """Checks to see if the number provided is a valid TIN. This searches for the proper sub-type and validates using that.""" try: return bool(validate(number)) except ValidationError: return False def guess_type(number): """Return a list of possible TIN types for which this number is valid..""" return [mod.__name__.rsplit('.', 1)[-1] for mod in _tin_modules if mod.is_valid(number)] def format(number): """Reformat the passed number to the standard format.""" for mod in _tin_modules: if mod.is_valid(number) and hasattr(mod, 'format'): return mod.format(number) return number python-stdnum-0.9/stdnum/us/ssn.py0000644000000000000000000000600212226053047017266 0ustar rootroot00000000000000# ssn.py - functions for handling SSNs # # Copyright (C) 2011, 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """SSN (U.S. Social Security Number). The Social Security Number is used to identify individuals for taxation purposes. >>> validate('536-90-4399') '536904399' >>> validate('1112-23333') # dash in the wrong place Traceback (most recent call last): ... InvalidFormat: ... >>> validate('666-00-0000') # invalid area Traceback (most recent call last): ... InvalidComponent: ... >>> validate('078-05-1120') # blacklisted entry Traceback (most recent call last): ... InvalidComponent: ... >>> compact('1234-56-789') '123456789' >>> format('111223333') '111-22-3333' """ import re from stdnum.exceptions import * from stdnum.util import clean # regular expression for matching SSN _ssn_re = re.compile('^(?P[0-9]{3})-?(?P[0-9]{2})-?(?P[0-9]{4})$') # blacklist of SSNs _ssn_blacklist = set(('078-05-1120', '457-55-5462', '219-09-9999')) def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" return clean(number, '-').strip() def validate(number): """Checks to see if the number provided is a valid SSN. This checks the length, groups and formatting if it is present.""" match = _ssn_re.search(clean(number, '').strip()) if not match: raise InvalidFormat() area = match.group('area') group = match.group('group') serial = match.group('serial') # check for all-0 or some unused areas # (9xx also won't be issued which includes the advertising range) if area == '000' or area == '666' or area[0] == '9' or \ group == '00' or serial == '0000': raise InvalidComponent() # check blacklists if format(number) in _ssn_blacklist: raise InvalidComponent() return compact(number) def is_valid(number): """Checks to see if the number provided is a valid SSN. This checks the length, groups and formatting if it is present.""" try: return bool(validate(number)) except ValidationError: return False def format(number): """Reformat the passed number to the standard format.""" if len(number) == 9: number = number[:3] + '-' + number[3:5] + '-' + number[5:] return number python-stdnum-0.9/stdnum/us/ein.dat0000644000000000000000000000120612237446535017371 0ustar rootroot00000000000000# manually converted from the IRS website # http://www.irs.gov/Businesses/Small-Businesses-&-Self-Employed/How-EINs-are-Assigned-and-Valid-EIN-Prefixes 01,02,03,04,05,06,11,13,14,16,21,22,23,25,34,51,52,54,55,56,57,58,59,65 campus="Brookhaven" 10,12 campus="Andover" 15,24 campus="Fresno" 20,26,27,45,46 campus="Internet" 30,32,35,36,37,38,61 campus="Cincinnati" 31 campus="Small Business Administration (SBA)" 33,39,41,42,43,46,48,62,63,64,66,68,71,72,73,74,75,76,77,81,82,83,84,85,86,87,88,91,92,93,98,99 campus="Philadelphia" 40,44 campus="Kansas City" 50,53 campus="Austin" 60,67 campus="Atlanta" 80,90 campus="Ogden" 94,95 campus="Memphis" python-stdnum-0.9/stdnum/us/ptin.py0000644000000000000000000000417012237446535017453 0ustar rootroot00000000000000# ptin.py - functions for handling PTINs # # Copyright (C) 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """PTIN (U.S. Preparer Tax Identification Number). A Preparer Tax Identification Number (PTIN) is United States identification number for tax return preparers. It is an eight-digit number prefixed with a capital P. >>> validate('P-00634642') 'P00634642' >>> validate('P01594846') 'P01594846' >>> validate('00634642') # missing P Traceback (most recent call last): ... InvalidFormat: ... """ import re from stdnum.exceptions import * from stdnum.util import clean # regular expression for matching PTINs _ptin_re = re.compile('^P[0-9]{8}$') def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" return clean(number, '-').strip() def validate(number): """Checks to see if the number provided is a valid PTIN. This checks the length, groups and formatting if it is present.""" number = compact(number).upper() if not _ptin_re.search(number): raise InvalidFormat() # sadly, no more information on PTIN number validation was found return number def is_valid(number): """Checks to see if the number provided is a valid ATIN. This checks the length, groups and formatting if it is present.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/us/__init__.py0000644000000000000000000000156011720140724020223 0ustar rootroot00000000000000# __init__.py - collection of United States numbers # coding: utf-8 # # Copyright (C) 2012 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of United States numbers.""" python-stdnum-0.9/stdnum/us/atin.py0000644000000000000000000000457412237446535017444 0ustar rootroot00000000000000# atin.py - functions for handling ATINs # # Copyright (C) 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """ATIN (U.S. Adoption Taxpayer Identification Number). An Adoption Taxpayer Identification Number (ATIN) is a temporary nine-digit number issued by the United States IRS for a child for whom the adopting parents cannot obtain a Social Security Number. >>> validate('123-45-6789') '123456789' >>> validate('1234-56789') # dash in the wrong place Traceback (most recent call last): ... InvalidFormat: ... >>> format('123456789') '123-45-6789' """ import re from stdnum.exceptions import * from stdnum.util import clean # regular expression for matching ATINs _atin_re = re.compile('^[0-9]{3}-?[0-9]{2}-?[0-9]{4}$') def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" return clean(number, '-').strip() def validate(number): """Checks to see if the number provided is a valid ATIN. This checks the length and formatting if it is present.""" match = _atin_re.search(clean(number, '').strip()) if not match: raise InvalidFormat() # sadly, no more information on ATIN number validation was found return compact(number) def is_valid(number): """Checks to see if the number provided is a valid ATIN. This checks the length and formatting if it is present.""" try: return bool(validate(number)) except ValidationError: return False def format(number): """Reformat the passed number to the standard format.""" if len(number) == 9: number = number[:3] + '-' + number[3:5] + '-' + number[5:] return number python-stdnum-0.9/stdnum/us/itin.py0000644000000000000000000000576112237446535017453 0ustar rootroot00000000000000# itin.py - functions for handling ITINs # # Copyright (C) 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """ITIN (U.S. Individual Taxpayer Identification Number). The Individual Taxpayer Identification Number is issued by the United States IRS to individuals who are required to have a taxpayer identification number but who are not eligible to obtain a Social Security Number. It is a nine-digit number that begins with the number 9 and the fourth and fifth digit are expected to be in a certain range. >>> validate('912-90-3456') '912903456' >>> validate('9129-03456') # dash in the wrong place Traceback (most recent call last): ... InvalidFormat: ... >>> validate('123-45-6789') # wrong start digit Traceback (most recent call last): ... InvalidComponent: ... >>> validate('912-93-4567') # wrong group Traceback (most recent call last): ... InvalidComponent: ... >>> compact('1234-56-789') '123456789' >>> format('111223333') '111-22-3333' """ import re from stdnum.exceptions import * from stdnum.util import clean # regular expression for matching ITINs _itin_re = re.compile('^(?P[0-9]{3})-?(?P[0-9]{2})-?[0-9]{4}$') # allowed group digits _allowed_groups = set((str(x) for x in range(70, 100) if x not in (89, 93))) def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" return clean(number, '-').strip() def validate(number): """Checks to see if the number provided is a valid ITIN. This checks the length, groups and formatting if it is present.""" match = _itin_re.search(clean(number, '').strip()) if not match: raise InvalidFormat() area = match.group('area') group = match.group('group') if area[0] != '9' or group not in _allowed_groups: raise InvalidComponent() return compact(number) def is_valid(number): """Checks to see if the number provided is a valid ITIN. This checks the length, groups and formatting if it is present.""" try: return bool(validate(number)) except ValidationError: return False def format(number): """Reformat the passed number to the standard format.""" if len(number) == 9: number = number[:3] + '-' + number[3:5] + '-' + number[5:] return number python-stdnum-0.9/stdnum/grid.py0000644000000000000000000000466012154624370016774 0ustar rootroot00000000000000# grid.py - functions for handling Global Release Identifier (GRid) numbers # # Copyright (C) 2010, 2011, 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """GRid (Global Release Identifier). The Global Release Identifier is used to identify releases of digital sound recordings and uses the ISO 7064 Mod 37, 36 algorithm to verify the correctness of the number. >>> validate('A12425GABC1234002M') 'A12425GABC1234002M' >>> validate('Grid: A1-2425G-ABC1234002-M') 'A12425GABC1234002M' >>> validate('A1-2425G-ABC1234002-Q') # incorrect check digit Traceback (most recent call last): ... InvalidChecksum: ... >>> compact('A1-2425G-ABC1234002-M') 'A12425GABC1234002M' >>> format('A12425GABC1234002M') 'A1-2425G-ABC1234002-M' """ from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the GRid to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, ' -').strip().upper() if number.startswith('GRID:'): number = number[5:] return number def validate(number): """Checks to see if the number provided is a valid GRid.""" from stdnum.iso7064 import mod_37_36 number = compact(number) if len(number) != 18: raise InvalidLength() return mod_37_36.validate(number) def is_valid(number): """Checks to see if the number provided is a valid GRid.""" try: return bool(validate(number)) except ValidationError: return False def format(number, separator='-'): """Reformat the passed number to the standard format.""" number = compact(number) number = (number[0:2], number[2:7], number[7:17], number[17:]) return separator.join(x for x in number if x) python-stdnum-0.9/stdnum/pl/0000755000000000000000000000000012260536561016104 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/pl/nip.py0000644000000000000000000000476612154624371017260 0ustar rootroot00000000000000# nip.py - functions for handling Polish VAT numbers # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """NIP (Numer Identyfikacji Podatkowej, Polish VAT number). The NIP (Numer Identyfikacji Podatkowej) number consists of 10 digit with a straightforward weighted checksum. >>> validate('PL 8567346215') '8567346215' >>> validate('PL 8567346216') # invalid check digits Traceback (most recent call last): ... InvalidChecksum: ... >>> format('PL 8567346215') '856-734-62-15' """ from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, ' -').upper().strip() if number.startswith('PL'): number = number[2:] return number def checksum(number): """Calculate the checksum.""" weights = (6, 5, 7, 2, 3, 4, 5, 6, 7, -1) return sum(weights[i] * int(n) for i, n in enumerate(number)) % 11 def validate(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" number = compact(number) if not number.isdigit(): raise InvalidFormat() if len(number) != 10: raise InvalidLength() if checksum(number) != 0: raise InvalidChecksum() return number def is_valid(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False def format(number): """Reformat the passed number to the standard format.""" number = compact(number) return '-'.join((number[0:3], number[3:6], number[6:8], number[8:])) python-stdnum-0.9/stdnum/pl/__init__.py0000644000000000000000000000163611720140725020214 0ustar rootroot00000000000000# __init__.py - collection of Polish numbers # coding: utf-8 # # Copyright (C) 2012 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of Polish numbers.""" # provide vat as an alias from stdnum.pl import nip as vat python-stdnum-0.9/stdnum/isbn.py0000644000000000000000000001443712154624370017005 0ustar rootroot00000000000000# isbn.py - functions for handling ISBNs # # Copyright (C) 2010, 2011, 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """ISBN (International Standard Book Number). The ISBN is the International Standard Book Number, used to identify publications. This module supports both numbers in ISBN-10 (10-digit) and ISBN-13 (13-digit) format. >>> validate('978-9024538270') '9789024538270' >>> validate('978-9024538271') Traceback (most recent call last): ... InvalidChecksum: ... >>> compact('1-85798-218-5') '1857982185' >>> format('9780471117094') '978-0-471-11709-4' >>> format('1857982185') '1-85798-218-5' >>> isbn_type('1-85798-218-5') 'ISBN10' >>> isbn_type('978-0-471-11709-4') 'ISBN13' >>> to_isbn13('1-85798-218-5') '978-1-85798-218-3' >>> to_isbn10('978-1-85798-218-3') '1-85798-218-5' """ from stdnum import ean from stdnum.exceptions import * from stdnum.util import clean def compact(number, convert=False): """Convert the ISBN to the minimal representation. This strips the number of any valid ISBN separators and removes surrounding whitespace. If the covert parameter is True the number is also converted to ISBN-13 format.""" number = clean(number, ' -').strip().upper() if len(number) == 9: number = '0' + number if convert: return to_isbn13(number) return number def _calc_isbn10_check_digit(number): """Calculate the ISBN check digit for 10-digit numbers. The number passed should not have the check bit included.""" check = sum((i + 1) * int(n) for i, n in enumerate(number)) % 11 return 'X' if check == 10 else str(check) def validate(number, convert=False): """Checks to see if the number provided is a valid ISBN (either a legacy 10-digit one or a 13-digit one). This checks the length and the check bit but does not check if the group and publisher are valid (use split() for that).""" number = compact(number, convert=False) if not number[:-1].isdigit(): raise InvalidFormat() if len(number) == 10: if _calc_isbn10_check_digit(number[:-1]) != number[-1]: raise InvalidChecksum() elif len(number) == 13: ean.validate(number) else: raise InvalidLength() if convert: number = to_isbn13(number) return number def isbn_type(number): """Check the passed number and returns 'ISBN13', 'ISBN10' or None (for invalid) for checking the type of number passed.""" try: number = validate(number, convert=False) except ValidationError: return None if len(number) == 10: return 'ISBN10' elif len(number) == 13: return 'ISBN13' def is_valid(number): """Checks to see if the number provided is a valid ISBN (either a legacy 10-digit one or a 13-digit one). This checks the length and the check bit but does not check if the group and publisher are valid (use split() for that).""" try: return bool(validate(number)) except ValidationError: return False def to_isbn13(number): """Convert the number to ISBN-13 format.""" number = number.strip() min_number = compact(number, convert=False) if len(min_number) == 13: return number # nothing to do, already ISBN-13 # put new check digit in place number = number[:-1] + ean.calc_check_digit('978' + min_number[:-1]) # add prefix if ' ' in number: return '978 ' + number elif '-' in number: return '978-' + number else: return '978' + number def to_isbn10(number): """Convert the number to ISBN-10 format.""" number = number.strip() min_number = compact(number, convert=False) if len(min_number) == 10: return number # nothing to do, already ISBN-13 elif isbn_type(min_number) != 'ISBN13': raise InvalidFormat('Not a valid ISBN13.') elif not number.startswith('978'): raise InvalidFormat('Does not use 978 Bookland prefix.') # strip EAN prefix number = number[3:-1].strip().strip('-') digit = _calc_isbn10_check_digit(min_number[3:-1]) # append the new check digit if ' ' in number: return number + ' ' + digit elif '-' in number: return number + '-' + digit else: return number + digit def split(number, convert=False): """Split the specified ISBN into an EAN.UCC prefix, a group prefix, a registrant, an item number and a check-digit. If the number is in ISBN-10 format the returned EAN.UCC prefix is '978'. If the covert parameter is True the number is converted to ISBN-13 format first.""" from stdnum import numdb # clean up number number = compact(number, convert) # get Bookland prefix if any delprefix = False if len(number) == 10: number = '978' + number delprefix = True # split the number result = numdb.get('isbn').split(number[:-1]) itemnr = result.pop() if result else '' prefix = result.pop(0) if result else '' group = result.pop(0) if result else '' publisher = result.pop(0) if result else '' # return results return ('' if delprefix else prefix, group, publisher, itemnr, number[-1]) def format(number, separator='-', convert=False): """Reformat the passed number to the standard format with the EAN.UCC prefix (if any), the group prefix, the registrant, the item number and the check-digit separated (if possible) by the specified separator. Passing an empty separator should equal compact() though this is less efficient. If the covert parameter is True the number is converted to ISBN-13 format first.""" return separator.join(x for x in split(number, convert) if x) python-stdnum-0.9/stdnum/imsi.py0000644000000000000000000000567612154624370017020 0ustar rootroot00000000000000# imsi.py - functions for handling International Mobile Subscriber Identity # (IMSI) numbers # # Copyright (C) 2011, 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """IMSI (International Mobile Subscriber Identity). The IMSI (International Mobile Subscriber Identity) is used to identify mobile phone users (the SIM). >>> validate('429011234567890') '429011234567890' >>> validate('439011234567890') # unknown MCC Traceback (most recent call last): ... InvalidFormat: ... >>> split('429011234567890') ('429', '01', '1234567890') >>> split('310150123456789') ('310', '150', '123456789') >>> info('460001234567890')['mcc'] '460' >>> str(info('460001234567890')['country']) 'China' """ from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the IMSI number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" return clean(number, ' -').strip().upper() def split(number): """Split the specified IMSI into a Mobile Country Code (MCC), a Mobile Network Code (MNC), a Mobile Station Identification Number (MSIN).""" from stdnum import numdb # clean up number number = compact(number) # split the number return tuple(numdb.get('imsi').split(number)) def validate(number): """Checks to see if the number provided is a valid IMSI.""" number = compact(number) if not number.isdigit(): raise InvalidFormat() if len(number) not in (14, 15): raise InvalidLength() if len(split(number)) != 3: raise InvalidFormat() return number def info(number): """Return a dictionary of data about the supplied number.""" from stdnum import numdb # clean up number number = compact(number) # split the number info = dict(number=number) mcc_info, mnc_info, msin_info = numdb.get('imsi').info(number) info['mcc'] = mcc_info[0] info.update(mcc_info[1]) info['mnc'] = mnc_info[0] info.update(mnc_info[1]) info['msin'] = msin_info[0] info.update(msin_info[1]) return info def is_valid(number): """Checks to see if the number provided is a valid IMSI.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/ean.py0000644000000000000000000000462312154624370016611 0ustar rootroot00000000000000# ean.py - functions for handling EANs # # Copyright (C) 2011, 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """EAN (International Article Number). Module for handling EAN (International Article Number) codes. This module handles numbers EAN-13, EAN-8 and UPC (12-digit) format. >>> validate('73513537') '73513537' >>> validate('978-0-471-11709-4') # EAN-13 format '9780471117094' """ from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the EAN to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" return clean(number, ' -').strip() def calc_check_digit(number): """Calculate the EAN check digit for 13-digit numbers. The number passed should not have the check bit included.""" return str((10 - sum((3 - 2 * (i % 2)) * int(n) for i, n in enumerate(reversed(number)))) % 10) def validate(number): """Checks to see if the number provided is a valid EAN-13. This checks the length and the check bit but does not check whether a known GS1 Prefix and company identifier are referenced.""" number = compact(number) if not number.isdigit(): raise InvalidFormat() if len(number) not in (13, 12, 8): raise InvalidLength() if calc_check_digit(number[:-1]) != number[-1]: raise InvalidChecksum() return number def is_valid(number): """Checks to see if the number provided is a valid EAN-13. This checks the length and the check bit but does not check whether a known GS1 Prefix and company identifier are referenced.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/fr/0000755000000000000000000000000012260536561016100 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/fr/siren.py0000644000000000000000000000525512154624370017577 0ustar rootroot00000000000000# siren.py - functions for handling French SIREN numbers # coding: utf-8 # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """SIREN (a French company identification number). The SIREN (Système d'Identification du Répertoire des Entreprises) is a 9 digit number used to identify French companies. The Luhn checksum is used to validate the numbers. >>> compact('552 008 443') '552008443' >>> validate('404833048') '404833048' >>> validate('404833047') Traceback (most recent call last): ... InvalidChecksum: ... >>> to_tva('443 121 975') '46 443 121 975' """ from stdnum import luhn from stdnum.exceptions import * from stdnum.util import clean # An online validation function is available but it does not provide an # automated entry point, has usage restrictions and seems to require # attribution to the service for any results used. # http://avis-situation-sirene.insee.fr/ def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" return clean(number, ' ').strip() def validate(number): """Checks to see if the number provided is a valid number. This checks the length, formatting and check digit.""" number = compact(number) if not number.isdigit(): raise InvalidFormat() if len(number) != 9: raise InvalidLength() luhn.validate(number) return number def is_valid(number): """Checks to see if the number provided is a valid number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False def to_tva(number): """Return a TVA that prepends the two extra check digits to the SIREN.""" # note that this always returns numeric check digits # it is unclean when the alphabetic ones are used return '%02d%s%s' % ( int(compact(number) + '12') % 97, ' ' if ' ' in number else '', number ) python-stdnum-0.9/stdnum/fr/tva.py0000644000000000000000000000625212154624370017247 0ustar rootroot00000000000000# tva.py - functions for handling French TVA numbers # coding: utf-8 # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """n° TVA (taxe sur la valeur ajoutée, French VAT number). The n° TVA (Numéro d'identification à la taxe sur la valeur ajoutée) is the SIREN (Système d’Identification du Répertoire des Entreprises) prefixed by two digits. In old style numbers the two digits are numeric, with new style numbers at least one is a alphabetic. >>> compact('Fr 40 303 265 045') '40303265045' >>> validate('23334175221') '23334175221' >>> validate('84 323 140 391') Traceback (most recent call last): ... InvalidChecksum: ... >>> validate('K7399859412') # new-style number 'K7399859412' >>> validate('4Z123456782') # new-style number starting with digit '4Z123456782' """ from stdnum.exceptions import * from stdnum.fr import siren from stdnum.util import clean # the valid characters for the first two digits (O and I are missing) _alphabet = '0123456789ABCDEFGHJKLMNPQRSTUVWXYZ' def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, ' -.').upper().strip() if number.startswith('FR'): number = number[2:] return number def validate(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" number = compact(number) if not all(x in _alphabet for x in number[:2]): raise InvalidFormat() if len(number) != 11: raise InvalidLength() siren.validate(number[2:]) if number.isdigit(): # all-numeric digits if int(number[:2]) != (int(number[2:] + '12') % 97): raise InvalidChecksum() else: # one of the first two digits isn't a number if number[0].isdigit(): check = ( _alphabet.index(number[0]) * 24 + _alphabet.index(number[1]) - 10) else: check = ( _alphabet.index(number[0]) * 34 + _alphabet.index(number[1]) - 100) if (int(number[2:]) + 1 + check // 11) % 11 != (check % 11): raise InvalidChecksum() return number def is_valid(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/fr/__init__.py0000644000000000000000000000163611720140725020210 0ustar rootroot00000000000000# __init__.py - collection of French numbers # coding: utf-8 # # Copyright (C) 2012 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of French numbers.""" # provide vat as an alias from stdnum.fr import tva as vat python-stdnum-0.9/stdnum/sk/0000755000000000000000000000000012260536561016106 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/sk/dph.py0000644000000000000000000000475112154624371017241 0ustar rootroot00000000000000# vat.py - functions for handling Slovak VAT numbers # coding: utf-8 # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """IČ DPH (IČ pre daň z pridanej hodnoty, Slovak VAT number). The IČ DPH (Identifikačné číslo pre daň z pridanej hodnoty) is a 10-digit number used for VAT purposes. It has a straightforward checksum. >>> validate('SK 202 274 96 19') '2022749619' >>> validate('SK 202 274 96 18') # invalid check digits Traceback (most recent call last): ... InvalidChecksum: ... """ from stdnum.exceptions import * from stdnum.sk import rc from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, ' -').upper().strip() if number.startswith('SK'): number = number[2:] return number def checksum(number): """Calculate the checksum.""" return int(number) % 11 def validate(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" number = compact(number) if not number.isdigit(): raise InvalidFormat() if len(number) != 10: raise InvalidLength() # it is unclear whether the RČ can be used as a valid VAT number if rc.is_valid(number): return number if number[0] == '0' or int(number[2]) not in (2, 3, 4, 7, 8, 9): raise InvalidFormat() if checksum(number) != 0: raise InvalidChecksum() return number def is_valid(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/sk/rc.py0000644000000000000000000000355712154624371017075 0ustar rootroot00000000000000# rc.py - functions for handling Slovak birth numbers # coding: utf-8 # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """RČ (Rodné číslo, the Slovak birth number). The birth number (RČ, Rodné číslo) is the Slovak national identifier. The number can be 9 or 10 digits long. Numbers given out after January 1st 1954 should have 10 digits. The number includes the birth date of the person and their gender. This number is identical to the Czech counterpart. >>> validate('710319/2745') '7103192745' >>> validate('991231123') '991231123' >>> validate('7103192746') # invalid check digit Traceback (most recent call last): ... InvalidChecksum: ... >>> validate('1103492745') # invalid date Traceback (most recent call last): ... InvalidComponent: ... >>> validate('590312/123') # 9 digit number in 1959 Traceback (most recent call last): ... InvalidLength: ... >>> format('7103192745') '710319/2745' """ # since this number is essentially the same as the Czech counterpart # (until 1993 the Czech Republic and Slovakia were one country) from stdnum.cz.rc import compact, validate, is_valid, format __all__ = ['compact', 'validate', 'is_valid', 'format'] python-stdnum-0.9/stdnum/sk/__init__.py0000644000000000000000000000163611720140731020213 0ustar rootroot00000000000000# __init__.py - collection of Slovak numbers # coding: utf-8 # # Copyright (C) 2012 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of Slovak numbers.""" # provide vat as an alias from stdnum.sk import dph as vat python-stdnum-0.9/stdnum/lu/0000755000000000000000000000000012260536561016111 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/lu/tva.py0000644000000000000000000000452712154624371017264 0ustar rootroot00000000000000# tva.py - functions for handling Luxembourgian VAT numbers # coding: utf-8 # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """TVA (taxe sur la valeur ajoutée, Luxembourgian VAT number). The n° TVA (Numéro d'identification à la taxe sur la valeur ajoutée) is used for tax purposes in Luxembourg. The number consists of 8 digits of which the last two are check digits. >>> validate('LU 150 274 42') '15027442' >>> validate('150 274 43') # invalid check digits Traceback (most recent call last): ... InvalidChecksum: ... """ from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, ' :.-').upper().strip() if number.startswith('LU'): number = number[2:] return number def calc_check_digits(number): """Calculate the check digits for the number.""" return '%02d' % (int(number) % 89) def validate(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" number = compact(number) if not number.isdigit(): raise InvalidFormat() if len(number) != 8: raise InvalidLength() if calc_check_digits(number[:6]) != number[-2:]: raise InvalidChecksum() return number def is_valid(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/lu/__init__.py0000644000000000000000000000165411720140726020222 0ustar rootroot00000000000000# __init__.py - collection of Luxembourgian numbers # coding: utf-8 # # Copyright (C) 2012 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of Luxembourgian numbers.""" # provide vat as an alias from stdnum.lu import tva as vat python-stdnum-0.9/stdnum/it/0000755000000000000000000000000012260536561016105 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/it/iva.py0000644000000000000000000000473712154624371017250 0ustar rootroot00000000000000# iva.py - functions for handling Italian VAT numbers # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Partita IVA (Italian VAT number). The Partita IVA (Imposta sul valore aggiunto) consists of 11 digits. The first 7 digits are a company identifier, the next 3 refer to the province of residence and the last is a check digit. The fiscal code for individuals is not accepted as valid code for intracommunity VAT related operations so it is ignored here. >>> validate('IT 00743110157') '00743110157' >>> validate('00743110158') # invalid check digit Traceback (most recent call last): ... InvalidChecksum: ... """ from stdnum import luhn from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, ' -:').upper().strip() if number.startswith('IT'): number = number[2:] return number def validate(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" number = compact(number) if not number.isdigit() or int(number[0:7]) == 0: raise InvalidFormat() if len(number) != 11: raise InvalidLength() # check the province of residence if not('001' <= number[7:10] <= '100') and \ number[7:10] not in ('120', '121', '888', '999'): raise InvalidComponent() luhn.validate(number) return number def is_valid(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/it/__init__.py0000644000000000000000000000164011720140731020205 0ustar rootroot00000000000000# __init__.py - collection of Italian numbers # coding: utf-8 # # Copyright (C) 2012 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of Italian numbers.""" # provide vat as an alias from stdnum.it import iva as vat python-stdnum-0.9/stdnum/mt/0000755000000000000000000000000012260536561016111 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/mt/__init__.py0000644000000000000000000000154411720140723020215 0ustar rootroot00000000000000# __init__.py - collection of Maltese numbers # coding: utf-8 # # Copyright (C) 2012 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of Maltese numbers.""" python-stdnum-0.9/stdnum/mt/vat.py0000644000000000000000000000434412154624371017261 0ustar rootroot00000000000000# vat.py - functions for handling Maltese VAT numbers # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """VAT (Maltese VAT number). The Maltese VAT registration number contains 8 digits and uses a simple weigted checksum. >>> validate('MT 1167-9112') '11679112' >>> validate('1167-9113') # invalid check digits Traceback (most recent call last): ... InvalidChecksum: ... """ from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, ' -').upper().strip() if number.startswith('MT'): number = number[2:] return number def checksum(number): """Calculate the checksum.""" weights = (3, 4, 6, 7, 8, 9, 10, 1) return sum(weights[i] * int(n) for i, n in enumerate(number)) % 37 def validate(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" number = compact(number) if not number.isdigit() or number[0] == '0': raise InvalidFormat() if len(number) != 8: raise InvalidLength() if checksum(number) != 0: raise InvalidChecksum() return number def is_valid(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/stdnum/si/0000755000000000000000000000000012260536561016104 5ustar rootroot00000000000000python-stdnum-0.9/stdnum/si/__init__.py0000644000000000000000000000164411720140731020210 0ustar rootroot00000000000000# __init__.py - collection of Slovenian numbers # coding: utf-8 # # Copyright (C) 2012 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """Collection of Slovenian numbers.""" # provide vat as an alias from stdnum.si import ddv as vat python-stdnum-0.9/stdnum/si/ddv.py0000644000000000000000000000501612154624371017234 0ustar rootroot00000000000000# ddv.py - functions for handling Slovenian VAT numbers # coding: utf-8 # # Copyright (C) 2012, 2013 Arthur de Jong # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA # 02110-1301 USA """ID za DDV (Davčna številka, Slovenian VAT number). The DDV number (Davčna številka) is used for VAT (DDV, Davek na dodano vrednost) purposes and consist of 8 digits of which the last is a check digit. >>> validate('SI 5022 3054') '50223054' >>> validate('SI 50223055') # invalid check digits Traceback (most recent call last): ... InvalidChecksum: ... """ from stdnum.exceptions import * from stdnum.util import clean def compact(number): """Convert the number to the minimal representation. This strips the number of any valid separators and removes surrounding whitespace.""" number = clean(number, ' -').upper().strip() if number.startswith('SI'): number = number[2:] return number def calc_check_digit(number): """Calculate the check digit. The number passed should not have the check digit included.""" check = (11 - sum((8 - i) * int(n) for i, n in enumerate(number)) % 11) # this results in a two-digit check digit for 11 which should be wrong return '0' if check == 10 else str(check) def validate(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" number = compact(number) if not number.isdigit() or number.startswith('0'): raise InvalidFormat() if len(number) != 8: raise InvalidLength() if calc_check_digit(number[:-1]) != number[-1]: raise InvalidChecksum() return number def is_valid(number): """Checks to see if the number provided is a valid VAT number. This checks the length, formatting and check digit.""" try: return bool(validate(number)) except ValidationError: return False python-stdnum-0.9/python_stdnum.egg-info/0000755000000000000000000000000012260536561020564 5ustar rootroot00000000000000python-stdnum-0.9/python_stdnum.egg-info/top_level.txt0000644000000000000000000000000712260536561023313 0ustar rootroot00000000000000stdnum python-stdnum-0.9/python_stdnum.egg-info/PKG-INFO0000644000000000000000000001377312260536561021674 0ustar rootroot00000000000000Metadata-Version: 1.1 Name: python-stdnum Version: 0.9 Summary: Python module to handle standardized numbers and codes Home-page: http://arthurdejong.org/python-stdnum/ Author: Arthur de Jong Author-email: arthur@arthurdejong.org License: LGPL Description: Parse, validate and reformat standard numbers and codes. This library offers functions for parsing, validating and reformatting standard numbers and codes in various formats. Currently this package supports the following formats: * at.uid: UID (Umsatzsteuer-Identifikationsnummer, Austrian VAT number) * be.vat: BTW, TVA, NWSt (Belgian VAT number) * bg.egn: EGN (ЕГН, Единен граждански номер, Bulgarian personal identity codes) * bg.pnf: PNF (ЛНЧ, Личен номер на чужденец, Bulgarian number of a foreigner) * bg.vat: VAT (Идентификационен номер по ДДС, Bulgarian VAT number) * br.cpf: CPF (Cadastro de Pessoas Físicas, Brazillian national identifier) * cy.vat: Αριθμός Εγγραφής Φ.Π.Α. (Cypriot VAT number) * cz.dic: DIČ (Daňové identifikační číslo, Czech VAT number) * cz.rc: RČ (Rodné číslo, the Czech birth number) * de.vat: Ust ID Nr. (Umsatzsteur Identifikationnummer, German VAT number) * dk.cpr: CPR (personnummer, the Danish citizen number) * dk.cvr: CVR (Momsregistreringsnummer, Danish VAT number) * ean: EAN (International Article Number) * ee.kmkr: KMKR (Käibemaksukohuslase, Estonian VAT number) * es.cif: CIF (Certificado de Identificación Fiscal, Spanish company tax number) * es.dni: DNI (Documento nacional de identidad, Spanish personal identity codes) * es.nie: NIE (Número de Identificación de Extranjeros, Spanish foreigner number) * es.nif: NIF (Número de Identificación Fiscal, Spanish VAT number) * eu.vat: VAT (European Union VAT number) * fi.alv: ALV nro (Arvonlisäveronumero, Finnish VAT number) * fi.hetu: HETU (Henkilötunnus, Finnish personal identity code) * fr.siren: SIREN (a French company identification number) * fr.tva: n° TVA (taxe sur la valeur ajoutée, French VAT number) * gb.vat: VAT (United Kingdom (and Isle of Man) VAT registration number) * gr.vat: FPA, ΦΠΑ (Foros Prostithemenis Aksias, the Greek VAT number) * grid: GRid (Global Release Identifier) * hr.oib: OIB (Osobni identifikacijski broj, Croatian identification number) * hu.anum: ANUM (Közösségi adószám, Hungarian VAT number) * iban: IBAN (International Bank Account Number) * ie.pps: PPS No (Personal Public Service Number, Irish personal number) * ie.vat: VAT (Irish VAT number) * imei: IMEI (International Mobile Equipment Identity) * imsi: IMSI (International Mobile Subscriber Identity) * isan: ISAN (International Standard Audiovisual Number) * isbn: ISBN (International Standard Book Number) * isil: ISIL (International Standard Identifier for Libraries) * ismn: ISMN (International Standard Music Number) * issn: ISSN (International Standard Serial Number) * it.iva: Partita IVA (Italian VAT number) * lt.pvm: PVM (Pridėtinės vertės mokestis mokėtojo kodas, Lithuanian VAT number) * lu.tva: TVA (taxe sur la valeur ajoutée, Luxembourgian VAT number) * lv.pvn: PVN (Pievienotās vērtības nodokļa, Latvian VAT number) * meid: MEID (Mobile Equipment Identifier) * mt.vat: VAT (Maltese VAT number) * my.nric: NRIC No. (Malaysian National Registration Identity Card Number) * nl.brin: Brin number (Dutch number for schools) * nl.bsn: BSN (Burgerservicenummer, Dutch national identification number) * nl.btw: BTW-nummer (Omzetbelastingnummer, the Dutch VAT number) * nl.onderwijsnummer: Onderwijsnummer (Dutch student school number) * nl.postcode: Postcode (Dutch postal code) * pl.nip: NIP (Numer Identyfikacji Podatkowej, Polish VAT number) * pt.nif: NIF (Número de identificação fiscal, Portuguese VAT number) * ro.cf: CF (Cod de înregistrare în scopuri de TVA, Romanian VAT number) * ro.cnp: CNP (Cod Numeric Personal, Romanian Numerical Personal Code) * se.vat: VAT (Moms, Mervärdesskatt, Swedish VAT number) * si.ddv: ID za DDV (Davčna številka, Slovenian VAT number) * sk.dph: IČ DPH (IČ pre daň z pridanej hodnoty, Slovak VAT number) * sk.rc: RČ (Rodné číslo, the Slovak birth number) * us.atin: ATIN (U.S. Adoption Taxpayer Identification Number) * us.ein: EIN (U.S. Employer Identification Number) * us.itin: ITIN (U.S. Individual Taxpayer Identification Number) * us.ptin: PTIN (U.S. Preparer Tax Identification Number) * us.ssn: SSN (U.S. Social Security Number) * us.tin: TIN (U.S. Taxpayer Identification Number) Furthermore a number of generic check digit algorithms are available: * iso7064.mod_11_10: The ISO 7064 Mod 11, 10 algorithm * iso7064.mod_11_2: The ISO 7064 Mod 11, 2 algorithm * iso7064.mod_37_2: The ISO 7064 Mod 37, 2 algorithm * iso7064.mod_37_36: The ISO 7064 Mod 37, 36 algorithm * iso7064.mod_97_10: The ISO 7064 Mod 97, 10 algorithm * luhn: The Luhn and Luhn mod N algorithms * verhoeff: The Verhoeff algorithm Platform: UNKNOWN Classifier: Development Status :: 4 - Beta Classifier: Intended Audience :: Developers Classifier: Intended Audience :: System Administrators Classifier: License :: OSI Approved :: GNU Library or Lesser General Public License (LGPL) Classifier: Operating System :: OS Independent Classifier: Programming Language :: Python Classifier: Topic :: Software Development :: Libraries :: Python Modules Classifier: Topic :: Text Processing :: General python-stdnum-0.9/python_stdnum.egg-info/SOURCES.txt0000644000000000000000000001066712260536561022462 0ustar rootroot00000000000000COPYING ChangeLog MANIFEST.in NEWS README getiban.py getimsi.py getisbn.py getisil.py getmybp.py getnumlist.py numdb-test.dat setup.cfg setup.py docs/conf.py docs/index.rst docs/stdnum.at.uid.rst docs/stdnum.be.vat.rst docs/stdnum.bg.egn.rst docs/stdnum.bg.pnf.rst docs/stdnum.bg.vat.rst docs/stdnum.br.cpf.rst docs/stdnum.cy.vat.rst docs/stdnum.cz.dic.rst docs/stdnum.cz.rc.rst docs/stdnum.de.vat.rst docs/stdnum.dk.cpr.rst docs/stdnum.dk.cvr.rst docs/stdnum.ean.rst docs/stdnum.ee.kmkr.rst docs/stdnum.es.cif.rst docs/stdnum.es.dni.rst docs/stdnum.es.nie.rst docs/stdnum.es.nif.rst docs/stdnum.eu.vat.rst docs/stdnum.exceptions.rst docs/stdnum.fi.alv.rst docs/stdnum.fi.hetu.rst docs/stdnum.fr.siren.rst docs/stdnum.fr.tva.rst docs/stdnum.gb.vat.rst docs/stdnum.gr.vat.rst docs/stdnum.grid.rst docs/stdnum.hr.oib.rst docs/stdnum.hu.anum.rst docs/stdnum.iban.rst docs/stdnum.ie.pps.rst docs/stdnum.ie.vat.rst docs/stdnum.imei.rst docs/stdnum.imsi.rst docs/stdnum.isan.rst docs/stdnum.isbn.rst docs/stdnum.isil.rst docs/stdnum.ismn.rst docs/stdnum.iso7064.rst docs/stdnum.issn.rst docs/stdnum.it.iva.rst docs/stdnum.lt.pvm.rst docs/stdnum.lu.tva.rst docs/stdnum.luhn.rst docs/stdnum.lv.pvn.rst docs/stdnum.meid.rst docs/stdnum.mt.vat.rst docs/stdnum.my.nric.rst docs/stdnum.nl.brin.rst docs/stdnum.nl.bsn.rst docs/stdnum.nl.btw.rst docs/stdnum.nl.onderwijsnummer.rst docs/stdnum.nl.postcode.rst docs/stdnum.pl.nip.rst docs/stdnum.pt.nif.rst docs/stdnum.ro.cf.rst docs/stdnum.ro.cnp.rst docs/stdnum.se.vat.rst docs/stdnum.si.ddv.rst docs/stdnum.sk.dph.rst docs/stdnum.sk.rc.rst docs/stdnum.us.atin.rst docs/stdnum.us.ein.rst docs/stdnum.us.itin.rst docs/stdnum.us.ptin.rst docs/stdnum.us.ssn.rst docs/stdnum.us.tin.rst docs/stdnum.verhoeff.rst docs/_templates/autosummary/module.rst python_stdnum.egg-info/PKG-INFO python_stdnum.egg-info/SOURCES.txt python_stdnum.egg-info/dependency_links.txt python_stdnum.egg-info/requires.txt python_stdnum.egg-info/top_level.txt stdnum/__init__.py stdnum/ean.py stdnum/exceptions.py stdnum/grid.py stdnum/iban.dat stdnum/iban.py stdnum/imei.py stdnum/imsi.dat stdnum/imsi.py stdnum/isan.py stdnum/isbn.dat stdnum/isbn.py stdnum/isil.dat stdnum/isil.py stdnum/ismn.py stdnum/issn.py stdnum/luhn.py stdnum/meid.py stdnum/numdb.py stdnum/util.py stdnum/verhoeff.py stdnum/at/__init__.py stdnum/at/uid.py stdnum/be/__init__.py stdnum/be/vat.py stdnum/bg/__init__.py stdnum/bg/egn.py stdnum/bg/pnf.py stdnum/bg/vat.py stdnum/br/__init__.py stdnum/br/cpf.py stdnum/cy/__init__.py stdnum/cy/vat.py stdnum/cz/__init__.py stdnum/cz/dic.py stdnum/cz/rc.py stdnum/de/__init__.py stdnum/de/vat.py stdnum/dk/__init__.py stdnum/dk/cpr.py stdnum/dk/cvr.py stdnum/ee/__init__.py stdnum/ee/kmkr.py stdnum/es/__init__.py stdnum/es/cif.py stdnum/es/dni.py stdnum/es/nie.py stdnum/es/nif.py stdnum/eu/__init__.py stdnum/eu/vat.py stdnum/fi/__init__.py stdnum/fi/alv.py stdnum/fi/hetu.py stdnum/fr/__init__.py stdnum/fr/siren.py stdnum/fr/tva.py stdnum/gb/__init__.py stdnum/gb/vat.py stdnum/gr/__init__.py stdnum/gr/vat.py stdnum/hr/__init__.py stdnum/hr/oib.py stdnum/hu/__init__.py stdnum/hu/anum.py stdnum/ie/__init__.py stdnum/ie/pps.py stdnum/ie/vat.py stdnum/iso7064/__init__.py stdnum/iso7064/mod_11_10.py stdnum/iso7064/mod_11_2.py stdnum/iso7064/mod_37_2.py stdnum/iso7064/mod_37_36.py stdnum/iso7064/mod_97_10.py stdnum/it/__init__.py stdnum/it/iva.py stdnum/lt/__init__.py stdnum/lt/pvm.py stdnum/lu/__init__.py stdnum/lu/tva.py stdnum/lv/__init__.py stdnum/lv/pvn.py stdnum/mt/__init__.py stdnum/mt/vat.py stdnum/my/__init__.py stdnum/my/bp.dat stdnum/my/nric.py stdnum/nl/__init__.py stdnum/nl/brin.py stdnum/nl/bsn.py stdnum/nl/btw.py stdnum/nl/onderwijsnummer.py stdnum/nl/postcode.py stdnum/pl/__init__.py stdnum/pl/nip.py stdnum/pt/__init__.py stdnum/pt/nif.py stdnum/ro/__init__.py stdnum/ro/cf.py stdnum/ro/cnp.py stdnum/se/__init__.py stdnum/se/vat.py stdnum/si/__init__.py stdnum/si/ddv.py stdnum/sk/__init__.py stdnum/sk/dph.py stdnum/sk/rc.py stdnum/us/__init__.py stdnum/us/atin.py stdnum/us/ein.dat stdnum/us/ein.py stdnum/us/itin.py stdnum/us/ptin.py stdnum/us/ssn.py stdnum/us/tin.py tests/test_bg_vat.doctest tests/test_ean.doctest tests/test_eu_vat.doctest tests/test_fi_hetu.doctest tests/test_gb_vat.doctest tests/test_iban.doctest tests/test_imei.doctest tests/test_isan.doctest tests/test_isbn.doctest tests/test_ismn.doctest tests/test_iso7064.doctest tests/test_luhn.doctest tests/test_meid.doctest tests/test_my_nric.doctest tests/test_robustness.doctest tests/test_verhoeff.doctestpython-stdnum-0.9/python_stdnum.egg-info/requires.txt0000644000000000000000000000002712260536561023163 0ustar rootroot00000000000000distribute [VIES] sudspython-stdnum-0.9/python_stdnum.egg-info/dependency_links.txt0000644000000000000000000000000112260536561024632 0ustar rootroot00000000000000 python-stdnum-0.9/COPYING0000644000000000000000000006350411423014675015217 0ustar rootroot00000000000000 GNU LESSER GENERAL PUBLIC LICENSE Version 2.1, February 1999 Copyright (C) 1991, 1999 Free Software Foundation, Inc. 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA Everyone is permitted to copy and distribute verbatim copies of this license document, but changing it is not allowed. [This is the first released version of the Lesser GPL. It also counts as the successor of the GNU Library Public License, version 2, hence the version number 2.1.] Preamble The licenses for most software are designed to take away your freedom to share and change it. By contrast, the GNU General Public Licenses are intended to guarantee your freedom to share and change free software--to make sure the software is free for all its users. This license, the Lesser General Public License, applies to some specially designated software packages--typically libraries--of the Free Software Foundation and other authors who decide to use it. You can use it too, but we suggest you first think carefully about whether this license or the ordinary General Public License is the better strategy to use in any particular case, based on the explanations below. When we speak of free software, we are referring to freedom of use, not price. Our General Public Licenses are designed to make sure that you have the freedom to distribute copies of free software (and charge for this service if you wish); that you receive source code or can get it if you want it; that you can change the software and use pieces of it in new free programs; and that you are informed that you can do these things. To protect your rights, we need to make restrictions that forbid distributors to deny you these rights or to ask you to surrender these rights. These restrictions translate to certain responsibilities for you if you distribute copies of the library or if you modify it. For example, if you distribute copies of the library, whether gratis or for a fee, you must give the recipients all the rights that we gave you. You must make sure that they, too, receive or can get the source code. If you link other code with the library, you must provide complete object files to the recipients, so that they can relink them with the library after making changes to the library and recompiling it. And you must show them these terms so they know their rights. We protect your rights with a two-step method: (1) we copyright the library, and (2) we offer you this license, which gives you legal permission to copy, distribute and/or modify the library. To protect each distributor, we want to make it very clear that there is no warranty for the free library. Also, if the library is modified by someone else and passed on, the recipients should know that what they have is not the original version, so that the original author's reputation will not be affected by problems that might be introduced by others. Finally, software patents pose a constant threat to the existence of any free program. We wish to make sure that a company cannot effectively restrict the users of a free program by obtaining a restrictive license from a patent holder. Therefore, we insist that any patent license obtained for a version of the library must be consistent with the full freedom of use specified in this license. Most GNU software, including some libraries, is covered by the ordinary GNU General Public License. This license, the GNU Lesser General Public License, applies to certain designated libraries, and is quite different from the ordinary General Public License. We use this license for certain libraries in order to permit linking those libraries into non-free programs. When a program is linked with a library, whether statically or using a shared library, the combination of the two is legally speaking a combined work, a derivative of the original library. The ordinary General Public License therefore permits such linking only if the entire combination fits its criteria of freedom. The Lesser General Public License permits more lax criteria for linking other code with the library. We call this license the "Lesser" General Public License because it does Less to protect the user's freedom than the ordinary General Public License. It also provides other free software developers Less of an advantage over competing non-free programs. These disadvantages are the reason we use the ordinary General Public License for many libraries. However, the Lesser license provides advantages in certain special circumstances. For example, on rare occasions, there may be a special need to encourage the widest possible use of a certain library, so that it becomes a de-facto standard. To achieve this, non-free programs must be allowed to use the library. A more frequent case is that a free library does the same job as widely used non-free libraries. In this case, there is little to gain by limiting the free library to free software only, so we use the Lesser General Public License. In other cases, permission to use a particular library in non-free programs enables a greater number of people to use a large body of free software. For example, permission to use the GNU C Library in non-free programs enables many more people to use the whole GNU operating system, as well as its variant, the GNU/Linux operating system. Although the Lesser General Public License is Less protective of the users' freedom, it does ensure that the user of a program that is linked with the Library has the freedom and the wherewithal to run that program using a modified version of the Library. The precise terms and conditions for copying, distribution and modification follow. Pay close attention to the difference between a "work based on the library" and a "work that uses the library". The former contains code derived from the library, whereas the latter must be combined with the library in order to run. GNU LESSER GENERAL PUBLIC LICENSE TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION 0. This License Agreement applies to any software library or other program which contains a notice placed by the copyright holder or other authorized party saying it may be distributed under the terms of this Lesser General Public License (also called "this License"). Each licensee is addressed as "you". A "library" means a collection of software functions and/or data prepared so as to be conveniently linked with application programs (which use some of those functions and data) to form executables. The "Library", below, refers to any such software library or work which has been distributed under these terms. A "work based on the Library" means either the Library or any derivative work under copyright law: that is to say, a work containing the Library or a portion of it, either verbatim or with modifications and/or translated straightforwardly into another language. (Hereinafter, translation is included without limitation in the term "modification".) "Source code" for a work means the preferred form of the work for making modifications to it. For a library, complete source code means all the source code for all modules it contains, plus any associated interface definition files, plus the scripts used to control compilation and installation of the library. Activities other than copying, distribution and modification are not covered by this License; they are outside its scope. The act of running a program using the Library is not restricted, and output from such a program is covered only if its contents constitute a work based on the Library (independent of the use of the Library in a tool for writing it). Whether that is true depends on what the Library does and what the program that uses the Library does. 1. You may copy and distribute verbatim copies of the Library's complete source code as you receive it, in any medium, provided that you conspicuously and appropriately publish on each copy an appropriate copyright notice and disclaimer of warranty; keep intact all the notices that refer to this License and to the absence of any warranty; and distribute a copy of this License along with the Library. You may charge a fee for the physical act of transferring a copy, and you may at your option offer warranty protection in exchange for a fee. 2. You may modify your copy or copies of the Library or any portion of it, thus forming a work based on the Library, and copy and distribute such modifications or work under the terms of Section 1 above, provided that you also meet all of these conditions: a) The modified work must itself be a software library. b) You must cause the files modified to carry prominent notices stating that you changed the files and the date of any change. c) You must cause the whole of the work to be licensed at no charge to all third parties under the terms of this License. d) If a facility in the modified Library refers to a function or a table of data to be supplied by an application program that uses the facility, other than as an argument passed when the facility is invoked, then you must make a good faith effort to ensure that, in the event an application does not supply such function or table, the facility still operates, and performs whatever part of its purpose remains meaningful. (For example, a function in a library to compute square roots has a purpose that is entirely well-defined independent of the application. Therefore, Subsection 2d requires that any application-supplied function or table used by this function must be optional: if the application does not supply it, the square root function must still compute square roots.) These requirements apply to the modified work as a whole. If identifiable sections of that work are not derived from the Library, and can be reasonably considered independent and separate works in themselves, then this License, and its terms, do not apply to those sections when you distribute them as separate works. But when you distribute the same sections as part of a whole which is a work based on the Library, the distribution of the whole must be on the terms of this License, whose permissions for other licensees extend to the entire whole, and thus to each and every part regardless of who wrote it. Thus, it is not the intent of this section to claim rights or contest your rights to work written entirely by you; rather, the intent is to exercise the right to control the distribution of derivative or collective works based on the Library. In addition, mere aggregation of another work not based on the Library with the Library (or with a work based on the Library) on a volume of a storage or distribution medium does not bring the other work under the scope of this License. 3. You may opt to apply the terms of the ordinary GNU General Public License instead of this License to a given copy of the Library. To do this, you must alter all the notices that refer to this License, so that they refer to the ordinary GNU General Public License, version 2, instead of to this License. (If a newer version than version 2 of the ordinary GNU General Public License has appeared, then you can specify that version instead if you wish.) Do not make any other change in these notices. Once this change is made in a given copy, it is irreversible for that copy, so the ordinary GNU General Public License applies to all subsequent copies and derivative works made from that copy. This option is useful when you wish to copy part of the code of the Library into a program that is not a library. 4. You may copy and distribute the Library (or a portion or derivative of it, under Section 2) in object code or executable form under the terms of Sections 1 and 2 above provided that you accompany it with the complete corresponding machine-readable source code, which must be distributed under the terms of Sections 1 and 2 above on a medium customarily used for software interchange. If distribution of object code is made by offering access to copy from a designated place, then offering equivalent access to copy the source code from the same place satisfies the requirement to distribute the source code, even though third parties are not compelled to copy the source along with the object code. 5. A program that contains no derivative of any portion of the Library, but is designed to work with the Library by being compiled or linked with it, is called a "work that uses the Library". Such a work, in isolation, is not a derivative work of the Library, and therefore falls outside the scope of this License. However, linking a "work that uses the Library" with the Library creates an executable that is a derivative of the Library (because it contains portions of the Library), rather than a "work that uses the library". The executable is therefore covered by this License. Section 6 states terms for distribution of such executables. When a "work that uses the Library" uses material from a header file that is part of the Library, the object code for the work may be a derivative work of the Library even though the source code is not. Whether this is true is especially significant if the work can be linked without the Library, or if the work is itself a library. The threshold for this to be true is not precisely defined by law. If such an object file uses only numerical parameters, data structure layouts and accessors, and small macros and small inline functions (ten lines or less in length), then the use of the object file is unrestricted, regardless of whether it is legally a derivative work. (Executables containing this object code plus portions of the Library will still fall under Section 6.) Otherwise, if the work is a derivative of the Library, you may distribute the object code for the work under the terms of Section 6. Any executables containing that work also fall under Section 6, whether or not they are linked directly with the Library itself. 6. As an exception to the Sections above, you may also combine or link a "work that uses the Library" with the Library to produce a work containing portions of the Library, and distribute that work under terms of your choice, provided that the terms permit modification of the work for the customer's own use and reverse engineering for debugging such modifications. You must give prominent notice with each copy of the work that the Library is used in it and that the Library and its use are covered by this License. You must supply a copy of this License. If the work during execution displays copyright notices, you must include the copyright notice for the Library among them, as well as a reference directing the user to the copy of this License. Also, you must do one of these things: a) Accompany the work with the complete corresponding machine-readable source code for the Library including whatever changes were used in the work (which must be distributed under Sections 1 and 2 above); and, if the work is an executable linked with the Library, with the complete machine-readable "work that uses the Library", as object code and/or source code, so that the user can modify the Library and then relink to produce a modified executable containing the modified Library. (It is understood that the user who changes the contents of definitions files in the Library will not necessarily be able to recompile the application to use the modified definitions.) b) Use a suitable shared library mechanism for linking with the Library. A suitable mechanism is one that (1) uses at run time a copy of the library already present on the user's computer system, rather than copying library functions into the executable, and (2) will operate properly with a modified version of the library, if the user installs one, as long as the modified version is interface-compatible with the version that the work was made with. c) Accompany the work with a written offer, valid for at least three years, to give the same user the materials specified in Subsection 6a, above, for a charge no more than the cost of performing this distribution. d) If distribution of the work is made by offering access to copy from a designated place, offer equivalent access to copy the above specified materials from the same place. e) Verify that the user has already received a copy of these materials or that you have already sent this user a copy. For an executable, the required form of the "work that uses the Library" must include any data and utility programs needed for reproducing the executable from it. However, as a special exception, the materials to be distributed need not include anything that is normally distributed (in either source or binary form) with the major components (compiler, kernel, and so on) of the operating system on which the executable runs, unless that component itself accompanies the executable. It may happen that this requirement contradicts the license restrictions of other proprietary libraries that do not normally accompany the operating system. Such a contradiction means you cannot use both them and the Library together in an executable that you distribute. 7. You may place library facilities that are a work based on the Library side-by-side in a single library together with other library facilities not covered by this License, and distribute such a combined library, provided that the separate distribution of the work based on the Library and of the other library facilities is otherwise permitted, and provided that you do these two things: a) Accompany the combined library with a copy of the same work based on the Library, uncombined with any other library facilities. This must be distributed under the terms of the Sections above. b) Give prominent notice with the combined library of the fact that part of it is a work based on the Library, and explaining where to find the accompanying uncombined form of the same work. 8. You may not copy, modify, sublicense, link with, or distribute the Library except as expressly provided under this License. Any attempt otherwise to copy, modify, sublicense, link with, or distribute the Library is void, and will automatically terminate your rights under this License. However, parties who have received copies, or rights, from you under this License will not have their licenses terminated so long as such parties remain in full compliance. 9. You are not required to accept this License, since you have not signed it. However, nothing else grants you permission to modify or distribute the Library or its derivative works. These actions are prohibited by law if you do not accept this License. Therefore, by modifying or distributing the Library (or any work based on the Library), you indicate your acceptance of this License to do so, and all its terms and conditions for copying, distributing or modifying the Library or works based on it. 10. Each time you redistribute the Library (or any work based on the Library), the recipient automatically receives a license from the original licensor to copy, distribute, link with or modify the Library subject to these terms and conditions. You may not impose any further restrictions on the recipients' exercise of the rights granted herein. You are not responsible for enforcing compliance by third parties with this License. 11. If, as a consequence of a court judgment or allegation of patent infringement or for any other reason (not limited to patent issues), conditions are imposed on you (whether by court order, agreement or otherwise) that contradict the conditions of this License, they do not excuse you from the conditions of this License. If you cannot distribute so as to satisfy simultaneously your obligations under this License and any other pertinent obligations, then as a consequence you may not distribute the Library at all. For example, if a patent license would not permit royalty-free redistribution of the Library by all those who receive copies directly or indirectly through you, then the only way you could satisfy both it and this License would be to refrain entirely from distribution of the Library. If any portion of this section is held invalid or unenforceable under any particular circumstance, the balance of the section is intended to apply, and the section as a whole is intended to apply in other circumstances. It is not the purpose of this section to induce you to infringe any patents or other property right claims or to contest validity of any such claims; this section has the sole purpose of protecting the integrity of the free software distribution system which is implemented by public license practices. Many people have made generous contributions to the wide range of software distributed through that system in reliance on consistent application of that system; it is up to the author/donor to decide if he or she is willing to distribute software through any other system and a licensee cannot impose that choice. This section is intended to make thoroughly clear what is believed to be a consequence of the rest of this License. 12. If the distribution and/or use of the Library is restricted in certain countries either by patents or by copyrighted interfaces, the original copyright holder who places the Library under this License may add an explicit geographical distribution limitation excluding those countries, so that distribution is permitted only in or among countries not thus excluded. In such case, this License incorporates the limitation as if written in the body of this License. 13. The Free Software Foundation may publish revised and/or new versions of the Lesser General Public License from time to time. Such new versions will be similar in spirit to the present version, but may differ in detail to address new problems or concerns. Each version is given a distinguishing version number. If the Library specifies a version number of this License which applies to it and "any later version", you have the option of following the terms and conditions either of that version or of any later version published by the Free Software Foundation. If the Library does not specify a license version number, you may choose any version ever published by the Free Software Foundation. 14. If you wish to incorporate parts of the Library into other free programs whose distribution conditions are incompatible with these, write to the author to ask for permission. For software which is copyrighted by the Free Software Foundation, write to the Free Software Foundation; we sometimes make exceptions for this. Our decision will be guided by the two goals of preserving the free status of all derivatives of our free software and of promoting the sharing and reuse of software generally. NO WARRANTY 15. BECAUSE THE LIBRARY IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY FOR THE LIBRARY, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES PROVIDE THE LIBRARY "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE LIBRARY IS WITH YOU. SHOULD THE LIBRARY PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING, REPAIR OR CORRECTION. 16. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR REDISTRIBUTE THE LIBRARY AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE THE LIBRARY (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A FAILURE OF THE LIBRARY TO OPERATE WITH ANY OTHER SOFTWARE), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. END OF TERMS AND CONDITIONS How to Apply These Terms to Your New Libraries If you develop a new library, and you want it to be of the greatest possible use to the public, we recommend making it free software that everyone can redistribute and change. You can do so by permitting redistribution under these terms (or, alternatively, under the terms of the ordinary General Public License). To apply these terms, attach the following notices to the library. It is safest to attach them to the start of each source file to most effectively convey the exclusion of warranty; and each file should have at least the "copyright" line and a pointer to where the full notice is found. Copyright (C) This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA Also add information on how to contact you by electronic and paper mail. You should also get your employer (if you work as a programmer) or your school, if any, to sign a "copyright disclaimer" for the library, if necessary. Here is a sample; alter the names: Yoyodyne, Inc., hereby disclaims all copyright interest in the library `Frob' (a library for tweaking knobs) written by James Random Hacker. , 1 April 1990 Ty Coon, President of Vice That's all there is to it!