Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add Canada SIN generator in Faker::Code #877

Merged
merged 2 commits into from
Jun 10, 2018
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
### Latest update: 2018-06-09

### Feature Request
- [PR #877](https://github.com/stympy/faker/pull/877) Add Canada SIN generator in Faker::Code [@gkunwar](https://github.com/gkunwar)
- [PR #1268](https://github.com/stympy/faker/pull/1268) Add Faker::Nation.national_sport [@gkunwar](https://github.com/gkunwar)
- [PR #1273](https://github.com/stympy/faker/pull/1273) Add Faker::Device [@vbrazo](https://github.com/vbrazo)
- [PR #1272](https://github.com/stympy/faker/pull/1272) Add Faker::DrWho.actor [@timcustard](https://github.com/timcustard)
Expand Down
2 changes: 2 additions & 0 deletions doc/code.md
Original file line number Diff line number Diff line change
Expand Up @@ -16,4 +16,6 @@ Faker::Code.nric(27, 34) #=> S8505970Z
Faker::Code.imei #= "546327785982623"

Faker::Code.asin #=> "B00000IGGJ"

Fake::Code:sin #=> "159160274"
```
43 changes: 43 additions & 0 deletions lib/faker/code.rb
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,25 @@ def asin
fetch('code.asin')
end

# Generates Social Insurance Number issued in Canada
# https://en.wikipedia.org/wiki/Social_Insurance_Number
def sin
# 1 - province or temporary resident
# 2-8 - random numbers
# 9 - checksum

# 1st digit. 8,0 are not used
registry = Faker::Base.sample([1, 2, 3, 4, 5, 6, 7, 9]).to_s

# generate 2nd to 8th
partial = Array.new(7) { Faker::Config.random.rand(0..9) }.join

# Generate 9th digit
check_digit = generate_sin_check_digit(registry + partial + '0').to_s

registry + partial + check_digit
end

private

# Reporting body identifier
Expand Down Expand Up @@ -138,6 +157,30 @@ def generate_nric_check_alphabet(values, prefix)
total += 4 if prefix == 'T'
%w[A B C D E F G H I Z J][10 - total % 11]
end

def generate_sin_check_digit(digits)
# Fast Luhn checksum code from luhn.js:
# https://gist.github.com/ShirtlessKirk/2134376

len = 9
mul = 0

luhn_arr = [
[0, 1, 2, 3, 4, 5, 6, 7, 8, 9],
[0, 2, 4, 6, 8, 1, 3, 5, 7, 9]
]
sum = 0

while len > 0
len -= 1
num = digits[len].to_i
sum += luhn_arr[mul][num]
mul ^= 1
end

checksum = sum % 10
checksum.zero? ? checksum : (10 - checksum)
end
end
end
end
6 changes: 6 additions & 0 deletions test/test_faker_code.rb
Original file line number Diff line number Diff line change
Expand Up @@ -53,6 +53,12 @@ def test_imei_luhn_value
assert luhn_checksum_valid(@tester.imei)
end

def test_sin
assert @tester.sin.match(/\d{9}/)
assert @tester.sin.length == 9
assert luhn_checksum_valid(@tester.sin)
end

def luhn_checksum_valid(numbers)
sum = 0
i = 0
Expand Down