diff options
| author | Eric Cheng <[email protected]> | 2022-05-25 12:59:06 -0400 |
|---|---|---|
| committer | GitHub <[email protected]> | 2022-05-25 16:59:06 +0000 |
| commit | c95826f348bf317d3cff240a7ebbae4bd80956f6 (patch) | |
| tree | 39004bab49760f632f61a6b83212194873048f25 /src | |
| parent | 4e38a7083ab02567c019b3078b63801fe73a4333 (diff) | |
| download | faker-c95826f348bf317d3cff240a7ebbae4bd80956f6.tar.xz faker-c95826f348bf317d3cff240a7ebbae4bd80956f6.zip | |
fix: Luhn generation algorithms and tests (#980)
Co-authored-by: ST-DDT <[email protected]>
Diffstat (limited to 'src')
| -rw-r--r-- | src/modules/helpers/index.ts | 23 | ||||
| -rw-r--r-- | src/modules/helpers/luhn-check.ts | 42 |
2 files changed, 44 insertions, 21 deletions
diff --git a/src/modules/helpers/index.ts b/src/modules/helpers/index.ts index ac302c6d..a68b66ae 100644 --- a/src/modules/helpers/index.ts +++ b/src/modules/helpers/index.ts @@ -1,4 +1,5 @@ import type { Faker } from '../..'; +import { luhnCheckValue } from './luhn-check'; /** * Module with various helper methods that transform the method input rather than returning values from locales. @@ -141,30 +142,10 @@ export class Helpers { ): string { // default values required for calling method without arguments - // Function calculating the Luhn checksum of a number string - const getCheckBit = (number: number[]) => { - number.reverse(); - number = number.map((num, index) => { - if (index % 2 === 0) { - num *= 2; - if (num > 9) { - num -= 9; - } - } - return num; - }); - const sum = number.reduce((prev, curr) => prev + curr); - return sum % 10; - }; - string = this.regexpStyleStringParse(string); // replace [4-9] with a random number in range etc... string = this.replaceSymbolWithNumber(string, symbol); // replace ### with random numbers - const numberList = string - .replace(/\D/g, '') - .split('') - .map((num) => parseInt(num)); - const checkNum = getCheckBit(numberList); + const checkNum = luhnCheckValue(string); return string.replace('L', String(checkNum)); } diff --git a/src/modules/helpers/luhn-check.ts b/src/modules/helpers/luhn-check.ts new file mode 100644 index 00000000..9cfcc577 --- /dev/null +++ b/src/modules/helpers/luhn-check.ts @@ -0,0 +1,42 @@ +/** + * Checks that the given string passes the luhn algorithm. + * + * @param str The string to validate. + */ +export function luhnCheck(str: string): boolean { + return luhnChecksum(str) === 0; +} + +/** + * Calculates the luhn check value for the given string. + * + * @param str The string to calculate the check value for. + * May contain the `L` placeholder at the end. + */ +export function luhnCheckValue(str: string): number { + const checksum = luhnChecksum(str.replace(/L?$/, '0')); + return checksum === 0 ? 0 : 10 - checksum; +} + +/** + * Calculates the luhn checksum value for the given value. + * + * @param str The string to generate the checksum for. + */ +function luhnChecksum(str: string): number { + str = str.replace(/[\s-]/g, ''); + let sum = 0; + let alternate = false; + for (let i = str.length - 1; i >= 0; i--) { + let n = parseInt(str.substring(i, i + 1)); + if (alternate) { + n *= 2; + if (n > 9) { + n = (n % 10) + 1; + } + } + sum += n; + alternate = !alternate; + } + return sum % 10; +} |
