UNPKG

formvalidation

Version:

The best jQuery plugin to validate form fields. Support Bootstrap, Foundation, Pure, SemanticUI, UIKit and custom frameworks

1,288 lines (1,227 loc) 56.2 kB
/** * id validator * * @link http://formvalidation.io/validators/id/ * @author https://twitter.com/nghuuphuoc * @copyright (c) 2013 - 2015 Nguyen Huu Phuoc * @license http://formvalidation.io/license/ */ (function($) { FormValidation.I18n = $.extend(true, FormValidation.I18n || {}, { 'en_US': { id: { 'default': 'Please enter a valid identification number', country: 'Please enter a valid identification number in %s', countries: { BA: 'Bosnia and Herzegovina', BG: 'Bulgaria', BR: 'Brazil', CH: 'Switzerland', CL: 'Chile', CN: 'China', CZ: 'Czech Republic', DK: 'Denmark', EE: 'Estonia', ES: 'Spain', FI: 'Finland', HR: 'Croatia', IE: 'Ireland', IS: 'Iceland', LT: 'Lithuania', LV: 'Latvia', ME: 'Montenegro', MK: 'Macedonia', NL: 'Netherlands', PL: 'Poland', RO: 'Romania', RS: 'Serbia', SE: 'Sweden', SI: 'Slovenia', SK: 'Slovakia', SM: 'San Marino', TH: 'Thailand', ZA: 'South Africa' } } } }); FormValidation.Validator.id = { html5Attributes: { message: 'message', country: 'country' }, // Supported country codes COUNTRY_CODES: [ 'BA', 'BG', 'BR', 'CH', 'CL', 'CN', 'CZ', 'DK', 'EE', 'ES', 'FI', 'HR', 'IE', 'IS', 'LT', 'LV', 'ME', 'MK', 'NL', 'PL', 'RO', 'RS', 'SE', 'SI', 'SK', 'SM', 'TH', 'ZA' ], /** * Validate identification number in different countries * * @see http://en.wikipedia.org/wiki/National_identification_number * @param {FormValidation.Base} validator The validator plugin instance * @param {jQuery} $field Field element * @param {Object} options Consist of key: * - message: The invalid message * - country: The ISO 3166-1 country code. It can be * - One of country code defined in COUNTRY_CODES * - Name of field which its value defines the country code * - Name of callback function that returns the country code * - A callback function that returns the country code * @returns {Boolean|Object} */ validate: function(validator, $field, options) { var value = validator.getFieldValue($field, 'id'); if (value === '') { return true; } var locale = validator.getLocale(), country = options.country; if (!country) { country = value.substr(0, 2); } else if (typeof country !== 'string' || $.inArray(country.toUpperCase(), this.COUNTRY_CODES) === -1) { // Determine the country code country = validator.getDynamicOption($field, country); } if ($.inArray(country, this.COUNTRY_CODES) === -1) { return true; } var method = ['_', country.toLowerCase()].join(''); return this[method](value) ? true : { valid: false, message: FormValidation.Helper.format(options.message || FormValidation.I18n[locale].id.country, FormValidation.I18n[locale].id.countries[country.toUpperCase()]) }; }, /** * Validate Unique Master Citizen Number which uses in * - Bosnia and Herzegovina (country code: BA) * - Macedonia (MK) * - Montenegro (ME) * - Serbia (RS) * - Slovenia (SI) * * @see http://en.wikipedia.org/wiki/Unique_Master_Citizen_Number * @param {String} value The ID * @param {String} countryCode The ISO country code, can be BA, MK, ME, RS, SI * @returns {Boolean} */ _validateJMBG: function(value, countryCode) { if (!/^\d{13}$/.test(value)) { return false; } var day = parseInt(value.substr(0, 2), 10), month = parseInt(value.substr(2, 2), 10), year = parseInt(value.substr(4, 3), 10), rr = parseInt(value.substr(7, 2), 10), k = parseInt(value.substr(12, 1), 10); // Validate date of birth // FIXME: Validate the year of birth if (day > 31 || month > 12) { return false; } // Validate checksum var sum = 0; for (var i = 0; i < 6; i++) { sum += (7 - i) * (parseInt(value.charAt(i), 10) + parseInt(value.charAt(i + 6), 10)); } sum = 11 - sum % 11; if (sum === 10 || sum === 11) { sum = 0; } if (sum !== k) { return false; } // Validate political region // rr is the political region of birth, which can be in ranges: // 10-19: Bosnia and Herzegovina // 20-29: Montenegro // 30-39: Croatia (not used anymore) // 41-49: Macedonia // 50-59: Slovenia (only 50 is used) // 70-79: Central Serbia // 80-89: Serbian province of Vojvodina // 90-99: Kosovo switch (countryCode.toUpperCase()) { case 'BA': return (10 <= rr && rr <= 19); case 'MK': return (41 <= rr && rr <= 49); case 'ME': return (20 <= rr && rr <= 29); case 'RS': return (70 <= rr && rr <= 99); case 'SI': return (50 <= rr && rr <= 59); default: return true; } }, _ba: function(value) { return this._validateJMBG(value, 'BA'); }, _mk: function(value) { return this._validateJMBG(value, 'MK'); }, _me: function(value) { return this._validateJMBG(value, 'ME'); }, _rs: function(value) { return this._validateJMBG(value, 'RS'); }, /** * Examples: 0101006500006 */ _si: function(value) { return this._validateJMBG(value, 'SI'); }, /** * Validate Bulgarian national identification number (EGN) * Examples: * - Valid: 7523169263, 8032056031, 803205 603 1, 8001010008, 7501020018, 7552010005, 7542011030 * - Invalid: 8019010008 * * @see http://en.wikipedia.org/wiki/Uniform_civil_number * @param {String} value The ID * @returns {Boolean} */ _bg: function(value) { if (!/^\d{10}$/.test(value) && !/^\d{6}\s\d{3}\s\d{1}$/.test(value)) { return false; } value = value.replace(/\s/g, ''); // Check the birth date var year = parseInt(value.substr(0, 2), 10) + 1900, month = parseInt(value.substr(2, 2), 10), day = parseInt(value.substr(4, 2), 10); if (month > 40) { year += 100; month -= 40; } else if (month > 20) { year -= 100; month -= 20; } if (!FormValidation.Helper.date(year, month, day)) { return false; } var sum = 0, weight = [2, 4, 8, 5, 10, 9, 7, 3, 6]; for (var i = 0; i < 9; i++) { sum += parseInt(value.charAt(i), 10) * weight[i]; } sum = (sum % 11) % 10; return (sum + '' === value.substr(9, 1)); }, /** * Validate Brazilian national identification number (CPF) * Examples: * - Valid: 39053344705, 390.533.447-05, 111.444.777-35 * - Invalid: 231.002.999-00 * * @see http://en.wikipedia.org/wiki/Cadastro_de_Pessoas_F%C3%ADsicas * @param {String} value The ID * @returns {Boolean} */ _br: function(value) { value = value.replace(/\D/g, ''); if (!/^\d{11}$/.test(value) || /^1{11}|2{11}|3{11}|4{11}|5{11}|6{11}|7{11}|8{11}|9{11}|0{11}$/.test(value)) { return false; } var d1 = 0; for (var i = 0; i < 9; i++) { d1 += (10 - i) * parseInt(value.charAt(i), 10); } d1 = 11 - d1 % 11; if (d1 === 10 || d1 === 11) { d1 = 0; } if (d1 + '' !== value.charAt(9)) { return false; } var d2 = 0; for (i = 0; i < 10; i++) { d2 += (11 - i) * parseInt(value.charAt(i), 10); } d2 = 11 - d2 % 11; if (d2 === 10 || d2 === 11) { d2 = 0; } return (d2 + '' === value.charAt(10)); }, /** * Validate Swiss Social Security Number (AHV-Nr/No AVS) * Examples: * - Valid: 756.1234.5678.95, 7561234567895 * * @see http://en.wikipedia.org/wiki/National_identification_number#Switzerland * @see http://www.bsv.admin.ch/themen/ahv/00011/02185/index.html?lang=de * @param {String} value The ID * @returns {Boolean} */ _ch: function(value) { if (!/^756[\.]{0,1}[0-9]{4}[\.]{0,1}[0-9]{4}[\.]{0,1}[0-9]{2}$/.test(value)) { return false; } value = value.replace(/\D/g, '').substr(3); var length = value.length, sum = 0, weight = (length === 8) ? [3, 1] : [1, 3]; for (var i = 0; i < length - 1; i++) { sum += parseInt(value.charAt(i), 10) * weight[i % 2]; } sum = 10 - sum % 10; return (sum + '' === value.charAt(length - 1)); }, /** * Validate Chilean national identification number (RUN/RUT) * Examples: * - Valid: 76086428-5, 22060449-7, 12531909-2 * * @see http://en.wikipedia.org/wiki/National_identification_number#Chile * @see https://palena.sii.cl/cvc/dte/ee_empresas_emisoras.html for samples * @param {String} value The ID * @returns {Boolean} */ _cl: function(value) { if (!/^\d{7,8}[-]{0,1}[0-9K]$/i.test(value)) { return false; } value = value.replace(/\-/g, ''); while (value.length < 9) { value = '0' + value; } var sum = 0, weight = [3, 2, 7, 6, 5, 4, 3, 2]; for (var i = 0; i < 8; i++) { sum += parseInt(value.charAt(i), 10) * weight[i]; } sum = 11 - sum % 11; if (sum === 11) { sum = 0; } else if (sum === 10) { sum = 'K'; } return sum + '' === value.charAt(8).toUpperCase(); }, /** * Validate Chinese citizen identification number * * Rules: * - For current 18-digit system (since 1st Oct 1999, defined by GB11643—1999 national standard): * - Digit 0-5: Must be a valid administrative division code of China PR. * - Digit 6-13: Must be a valid YYYYMMDD date of birth. A future date is tolerated. * - Digit 14-16: Order code, any integer. * - Digit 17: An ISO 7064:1983, MOD 11-2 checksum. * Both upper/lower case of X are tolerated. * - For deprecated 15-digit system: * - Digit 0-5: Must be a valid administrative division code of China PR. * - Digit 6-11: Must be a valid YYMMDD date of birth, indicating the year of 19XX. * - Digit 12-14: Order code, any integer. * Lists of valid administrative division codes of China PR can be seen here: * <http://www.stats.gov.cn/tjsj/tjbz/xzqhdm/> * Published and maintained by National Bureau of Statistics of China PR. * NOTE: Current and deprecated codes MUST BOTH be considered valid. * Many Chinese citizens born in once existed administrative divisions! * * @see http://en.wikipedia.org/wiki/Resident_Identity_Card#Identity_card_number * @param {String} value The ID * @returns {Boolean} */ _cn: function(value) { // Basic format check (18 or 15 digits, considering X in checksum) value = value.trim(); if (!/^\d{15}$/.test(value) && !/^\d{17}[\dXx]{1}$/.test(value)) { return false; } // Check China PR Administrative division code var adminDivisionCodes = { 11: { 0: [0], 1: [[0, 9], [11, 17]], 2: [0, 28, 29] }, 12: { 0: [0], 1: [[0, 16]], 2: [0, 21, 23, 25] }, 13: { 0: [0], 1: [[0, 5], 7, 8, 21, [23, 33], [81, 85]], 2: [[0, 5], [7, 9], [23, 25], 27, 29, 30, 81, 83], 3: [[0, 4], [21, 24]], 4: [[0, 4], 6, 21, [23, 35], 81], 5: [[0, 3], [21, 35], 81, 82], 6: [[0, 4], [21, 38], [81, 84]], 7: [[0, 3], 5, 6, [21, 33]], 8: [[0, 4], [21, 28]], 9: [[0, 3], [21, 30], [81, 84]], 10: [[0, 3], [22, 26], 28, 81, 82], 11: [[0, 2], [21, 28], 81, 82] }, 14: { 0: [0], 1: [0, 1, [5, 10], [21, 23], 81], 2: [[0, 3], 11, 12, [21, 27]], 3: [[0, 3], 11, 21, 22], 4: [[0, 2], 11, 21, [23, 31], 81], 5: [[0, 2], 21, 22, 24, 25, 81], 6: [[0, 3], [21, 24]], 7: [[0, 2], [21, 29], 81], 8: [[0, 2], [21, 30], 81, 82], 9: [[0, 2], [21, 32], 81], 10: [[0, 2], [21, 34], 81, 82], 11: [[0, 2], [21, 30], 81, 82], 23: [[0, 3], 22, 23, [25, 30], 32, 33] }, 15: { 0: [0], 1: [[0, 5], [21, 25]], 2: [[0, 7], [21, 23]], 3: [[0, 4]], 4: [[0, 4], [21, 26], [28, 30]], 5: [[0, 2], [21, 26], 81], 6: [[0, 2], [21, 27]], 7: [[0, 3], [21, 27], [81, 85]], 8: [[0, 2], [21, 26]], 9: [[0, 2], [21, 29], 81], 22: [[0, 2], [21, 24]], 25: [[0, 2], [22, 31]], 26: [[0, 2], [24, 27], [29, 32], 34], 28: [0, 1, [22, 27]], 29: [0, [21, 23]] }, 21: { 0: [0], 1: [[0, 6], [11, 14], [22, 24], 81], 2: [[0, 4], [11, 13], 24, [81, 83]], 3: [[0, 4], 11, 21, 23, 81], 4: [[0, 4], 11, [21, 23]], 5: [[0, 5], 21, 22], 6: [[0, 4], 24, 81, 82], 7: [[0, 3], 11, 26, 27, 81, 82], 8: [[0, 4], 11, 81, 82], 9: [[0, 5], 11, 21, 22], 10: [[0, 5], 11, 21, 81], 11: [[0, 3], 21, 22], 12: [[0, 2], 4, 21, 23, 24, 81, 82], 13: [[0, 3], 21, 22, 24, 81, 82], 14: [[0, 4], 21, 22, 81] }, 22: { 0: [0], 1: [[0, 6], 12, 22, [81, 83]], 2: [[0, 4], 11, 21, [81, 84]], 3: [[0, 3], 22, 23, 81, 82], 4: [[0, 3], 21, 22], 5: [[0, 3], 21, 23, 24, 81, 82], 6: [[0, 2], 4, 5, [21, 23], 25, 81], 7: [[0, 2], [21, 24], 81], 8: [[0, 2], 21, 22, 81, 82], 24: [[0, 6], 24, 26] }, 23: { 0: [0], 1: [[0, 12], 21, [23, 29], [81, 84]], 2: [[0, 8], 21, [23, 25], 27, [29, 31], 81], 3: [[0, 7], 21, 81, 82], 4: [[0, 7], 21, 22], 5: [[0, 3], 5, 6, [21, 24]], 6: [[0, 6], [21, 24]], 7: [[0, 16], 22, 81], 8: [[0, 5], 11, 22, 26, 28, 33, 81, 82], 9: [[0, 4], 21], 10: [[0, 5], 24, 25, 81, [83, 85]], 11: [[0, 2], 21, 23, 24, 81, 82], 12: [[0, 2], [21, 26], [81, 83]], 27: [[0, 4], [21, 23]] }, 31: { 0: [0], 1: [0, 1, [3, 10], [12, 20]], 2: [0, 30] }, 32: { 0: [0], 1: [[0, 7], 11, [13, 18], 24, 25], 2: [[0, 6], 11, 81, 82], 3: [[0, 5], 11, 12, [21, 24], 81, 82], 4: [[0, 2], 4, 5, 11, 12, 81, 82], 5: [[0, 9], [81, 85]], 6: [[0, 2], 11, 12, 21, 23, [81, 84]], 7: [0, 1, 3, 5, 6, [21, 24]], 8: [[0, 4], 11, 26, [29, 31]], 9: [[0, 3], [21, 25], 28, 81, 82], 10: [[0, 3], 11, 12, 23, 81, 84, 88], 11: [[0, 2], 11, 12, [81, 83]], 12: [[0, 4], [81, 84]], 13: [[0, 2], 11, [21, 24]] }, 33: { 0: [0], 1: [[0, 6], [8, 10], 22, 27, 82, 83, 85], 2: [0, 1, [3, 6], 11, 12, 25, 26, [81, 83]], 3: [[0, 4], 22, 24, [26, 29], 81, 82], 4: [[0, 2], 11, 21, 24, [81, 83]], 5: [[0, 3], [21, 23]], 6: [[0, 2], 21, 24, [81, 83]], 7: [[0, 3], 23, 26, 27, [81, 84]], 8: [[0, 3], 22, 24, 25, 81], 9: [[0, 3], 21, 22], 10: [[0, 4], [21, 24], 81, 82], 11: [[0, 2], [21, 27], 81] }, 34: { 0: [0], 1: [[0, 4], 11, [21, 24], 81], 2: [[0, 4], 7, 8, [21, 23], 25], 3: [[0, 4], 11, [21, 23]], 4: [[0, 6], 21], 5: [[0, 4], 6, [21, 23]], 6: [[0, 4], 21], 7: [[0, 3], 11, 21], 8: [[0, 3], 11, [22, 28], 81], 10: [[0, 4], [21, 24]], 11: [[0, 3], 22, [24, 26], 81, 82], 12: [[0, 4], 21, 22, 25, 26, 82], 13: [[0, 2], [21, 24]], 14: [[0, 2], [21, 24]], 15: [[0, 3], [21, 25]], 16: [[0, 2], [21, 23]], 17: [[0, 2], [21, 23]], 18: [[0, 2], [21, 25], 81] }, 35: { 0: [0], 1: [[0, 5], 11, [21, 25], 28, 81, 82], 2: [[0, 6], [11, 13]], 3: [[0, 5], 22], 4: [[0, 3], 21, [23, 30], 81], 5: [[0, 5], 21, [24, 27], [81, 83]], 6: [[0, 3], [22, 29], 81], 7: [[0, 2], [21, 25], [81, 84]], 8: [[0, 2], [21, 25], 81], 9: [[0, 2], [21, 26], 81, 82] }, 36: { 0: [0], 1: [[0, 5], 11, [21, 24]], 2: [[0, 3], 22, 81], 3: [[0, 2], 13, [21, 23]], 4: [[0, 3], 21, [23, 30], 81, 82], 5: [[0, 2], 21], 6: [[0, 2], 22, 81], 7: [[0, 2], [21, 35], 81, 82], 8: [[0, 3], [21, 30], 81], 9: [[0, 2], [21, 26], [81, 83]], 10: [[0, 2], [21, 30]], 11: [[0, 2], [21, 30], 81] }, 37: { 0: [0], 1: [[0, 5], 12, 13, [24, 26], 81], 2: [[0, 3], 5, [11, 14], [81, 85]], 3: [[0, 6], [21, 23]], 4: [[0, 6], 81], 5: [[0, 3], [21, 23]], 6: [[0, 2], [11, 13], 34, [81, 87]], 7: [[0, 5], 24, 25, [81, 86]], 8: [[0, 2], 11, [26, 32], [81, 83]], 9: [[0, 3], 11, 21, 23, 82, 83], 10: [[0, 2], [81, 83]], 11: [[0, 3], 21, 22], 12: [[0, 3]], 13: [[0, 2], 11, 12, [21, 29]], 14: [[0, 2], [21, 28], 81, 82], 15: [[0, 2], [21, 26], 81], 16: [[0, 2], [21, 26]], 17: [[0, 2], [21, 28]] }, 41: { 0: [0], 1: [[0, 6], 8, 22, [81, 85]], 2: [[0, 5], 11, [21, 25]], 3: [[0, 7], 11, [22, 29], 81], 4: [[0, 4], 11, [21, 23], 25, 81, 82], 5: [[0, 3], 5, 6, 22, 23, 26, 27, 81], 6: [[0, 3], 11, 21, 22], 7: [[0, 4], 11, 21, [24, 28], 81, 82], 8: [[0, 4], 11, [21, 23], 25, [81, 83]], 9: [[0, 2], 22, 23, [26, 28]], 10: [[0, 2], [23, 25], 81, 82], 11: [[0, 4], [21, 23]], 12: [[0, 2], 21, 22, 24, 81, 82], 13: [[0, 3], [21, 30], 81], 14: [[0, 3], [21, 26], 81], 15: [[0, 3], [21, 28]], 16: [[0, 2], [21, 28], 81], 17: [[0, 2], [21, 29]], 90: [0, 1] }, 42: { 0: [0], 1: [[0, 7], [11, 17]], 2: [[0, 5], 22, 81], 3: [[0, 3], [21, 25], 81], 5: [[0, 6], [25, 29], [81, 83]], 6: [[0, 2], 6, 7, [24, 26], [82, 84]], 7: [[0, 4]], 8: [[0, 2], 4, 21, 22, 81], 9: [[0, 2], [21, 23], 81, 82, 84], 10: [[0, 3], [22, 24], 81, 83, 87], 11: [[0, 2], [21, 27], 81, 82], 12: [[0, 2], [21, 24], 81], 13: [[0, 3], 21, 81], 28: [[0, 2], 22, 23, [25, 28]], 90: [0, [4, 6], 21] }, 43: { 0: [0], 1: [[0, 5], 11, 12, 21, 22, 24, 81], 2: [[0, 4], 11, 21, [23, 25], 81], 3: [[0, 2], 4, 21, 81, 82], 4: [0, 1, [5, 8], 12, [21, 24], 26, 81, 82], 5: [[0, 3], 11, [21, 25], [27, 29], 81], 6: [[0, 3], 11, 21, 23, 24, 26, 81, 82], 7: [[0, 3], [21, 26], 81], 8: [[0, 2], 11, 21, 22], 9: [[0, 3], [21, 23], 81], 10: [[0, 3], [21, 28], 81], 11: [[0, 3], [21, 29]], 12: [[0, 2], [21, 30], 81], 13: [[0, 2], 21, 22, 81, 82], 31: [0, 1, [22, 27], 30] }, 44: { 0: [0], 1: [[0, 7], [11, 16], 83, 84], 2: [[0, 5], 21, 22, 24, 29, 32, 33, 81, 82], 3: [0, 1, [3, 8]], 4: [[0, 4]], 5: [0, 1, [6, 15], 23, 82, 83], 6: [0, 1, [4, 8]], 7: [0, 1, [3, 5], 81, [83, 85]], 8: [[0, 4], 11, 23, 25, [81, 83]], 9: [[0, 3], 23, [81, 83]], 12: [[0, 3], [23, 26], 83, 84], 13: [[0, 3], [22, 24], 81], 14: [[0, 2], [21, 24], 26, 27, 81], 15: [[0, 2], 21, 23, 81], 16: [[0, 2], [21, 25]], 17: [[0, 2], 21, 23, 81], 18: [[0, 3], 21, 23, [25, 27], 81, 82], 19: [0], 20: [0], 51: [[0, 3], 21, 22], 52: [[0, 3], 21, 22, 24, 81], 53: [[0, 2], [21, 23], 81] }, 45: { 0: [0], 1: [[0, 9], [21, 27]], 2: [[0, 5], [21, 26]], 3: [[0, 5], 11, 12, [21, 32]], 4: [0, 1, [3, 6], 11, [21, 23], 81], 5: [[0, 3], 12, 21], 6: [[0, 3], 21, 81], 7: [[0, 3], 21, 22], 8: [[0, 4], 21, 81], 9: [[0, 3], [21, 24], 81], 10: [[0, 2], [21, 31]], 11: [[0, 2], [21, 23]], 12: [[0, 2], [21, 29], 81], 13: [[0, 2], [21, 24], 81], 14: [[0, 2], [21, 25], 81] }, 46: { 0: [0], 1: [0, 1, [5, 8]], 2: [0, 1], 3: [0, [21, 23]], 90: [[0, 3], [5, 7], [21, 39]] }, 50: { 0: [0], 1: [[0, 19]], 2: [0, [22, 38], [40, 43]], 3: [0, [81, 84]] }, 51: { 0: [0], 1: [0, 1, [4, 8], [12, 15], [21, 24], 29, 31, 32, [81, 84]], 3: [[0, 4], 11, 21, 22], 4: [[0, 3], 11, 21, 22], 5: [[0, 4], 21, 22, 24, 25], 6: [0, 1, 3, 23, 26, [81, 83]], 7: [0, 1, 3, 4, [22, 27], 81], 8: [[0, 2], 11, 12, [21, 24]], 9: [[0, 4], [21, 23]], 10: [[0, 2], 11, 24, 25, 28], 11: [[0, 2], [11, 13], 23, 24, 26, 29, 32, 33, 81], 13: [[0, 4], [21, 25], 81], 14: [[0, 2], [21, 25]], 15: [[0, 3], [21, 29]], 16: [[0, 3], [21, 23], 81], 17: [[0, 3], [21, 25], 81], 18: [[0, 3], [21, 27]], 19: [[0, 3], [21, 23]], 20: [[0, 2], 21, 22, 81], 32: [0, [21, 33]], 33: [0, [21, 38]], 34: [0, 1, [22, 37]] }, 52: { 0: [0], 1: [[0, 3], [11, 15], [21, 23], 81], 2: [0, 1, 3, 21, 22], 3: [[0, 3], [21, 30], 81, 82], 4: [[0, 2], [21, 25]], 5: [[0, 2], [21, 27]], 6: [[0, 3], [21, 28]], 22: [0, 1, [22, 30]], 23: [0, 1, [22, 28]], 24: [0, 1, [22, 28]], 26: [0, 1, [22, 36]], 27: [[0, 2], 22, 23, [25, 32]] }, 53: { 0: [0], 1: [[0, 3], [11, 14], 21, 22, [24, 29], 81], 3: [[0, 2], [21, 26], 28, 81], 4: [[0, 2], [21, 28]], 5: [[0, 2], [21, 24]], 6: [[0, 2], [21, 30]], 7: [[0, 2], [21, 24]], 8: [[0, 2], [21, 29]], 9: [[0, 2], [21, 27]], 23: [0, 1, [22, 29], 31], 25: [[0, 4], [22, 32]], 26: [0, 1, [21, 28]], 27: [0, 1, [22, 30]], 28: [0, 1, 22, 23], 29: [0, 1, [22, 32]], 31: [0, 2, 3, [22, 24]], 34: [0, [21, 23]], 33: [0, 21, [23, 25]], 35: [0, [21, 28]] }, 54: { 0: [0], 1: [[0, 2], [21, 27]], 21: [0, [21, 29], 32, 33], 22: [0, [21, 29], [31, 33]], 23: [0, 1, [22, 38]], 24: [0, [21, 31]], 25: [0, [21, 27]], 26: [0, [21, 27]] }, 61: { 0: [0], 1: [[0, 4], [11, 16], 22, [24, 26]], 2: [[0, 4], 22], 3: [[0, 4], [21, 24], [26, 31]], 4: [[0, 4], [22, 31], 81], 5: [[0, 2], [21, 28], 81, 82], 6: [[0, 2], [21, 32]], 7: [[0, 2], [21, 30]], 8: [[0, 2], [21, 31]], 9: [[0, 2], [21, 29]], 10: [[0, 2], [21, 26]] }, 62: { 0: [0], 1: [[0, 5], 11, [21, 23]], 2: [0, 1], 3: [[0, 2], 21], 4: [[0, 3], [21, 23]], 5: [[0, 3], [21, 25]], 6: [[0, 2], [21, 23]], 7: [[0, 2], [21, 25]], 8: [[0, 2], [21, 26]], 9: [[0, 2], [21, 24], 81, 82], 10: [[0, 2], [21, 27]], 11: [[0, 2], [21, 26]], 12: [[0, 2], [21, 28]], 24: [0, 21, [24, 29]], 26: [0, 21, [23, 30]], 29: [0, 1, [21, 27]], 30: [0, 1, [21, 27]] }, 63: { 0: [0], 1: [[0, 5], [21, 23]], 2: [0, 2, [21, 25]], 21: [0, [21, 23], [26, 28]], 22: [0, [21, 24]], 23: [0, [21, 24]], 25: [0, [21, 25]], 26: [0, [21, 26]], 27: [0, 1, [21, 26]], 28: [[0, 2], [21, 23]] }, 64: { 0: [0], 1: [0, 1, [4, 6], 21, 22, 81], 2: [[0, 3], 5, [21, 23]], 3: [[0, 3], [21, 24], 81], 4: [[0, 2], [21, 25]], 5: [[0, 2], 21, 22] }, 65: { 0: [0], 1: [[0, 9], 21], 2: [[0, 5]], 21: [0, 1, 22, 23], 22: [0, 1, 22, 23], 23: [[0, 3], [23, 25], 27, 28], 28: [0, 1, [22, 29]], 29: [0, 1, [22, 29]], 30: [0, 1, [22, 24]], 31: [0, 1, [21, 31]], 32: [0, 1, [21, 27]], 40: [0, 2, 3, [21, 28]], 42: [[0, 2], 21, [23, 26]], 43: [0, 1, [21, 26]], 90: [[0, 4]], 27: [[0, 2], 22, 23] }, 71: { 0: [0] }, 81: { 0: [0] }, 82: { 0: [0] } }; var provincial = parseInt(value.substr(0, 2), 10), prefectural = parseInt(value.substr(2, 2), 10), county = parseInt(value.substr(4, 2), 10); if (!adminDivisionCodes[provincial] || !adminDivisionCodes[provincial][prefectural]) { return false; } var inRange = false, rangeDef = adminDivisionCodes[provincial][prefectural]; for (var i = 0; i < rangeDef.length; i++) { if (($.isArray(rangeDef[i]) && rangeDef[i][0] <= county && county <= rangeDef[i][1]) || (!$.isArray(rangeDef[i]) && county === rangeDef[i])) { inRange = true; break; } } if (!inRange) { return false; } // Check date of birth var dob; if (value.length === 18) { dob = value.substr(6, 8); } else /* length == 15 */ { dob = '19' + value.substr(6, 6); } var year = parseInt(dob.substr(0, 4), 10), month = parseInt(dob.substr(4, 2), 10), day = parseInt(dob.substr(6, 2), 10); if (!FormValidation.Helper.date(year, month, day)) { return false; } // Check checksum (18-digit system only) if (value.length === 18) { var sum = 0, weight = [7, 9, 10, 5, 8, 4, 2, 1, 6, 3, 7, 9, 10, 5, 8, 4, 2]; for (i = 0; i < 17; i++) { sum += parseInt(value.charAt(i), 10) * weight[i]; } sum = (12 - (sum % 11)) % 11; var checksum = (value.charAt(17).toUpperCase() !== 'X') ? parseInt(value.charAt(17), 10) : 10; return checksum === sum; } return true; }, /** * Validate Czech national identification number (RC) * Examples: * - Valid: 7103192745, 991231123 * - Invalid: 1103492745, 590312123 * * @param {String} value The ID * @returns {Boolean} */ _cz: function(value) { if (!/^\d{9,10}$/.test(value)) { return false; } var year = 1900 + parseInt(value.substr(0, 2), 10), month = parseInt(value.substr(2, 2), 10) % 50 % 20, day = parseInt(value.substr(4, 2), 10); if (value.length === 9) { if (year >= 1980) { year -= 100; } if (year > 1953) { return false; } } else if (year < 1954) { year += 100; } if (!FormValidation.Helper.date(year, month, day)) { return false; } // Check that the birth date is not in the future if (value.length === 10) { var check = parseInt(value.substr(0, 9), 10) % 11; if (year < 1985) { check = check % 10; } return (check + '' === value.substr(9, 1)); } return true; }, /** * Validate Danish Personal Identification number (CPR) * Examples: * - Valid: 2110625629, 211062-5629 * - Invalid: 511062-5629 * * @see https://en.wikipedia.org/wiki/Personal_identification_number_(Denmark) * @param {String} value The ID * @returns {Boolean} */ _dk: function(value) { if (!/^[0-9]{6}[-]{0,1}[0-9]{4}$/.test(value)) { return false; } value = value.replace(/-/g, ''); var day = parseInt(value.substr(0, 2), 10), month = parseInt(value.substr(2, 2), 10), year = parseInt(value.substr(4, 2), 10); switch (true) { case ('5678'.indexOf(value.charAt(6)) !== -1 && year >= 58): year += 1800; break; case ('0123'.indexOf(value.charAt(6)) !== -1): case ('49'.indexOf(value.charAt(6)) !== -1 && year >= 37): year += 1900; break; default: year += 2000; break; } return FormValidation.Helper.date(year, month, day); }, /** * Validate Estonian Personal Identification Code (isikukood) * Examples: * - Valid: 37605030299 * * @see http://et.wikipedia.org/wiki/Isikukood * @param {String} value The ID * @returns {Boolean} */ _ee: function(value) { // Use the same format as Lithuanian Personal Code return this._lt(value); }, /** * Validate Spanish personal identity code (DNI) * Support i) DNI (for Spanish citizens), ii) NIE (for foreign people) * and iii) CIF (for legal entities) * * Examples: * - Valid: * i) 54362315K, 54362315-K * ii) X2482300W, X-2482300W, X-2482300-W * iii) A58818501, A-58818501 * - Invalid: * i) 54362315Z * ii) X-2482300A * iii) K58818501, G58818507 * * @see https://en.wikipedia.org/wiki/National_identification_number#Spain * @param {String} value The ID * @returns {Boolean} */ _es: function(value) { var isDNI = /^[0-9]{8}[-]{0,1}[A-HJ-NP-TV-Z]$/.test(value), isNIE = /^[XYZ][-]{0,1}[0-9]{7}[-]{0,1}[A-HJ-NP-TV-Z]$/.test(value), isCIF = /^[A-HNPQS][-]{0,1}[0-9]{7}[-]{0,1}[0-9A-J]$/.test(value); if (!isDNI && !isNIE && !isCIF) { return false; } value = value.replace(/-/g, ''); var check; if (isDNI || isNIE) { var index = 'XYZ'.indexOf(value.charAt(0)); if (index !== -1) { // It is NIE number value = index + value.substr(1) + ''; } check = parseInt(value.substr(0, 8), 10); check = 'TRWAGMYFPDXBNJZSQVHLCKE'[check % 23]; return (check === value.substr(8, 1)); } else { check = value.substr(1, 7); var letter = value[0], control = value.substr(-1), sum = 0; // The digits in the even positions are added to the sum directly. // The ones in the odd positions are multiplied by 2 and then added to the sum. // If the result of multiplying by 2 is 10 or higher, add the two digits // together and add that to the sum instead for (var i = 0; i < check.length; i++) { if (i % 2 !== 0) { sum += parseInt(check[i], 10); } else { var tmp = '' + (parseInt(check[i], 10) * 2); sum += parseInt(tmp[0], 10); if (tmp.length === 2) { sum += parseInt(tmp[1], 10); } } } // The control digit is calculated from the last digit of the sum. // If that last digit is not 0, subtract it from 10 var lastDigit = sum - (Math.floor(sum / 10) * 10); if (lastDigit !== 0) { lastDigit = 10 - lastDigit; } if ('KQS'.indexOf(letter) !== -1) { // If the CIF starts with a K, Q or S, the control digit must be a letter return (control === 'JABCDEFGHI'[lastDigit]); } else if ('ABEH'.indexOf(letter) !== -1) { // If it starts with A, B, E or H, it has to be a number return (control === ('' + lastDigit)); } else { // In any other case, it doesn't matter return (control === ('' + lastDigit) || control === 'JABCDEFGHI'[lastDigit]); } } }, /** * Validate Finnish Personal Identity Code (HETU) * Examples: * - Valid: 311280-888Y, 131052-308T * - Invalid: 131052-308U, 310252-308Y * * @param {String} value The ID * @returns {Boolean} */ _fi: function(value) { if (!/^[0-9]{6}[-+A][0-9]{3}[0-9ABCDEFHJKLMNPRSTUVWXY]$/.test(value)) { return false; } var day = parseInt(value.substr(0, 2), 10), month = parseInt(value.substr(2, 2), 10), year = parseInt(value.substr(4, 2), 10), centuries = { '+': 1800, '-': 1900, 'A': 2000 }; year = centuries[value.charAt(6)] + year; if (!FormValidation.Helper.date(year, month, day)) { return false; } var individual = parseInt(value.substr(7, 3), 10); if (individual < 2) { return false; } var n = value.substr(0, 6) + value.substr(7, 3) + ''; n = parseInt(n, 10); return '0123456789ABCDEFHJKLMNPRSTUVWXY'.charAt(n % 31) === value.charAt(10); }, /** * Validate Croatian personal identification number (OIB) * Examples: * - Valid: 33392005961 * - Invalid: 33392005962 * * @param {String} value The ID * @returns {Boolean} */ _hr: function(value) { if (!/^[0-9]{11}$/.test(value)) { return false; } return FormValidation.Helper.mod11And10(value); }, /** * Validate Irish Personal Public Service Number (PPS) * Examples: * - Valid: 6433435F, 6433435FT, 6433435FW, 6433435OA, 6433435IH, 1234567TW, 1234567FA * - Invalid: 6433435E, 6433435VH * * @see https://en.wikipedia.org/wiki/Personal_Public_Service_Number * @param {String} value The ID * @returns {Boolean} */ _ie: function(value) { if (!/^\d{7}[A-W][AHWTX]?$/.test(value)) { return false; } var getCheckDigit = function(value) { while (value.length < 7) { value = '0' + value; } var alphabet = 'WABCDEFGHIJKLMNOPQRSTUV', sum = 0; for (var i = 0; i < 7; i++) { sum += parseInt(value.charAt(i), 10) * (8 - i); } sum += 9 * alphabet.indexOf(value.substr(7)); return alphabet[sum % 23]; }; // 2013 format if (value.length === 9 && ('A' === value.charAt(8) || 'H' === value.charAt(8))) { return value.charAt(7) === getCheckDigit(value.substr(0, 7) + value.substr(8) + ''); } // The old format else { return value.charAt(7) === getCheckDigit(value.substr(0, 7)); } }, /** * Validate Iceland national identification number (Kennitala) * Examples: * - Valid: 120174-3399, 1201743399, 0902862349 * * @see http://en.wikipedia.org/wiki/Kennitala * @param {String} value The ID * @returns {Boolean} */ _is: function(value) { if (!/^[0-9]{6}[-]{0,1}[0-9]{4}$/.test(value)) { return false; } value = value.replace(/-/g, ''); var day = parseInt(value.substr(0, 2), 10), month = parseInt(value.substr(2, 2), 10), year = parseInt(value.substr(4, 2), 10), century = parseInt(value.charAt(9), 10); year = (century === 9) ? (1900 + year) : ((20 + century) * 100 + year); if (!FormValidation.Helper.date(year, month, day, true)) { return false; } // Validate the check digit var sum = 0, weight = [3, 2, 7, 6, 5, 4, 3, 2]; for (var i = 0; i < 8; i++) { sum += parseInt(value.charAt(i), 10) * weight[i]; } sum = 11 - sum % 11; return (sum + '' === value.charAt(8)); }, /** * Validate Lithuanian Personal Code (Asmens kodas) * Examples: * - Valid: 38703181745 * - Invalid: 38703181746, 78703181745, 38703421745 * * @see http://en.wikipedia.org/wiki/National_identification_number#Lithuania * @see http://www.adomas.org/midi2007/pcode.html * @param {String} value The ID * @returns {Boolean} */ _lt: function(value) { if (!/^[0-9]{11}$/.test(value)) { return false; } var gender = parseInt(value.charAt(0), 10), year = parseInt(value.substr(1, 2), 10), month = parseInt(value.substr(3, 2), 10), day = parseInt(value.substr(5, 2), 10), century = (gender % 2 === 0) ? (17 + gender / 2) : (17 + (gender + 1) / 2); year = century * 100 + year; if (!FormValidation.Helper.date(year, month, day, true)) { return false; } // Validate the check digit var sum = 0, weight = [1, 2, 3, 4, 5, 6, 7, 8, 9, 1]; for (var i = 0; i < 10; i++) { sum += parseInt(value.charAt(i), 10) * weight[i]; } sum = sum % 11; if (sum !== 10) { return sum + '' === value.charAt(10); } // Re-calculate the check digit sum = 0; weight = [3, 4, 5, 6, 7, 8, 9, 1, 2, 3]; for (i = 0; i < 10; i++) { sum += parseInt(value.charAt(i), 10) * weight[i]; } sum = sum % 11; if (sum === 10) { sum = 0; } return (sum + '' === value.charAt(10)); }, /** * Validate Latvian Personal Code (Personas kods) * Examples: * - Valid: 161175-19997, 16117519997 * - Invalid: 161375-19997 * * @see http://laacz.lv/2006/11/25/pk-parbaudes-algoritms/ * @param {String} value The ID * @returns {Boolean} */ _lv: function(value) { if (!/^[0-9]{6}[-]{0,1}[0-9]{5}$/.test(value)) { return false; } value = value.replace(/\D/g, ''); // Check birth date var day = parseInt(value.substr(0, 2), 10), month = parseInt(value.substr(2, 2), 10), year = parseInt(value.substr(4, 2), 10); year = year + 1800 + parseInt(value.charAt(6), 10) * 100; if (!FormValidation.Helper.date(year, month, day, true)) { return false; } // Check personal code var sum = 0, weight = [10, 5, 8, 4, 2, 1, 6, 3, 7, 9]; for (var i = 0; i < 10; i++) { sum += parseInt(value.charAt(i), 10) * weight[i]; } sum = (sum + 1) % 11 % 10; return (sum + '' === value.charAt(10)); }, /** * Validate Dutch national identification number (BSN) * Examples: * - Valid: 111222333, 941331490, 9413.31.490 * - Invalid: 111252333 * * @see https://nl.wikipedia.org/wiki/Burgerservicenummer * @param {String} value The ID * @returns {Boolean} */ _nl: function(value) { while (value.length < 9) { value = '0' + value; } if (!/^[0-9]{4}[.]{0,1}[0-9]{2}[.]{0,1}[0-9]{3}$/.test(value)) { return false; } value = value.replace(/\./g, ''); if (parseInt(value, 10) === 0) { return false; } var sum = 0, length = value.length; for (var i = 0; i < length - 1; i++) { sum += (9 - i) * parseInt(value.charAt(i), 10); } sum = sum % 11; if (sum === 10) { sum = 0; } return (sum + '' === value.charAt(length - 1)); }, /** * Validate Poland citizen number (PESEL) * * @see http://en.wikipedia.org/wiki/National_identification_number#Poland * @see http://en.wikipedia.org/wiki/PESEL * @param {String} value The ID * @returns {Boolean} */ _pl: function(value) { if (!/^[0-9]{11