/*
* Validator checking the correctness of the PESEL number (format, checksum, and date of birth correctness).
*/
function callService(context) {
const peselInput = context.getFirstParameter('pesel');
if (isInputEmpty(peselInput)) {
return [];
}
// A) Format verification (exactly 11 digits)
if (!peselInput.match(/^[0-9]{11}$/)) {
return [{
'key': 'pl.error.invalidPeselFormat',
'parameters': [peselInput]
}];
}
// B) Excluding a PESEL made up of all zeros
if (peselInput == "00000000000") {
return [{
'key': 'pl.error.peselAllZeros',
'parameters': [peselInput]
}];
}
// C) Checking the PESEL checksum
if (!isValidChecksum(peselInput)) {
return [{
'key': 'pl.error.invalidPeselChecksum',
'parameters': [peselInput]
}];
}
// D) Verifying the date of birth correctness
const year = getBirthYear(peselInput);
const month = getBirthMonth(peselInput) + 1;
const day = getBirthDay(peselInput);
if (isMonthAndDayCorrect(year, month, day) == false) {
return [{
'key': 'pl.error.invalidPeselBirthDate',
'parameters': [peselInput]
}];
}
return [];
/*
* Checks whether the provided value is empty.
*/
function isInputEmpty(value) {
return value == null || String(value).trim() === '';
}
/*
* Calculates and validates the PESEL checksum digit.
*/
function isValidChecksum(pesel) {
const weight = [1, 3, 7, 9, 1, 3, 7, 9, 1, 3];
const peselDigits = pesel.split('').map(Number);
let sum = 0;
for (let i = 0; i < weight.length; i++) {
sum += peselDigits[i] * weight[i];
}
const controlDigit = peselDigits[10];
const lastNumber = sum % 10;
const calculatedControlDigit = (10 - lastNumber) % 10;
return calculatedControlDigit === controlDigit;
}
/*
* Calculates the birth year from the PESEL number.
*/
function getBirthYear(pesel) {
let year = 10 * parseInt(pesel[0]);
year += parseInt(pesel[1]);
let month = 10 * parseInt(pesel[2]);
month += parseInt(pesel[3]);
if (month > 80 && month < 93) {
year += 1800;
} else if (month > 0 && month < 13) {
year += 1900;
} else if (month > 20 && month < 33) {
year += 2000;
} else if (month > 40 && month < 53) {
year += 2100;
} else if (month > 60 && month < 73) {
year += 2200;
}
return year;
}
/*
* Calculates the month of birth from the PESEL number.
*/
function getBirthMonth(pesel) {
let month = 10 * parseInt(pesel[2]);
month += parseInt(pesel[3]);
if (month > 80 && month < 93) {
month -= 80;
} else if (month > 20 && month < 33) {
month -= 20;
} else if (month > 40 && month < 53) {
month -= 40;
} else if (month > 60 && month < 73) {
month -= 60;
}
return month - 1;
}
/*
* Calculates the day of birth from the PESEL number.
*/
function getBirthDay(pesel) {
let day = 10 * parseInt(pesel[4]);
day += parseInt(pesel[5]);
return day;
}
/*
* Verifies whether the day and month are correct for the given year (including leap years).
*/
function isMonthAndDayCorrect(yearNumber, monthNumber, dayNumber) {
const longMonths = [1, 3, 5, 7, 8, 10, 12];
const shortMonths = [4, 6, 9, 11];
if (longMonths.indexOf(monthNumber) != -1) {
if (dayNumber > 31) {
return false;
} return true;
} else if (shortMonths.indexOf(monthNumber) != -1) {
if (dayNumber > 30) {
return false;
} return true;
} else if (monthNumber == 2) {
if (((yearNumber % 4 == 0) && (yearNumber % 100 != 0)) || (yearNumber % 400 == 0)) {
if (dayNumber > 29) {
return false;
} return true;
} else {
if (dayNumber > 28) {
return false;
} return true;
}
} else {
return false;
}
}
}