msr90

- Unnamed repository; edit this file 'description' to name the repository.
git clone git://git.acid.vegas/-c.git
Log | Files | Refs | Archive | README | LICENSE

commit f3a54fc25cc33e5837f122a4e5b89ca16e5d6b05
parent 6d57a8552a34fa8a5f3245cec25e7b6b99346046
Author: acidvegas <acid.vegas@acid.vegas>
Date: Sun, 12 May 2024 03:44:49 -0400

Added luhn algorithm example WITH THE OL MODULO 10

Diffstat:
MREADME.md | 27++++++++++++++++-----------
Aluhn_algo.py | 41+++++++++++++++++++++++++++++++++++++++++

2 files changed, 57 insertions(+), 11 deletions(-)

diff --git a/README.md b/README.md
@@ -99,17 +99,22 @@ Most cards do not even use a 3rd track, and is mostly un-used worldwide.
 | 9      | For assignment by national standards bodies *(next 3 digits are [ISO 3166-1](https://en.wikipedia.org/wiki/ISO_3166-1))* |
 
 ### Issuer Identification Number *(IIN)*
-| Issuer                    | INN Range                       | PAN Digits |
-| ------------------------- | ------------------------------- | ---------- |
-| American Express          | 34-37                           | 15         |
-| China Union Pay           | 62                              | 16-19      |
-| Diners Club International | 36, 38, 39, 309, 300-3005       | 14         |
-| Discover                  | 65, 644-649, 6011 622126-622925 | 16, 19     |
-| JCB                       | 3528-3589                       | 16         |
-| Maestro                   | 50, 56-69                       | 12-19      |
-| Mastercard                | 51-55, 2221-2720                | 16         |
-| RuPay                     | 607                             | 16         |
-| Visa                      | 4                               | 12, 16, 19 |
+| Issuer                    | INN Range                        | PAN Digits |
+| ------------------------- | -------------------------------- | ---------- |
+| American Express          | 34-37                            | 15         |
+| China Union Pay           | 62                               | 16-19      |
+| Diners Club International | 36, 38, 39, 309, 300-3005        | 14         |
+| Discover                  | 65, 644-649, 6011, 622126-622925 | 16, 19     |
+| JCB                       | 3528-3589                        | 16         |
+| Maestro                   | 50, 56-69                        | 12-19      |
+| Mastercard                | 51-55, 2221-2720                 | 16         |
+| RuPay                     | 607                              | 16         |
+| Visa                      | 4                                | 12, 16, 19 |
+
+## Notes
+The [Luhn Algorithm](https://en.wikipedia.org/wiki/Luhn_algorithm) or modulo-10 Algorithm *([example python code](./luhn_algo.py))* is used to determine the last digit of the account number, also known as the Check Number.
+
+This number should be divisible by 10, hence "modulo-10" ;)
 
 ## References
 - [Digital Card](https://en.wikipedia.org/wiki/Digital_card)
diff --git a/luhn_algo.py b/luhn_algo.py
@@ -0,0 +1,41 @@
+#!/usr/bin/env python
+# Luhn Algorithm Example - Developed by acidvegas in Python (https://git.acid.vegas/msr90)
+
+def modulus10(card_number: str) -> str:
+    '''
+    Validate a card number using the Luhn Algorithm
+
+    :param card_number: The card number to validate
+    '''
+   
+    digits = [int(d) for d in card_number]
+    total_sum = 0
+    reversed_digits = digits[::-1]
+
+    for i in range(len(reversed_digits)):
+        digit = reversed_digits[i]
+
+        if i % 2 != 0:
+            digit = digit * 2
+
+        if digit > 9:
+            digit -= 9
+
+        total_sum += digit
+
+    check_digit = (10 - (total_sum % 10)) % 10
+    full_card_number = card_number + str(check_digit)
+    
+    if (total_sum + check_digit) % 10 != 0:
+        raise ValueError('failed luhn check (non-divisible by 10)')
+
+    return full_card_number
+
+
+if __name__ == '__main__':
+    card_number = input('Enter your card number without the last digit:')
+
+    if not card_number.isdigit():
+        raise ValueError('invalid card number')
+    
+    print(f'Full card number: {modulus10(card_number)}')