romanianvalidators 0.1.6 → 0.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: b6f0345b9d1c418dd361412bdcf98b68134a099b
4
- data.tar.gz: 9c44ad509cbed0a6ffb8456995ce78099b122714
3
+ metadata.gz: 7ad45c5638e6e12b9fd6e9914810400220a0de56
4
+ data.tar.gz: a8ca1b49f450c18bd755980695c27e1d70abe65c
5
5
  SHA512:
6
- metadata.gz: 6ca4dc092344fe15b1803c86f48df7de87b3373ae6c5074903d04c11dca5618f44af1201543d58a9112b1187c176c3d1b4608f938166ee794ff65147c13f5b0f
7
- data.tar.gz: b2bc80c161f204a22b82d572b4d753dc824302481dc58e3a11ef0d499f42bdc13185ae115e4f95077f4e9d1d8ae7e353e75c5d225da6ac2adbd1bda45b98cce0
6
+ metadata.gz: 68dc85bf25ffa47139957327a360fb62f6dab5d39a837c14f2cee4c7243764a1931a91a940cfd89789cfc31899092d134dc01c42ddbfa55e0c3535485041f218
7
+ data.tar.gz: 9c16e8cf4a240f82fa6b9da7deff1db68526f36dd050848ccf8bba8faf83cb667d4482a06730634a191cc169083238ec3113f1285d3d9424fba3f08e288fb975
@@ -0,0 +1,13 @@
1
+ AllCops:
2
+ TargetRubyVersion: 2.3
3
+ Exclude:
4
+ - db/schema.rb
5
+ - SCRATCHPAD.rb
6
+ Documentation:
7
+ Enabled: false
8
+ Style/FrozenStringLiteralComment:
9
+ Enabled: false
10
+ Metrics/LineLength:
11
+ Max: 120
12
+ Metrics/AbcSize:
13
+ Max: 20
@@ -1 +1 @@
1
- ruby-2.1.2
1
+ ruby-2.3.0
@@ -1,7 +1,10 @@
1
1
  language: ruby
2
+ before_install:
3
+ - gem install bundler
2
4
  rvm:
3
5
  - 1.9.3
4
- - rbx-19mode
6
+ - rbx-3
5
7
  - ruby-head
6
8
  - 2.0.0
7
9
  - 2.1.2
10
+ - 2.3.0
data/README.md CHANGED
@@ -1,55 +1,100 @@
1
- # Romanian Validators [![Build Status](https://travis-ci.org/mtarnovan/romanianvalidators.png)](https://travis-ci.org/mtarnovan/romanianvalidators) [![Gem Version](https://badge.fury.io/rb/romanianvalidators.png)](http://badge.fury.io/rb/romanianvalidators) [![Code Climate](https://codeclimate.com/github/mtarnovan/romanianvalidators.png)](https://codeclimate.com/github/mtarnovan/romanianvalidators)
1
+ # Romanian Validators [![Build Status](https://travis-ci.org/mtarnovan/romanianvalidators.svg?branch=master)](https://travis-ci.org/mtarnovan/romanianvalidators) [![Gem Version](https://badge.fury.io/rb/romanianvalidators.svg)](https://badge.fury.io/rb/romanianvalidators) [![Code Climate](https://codeclimate.com/github/mtarnovan/romanianvalidators/badges/gpa.svg)](https://codeclimate.com/github/mtarnovan/romanianvalidators)
2
2
 
3
- ActiveModel validators for:
3
+ Validators for:
4
4
 
5
5
  * Cod Numeric Personal (CNP)
6
6
  * Cod de identificare fiscală (CIF) and
7
7
  * IBAN (only Romanian format as published by Romanian National Bank).
8
8
  * BIC
9
9
 
10
- Extracted from [Factureaza.ro](https://factureaza.ro), our online invoicing solution for the Romanian market.
10
+ Extracted from [openapi.ro](https://openapi.ro), business APIs for Romanian developers.
11
+ Includes `ActiveModel` validators.
11
12
 
12
13
  ## Installation
13
14
 
14
- ### In a Rails 3 app, as a gem
15
+ Include it in your `Gemfile`. If you just want the validation, without `ActiveModel`, use:
15
16
 
16
- First include it in your Gemfile.
17
+ gem 'romanianvalidators'
17
18
 
18
- $ cat Gemfile
19
- ...
20
- gem 'romanianvalidations'
21
- ...
19
+ If you want ActiveModel integration, use instead:
22
20
 
23
- Next install it with Bundler.
21
+ gem 'romanianvalidators', require: 'romanian_validators/active_model'
24
22
 
25
- $ bundle install
23
+ Has no other dependency (other than `ActiveModel` if you require it).
26
24
 
27
- Has no other dependency than `ActiveModel`, so it should work without Rails too.
28
-
29
- Tested with MRI 1.8.7, 1.9.3, 2.0.0, REE, Rubinius and JRuby (see `.travis.yml`)
25
+ Tested with MRI 1.9.3, 2.0, 2.1, 2.3, REE, Rubinius and JRuby (see `.travis.yml`)
30
26
 
31
27
  ## Usage
32
28
 
33
- In your models (`ActiveModel`), the gem provides the following new validators:
34
- * CIF
35
- * CNP
36
- * IBAN
37
- * BIC
29
+ Without `ActiveModel`, just call the `valid?` method on the corresponding module
30
+
31
+ ```ruby
32
+ > RomanianValidators::Cif.valid?(13548146)
33
+ => true
34
+ > RomanianValidators::Iban.valid?(123)
35
+ => false
36
+ ```
38
37
 
39
- The algorithms for validation are found in the source code.
38
+ With `ActiveModel`, include it in your model
40
39
 
40
+ ```ruby
41
+ include RomanianValidators::ActiveModel::Validations
42
+ ```
43
+
44
+ then use like this:
45
+
46
+ ```ruby
47
+ validates :my_attribute, cif: true
48
+ ```
49
+
50
+ Example:
41
51
  ```ruby
42
52
  class User
43
- validates :cnp, cnp: { message: 'This is not a valid CNP' }
44
- validates :company_cif, cif: true
53
+ include ActiveModel::Model
54
+ include RomanianValidators::ActiveModel::Validations
55
+ attr_accessor :cnp, :company_cif
56
+
57
+ validates :cnp, cnp: { message: 'This is not a valid CNP' }
58
+ validates :company_cif, cif: true
45
59
  end
60
+
61
+ > u = User.new(cnp: 123, company_cif: 123)
62
+ => #<User:0x007fbf7f959b38 @cnp=123, @company_cif=123>
63
+ > u.valid?
64
+ => false
65
+ > u.errors
66
+ => #<ActiveModel::Errors:0x007fbf80958548 @base=#<User:0x007fbf7f959b38 @cnp=123, @company_cif=123, @validation_context=nil, @errors=#<ActiveModel::Errors:0x007fbf80958548 ...>>, @messages={:cnp=>["This is not a valid CNP"], :company_cif=>["is invalid"]}, @details={:cnp=>[{:error=>"This is not a valid CNP"}], :company_cif=>[{:error=>:invalid}]}>
67
+ ```
68
+
69
+ For CIFs, a (lazy) enumerator is provided. This enumerator is significantly
70
+ more efficient than iterating over a range of numbers and filtering valid CIFs, because
71
+ it generates the control digit from `cif % 10` directly.
72
+
73
+ Example:
74
+
75
+ ```ruby
76
+ > RomanianValidators::Cif.enumerator(1).take(10).to_a
77
+ => [19, 27, 35, 43, 51, 60, 78, 86, 94, 108]
78
+ > RomanianValidators::Cif.enumerator(1_000_000, :down).take(10).to_a
79
+ => [999993, 999985, 999977, 999969, 999950, 999942, 999934, 999926, 999918, 999900]
80
+ ```
81
+
82
+ ### Upgrading
83
+
84
+ If upgrading from `0.1.x`, note that the `ActiveModel` validations are now in a separate module so you need to add
85
+ `include RomanianValidators::ActiveModel::Validations` in your models. Additionaly you need to add a `require` in your Gemfile (again, only if using `ActiveModel`):
86
+
87
+ ```ruby
88
+ gem 'romanianvalidators', require: 'romanianvalidators/active_model'
46
89
  ```
47
90
 
48
- ### TODO
91
+ ### Changelog
49
92
 
50
- * test more edge cases
51
- * add javascript validation ?
93
+ #### 0.2.0
94
+ * moved validations from `ActiveModel::Validations` to `RomanianValidators::ActiveModel::Validations`.
95
+ This module must be manually required in models.
96
+ * added a lazy enumerator that generates valid CIFs: `RomanianValidators::Cif.enumerator(start, direction = :up)`
52
97
 
53
98
  ### Copyright
54
99
 
55
- Copyright (c) 2007-2014 Mihai Târnovan. MIT LICENSE. See LICENSE for details.
100
+ Copyright (c) 2007-2018 Mihai Târnovan. MIT LICENSE. See LICENSE for details.
@@ -1,34 +1,9 @@
1
- require 'active_model'
2
-
3
- module ActiveModel
4
- module Validations
5
- def self.romanianvalidators
6
- %w(cif cnp iban bic)
7
- end
8
-
9
- module EmptyBlankEachValidator
10
- def validate_each(record, attribute, value)
11
- allow_blank = options.fetch(:allow_blank, false)
12
- allow_nil = options.fetch(:allow_nil, false)
13
- message = options.fetch(:message, :invalid)
14
- record.errors.add_on_empty(attribute) && return if value.nil? && !allow_nil
15
- record.errors.add_on_blank(attribute) && return if value.blank? && !allow_blank
16
- record.errors.add(attribute, message) && return unless valid?(value)
17
- end
18
- end
19
-
20
- romanianvalidators.each do |validator_name|
21
- require "active_model/validations/#{validator_name}_validator"
22
- end
1
+ module RomanianValidators
2
+ def self.available_validators
3
+ %w(cif cnp iban bic)
4
+ end
23
5
 
24
- module HelperMethods
25
- ActiveModel::Validations.romanianvalidators.each do |validator|
26
- define_method('validates_' + validator) do |*fields|
27
- options ||= (fields.delete(fields.find { |f| f.is_a? Hash })) || true
28
- args = fields.push(validator => options)
29
- validates(*args)
30
- end
31
- end
32
- end
6
+ available_validators.each do |validator_name|
7
+ require "romanianvalidators/#{validator_name}"
33
8
  end
34
9
  end
@@ -0,0 +1,32 @@
1
+ require 'romanianvalidators'
2
+ require 'active_model'
3
+ module RomanianValidators
4
+ module ActiveModel
5
+ module Validations
6
+ module EmptyBlankEachValidator
7
+ def validate_each(record, attribute, value)
8
+ allow_blank = options.fetch(:allow_blank, false)
9
+ allow_nil = options.fetch(:allow_nil, false)
10
+ message = options.fetch(:message, :invalid)
11
+ record.errors.add_on_empty(attribute) && return if value.nil? && !allow_nil
12
+ record.errors.add_on_blank(attribute) && return if value.blank? && !allow_blank
13
+ record.errors.add(attribute, message) && return unless valid?(value)
14
+ end
15
+ end
16
+
17
+ RomanianValidators.available_validators.each do |validator_name|
18
+ require "romanianvalidators/active_model/validations/#{validator_name}_validator"
19
+ end
20
+
21
+ module HelperMethods
22
+ RomanianValidators.available_validators.each do |validator|
23
+ define_method('validates_' + validator) do |*fields|
24
+ options ||= fields.delete(fields.find { |f| f.is_a? Hash }) || true
25
+ args = fields.push(validator => options)
26
+ validates(*args)
27
+ end
28
+ end
29
+ end
30
+ end
31
+ end
32
+ end
@@ -0,0 +1,13 @@
1
+ module RomanianValidators
2
+ module ActiveModel
3
+ module Validations
4
+ class BicValidator < ::ActiveModel::EachValidator
5
+ include ActiveModel::Validations::EmptyBlankEachValidator
6
+
7
+ def valid?(bic)
8
+ RomanianValidators::Bic.valid?(bic)
9
+ end
10
+ end
11
+ end
12
+ end
13
+ end
@@ -0,0 +1,13 @@
1
+ module RomanianValidators
2
+ module ActiveModel
3
+ module Validations
4
+ class CifValidator < ::ActiveModel::EachValidator
5
+ include ActiveModel::Validations::EmptyBlankEachValidator
6
+
7
+ def valid?(cif)
8
+ RomanianValidators::Cif.valid?(cif)
9
+ end
10
+ end
11
+ end
12
+ end
13
+ end
@@ -0,0 +1,13 @@
1
+ module RomanianValidators
2
+ module ActiveModel
3
+ module Validations
4
+ class CnpValidator < ::ActiveModel::EachValidator
5
+ include ActiveModel::Validations::EmptyBlankEachValidator
6
+
7
+ def valid?(cnp)
8
+ RomanianValidators::Cnp.valid?(cnp)
9
+ end
10
+ end
11
+ end
12
+ end
13
+ end
@@ -0,0 +1,13 @@
1
+ module RomanianValidators
2
+ module ActiveModel
3
+ module Validations
4
+ class IbanValidator < ::ActiveModel::EachValidator
5
+ include ActiveModel::Validations::EmptyBlankEachValidator
6
+
7
+ def valid?(iban)
8
+ RomanianValidators::Iban.valid?(iban)
9
+ end
10
+ end
11
+ end
12
+ end
13
+ end
@@ -0,0 +1,25 @@
1
+ module RomanianValidators
2
+ module Bic
3
+ COUNTRY_CODES =
4
+ %w(AF AL DZ AS AD AO AI AG AR AM AW AU AT AZ BS BH BD BB BY BE BZ BJ BM
5
+ BT BO BA BW BR BN BG BF BI KH CM CA CV KY CF TD CL CN CO KM CG CD CK CR
6
+ CI HR CU CY CZ DK DJ DM DO EC EG SV GQ ER EE ET FK FO FJ FI FR GF PF GA
7
+ GM GE DE GH GI GR GL GD GP GU GT GN GW GY HT VA HN HK HU IS IN ID IR IQ
8
+ IE IL IT JM JP JO KZ KE KI KP KR KW KG LA LV LB LS LR LY LI LT LU MO MK
9
+ MG MW MY MV ML MT MH MQ MR MU MX FM MD MC MN MS MA MZ MM NA NR NP NL AN
10
+ NC NZ NI NE NG NU NF MP NO OM PK PW PA PG PY PE PH PN PL PT PR QA RE RO
11
+ RU RW SH KN LC PM VC WS SM ST SA SN SC SL SG SK SI SB SO ZA ES LK SD SR
12
+ SJ SZ SE CH SY TW TJ TZ TH TG TK TO TT TN TR TM TC TV UG UA AE GB US UY
13
+ UZ VU VE VN VG VI WF EH YE ZM ZW).freeze
14
+
15
+ module_function
16
+
17
+ # This is only a basic validation of a BIC
18
+ # http://www.swift.com/biconline/index.cfm?fuseaction=display_aboutbic
19
+ def valid?(bic)
20
+ return false unless bic.size == 8 || bic.size == 11 # length 8 or 11
21
+ return false unless (bic[0..3] =~ /[^A-Z]/).nil? # first 4 must be letters only
22
+ COUNTRY_CODES.include?(bic[4..5])
23
+ end
24
+ end
25
+ end
@@ -0,0 +1,61 @@
1
+ module RomanianValidators
2
+ module Cif
3
+ TEST_KEY = '753217532'.to_s.chars.map(&:to_i).reverse.freeze
4
+ FIRST_CIF = 19 # used to break iteration when direction is :down
5
+
6
+ module_function
7
+
8
+ def valid?(cif)
9
+ return false unless well_formed?(cif)
10
+ control, sum = control_sum(cif, TEST_KEY)
11
+ sum * 10 % 11 % 10 == control
12
+ end
13
+
14
+ def well_formed?(cif)
15
+ cif.present? && (2..10).cover?(cif.size) && (cif =~ /[^0-9]/).nil?
16
+ end
17
+
18
+ def next_valid_cif(cif)
19
+ control, sum = control_sum(cif, TEST_KEY)
20
+ last_digit_of_next_cif = sum * 10 % 11 % 10
21
+
22
+ if last_digit_of_next_cif < control
23
+ next_valid_cif(((cif / 10) + 1) * 10)
24
+ else
25
+ replace_last_digit(cif, last_digit_of_next_cif)
26
+ end
27
+ end
28
+
29
+ def prev_valid_cif(cif)
30
+ control, sum = control_sum(cif, TEST_KEY)
31
+ last_digit_of_next_cif = sum * 10 % 11 % 10
32
+
33
+ if last_digit_of_next_cif > control
34
+ next_valid_cif(((cif / 10) - 1) * 10)
35
+ else
36
+ replace_last_digit(cif, last_digit_of_next_cif)
37
+ end
38
+ end
39
+
40
+ def enumerator(start, direction = :up)
41
+ Enumerator.new do |yielder|
42
+ memo = direction == :up ? next_valid_cif(start + 1) : prev_valid_cif(start - 1)
43
+ loop do
44
+ yielder << memo
45
+ memo = direction == :up ? next_valid_cif(memo + 1) : prev_valid_cif(memo - 1)
46
+ break if memo < FIRST_CIF
47
+ end
48
+ end.lazy
49
+ end
50
+
51
+ def replace_last_digit(number, digit)
52
+ ((number / 10).to_s + digit.to_s).to_i
53
+ end
54
+
55
+ def control_sum(n, test_key)
56
+ control, *rest_digits = n.to_s.chars.map(&:to_i).reverse
57
+ sum = rest_digits.zip(test_key).map { |a, b| a * b }.reduce(0, &:+)
58
+ [control, sum]
59
+ end
60
+ end
61
+ end
@@ -0,0 +1,34 @@
1
+ module RomanianValidators
2
+ module Cnp
3
+ TEST_KEY = '279146358279'.each_char.map(&:to_i)
4
+
5
+ module_function
6
+
7
+ def valid?(cnp)
8
+ return false unless well_formed?(cnp) && valid_birthdate?(cnp)
9
+ control = (0..11).reduce(0) { |acc, elem| acc + TEST_KEY[elem] * cnp[elem].chr.to_i } % 11
10
+ control = 1 if control == 10
11
+ control == cnp[12].chr.to_i
12
+ end
13
+
14
+ def well_formed?(cnp)
15
+ (cnp =~ /[^0-9]/).nil? && cnp.size == 13
16
+ end
17
+
18
+ def valid_birthdate?(cnp)
19
+ year_code = cnp[0].chr.to_i
20
+ year =
21
+ case year_code
22
+ when 1..2 then '19'
23
+ when 3..4 then '18'
24
+ when 5..6 then '20'
25
+ when 9 then '19' # oare se sare peste un an bisect intre 1800-2099 ?
26
+ else return false
27
+ end
28
+ year = (year + cnp[1..2]).to_i
29
+ Date.valid_civil?(year, cnp[3..4].to_i, cnp[5..6].to_i) ? true : false
30
+ rescue ArgumentError
31
+ return false
32
+ end
33
+ end
34
+ end
@@ -0,0 +1,25 @@
1
+ module RomanianValidators
2
+ module Iban
3
+ # use ord for ruby >= 1.9
4
+ USE_ORD = ''.respond_to?(:ord)
5
+
6
+ module_function
7
+
8
+ # Descrierea algoritmului:
9
+ # http://www.bnr.ro/files/d/Legislatie/EN/Reg_IBAN.pdf
10
+ def valid?(iban)
11
+ return false if iban.size < 3
12
+ transpose((iban.slice(4, iban.size) + iban[0..3])).to_i % 97 == 1
13
+ rescue
14
+ false
15
+ end
16
+
17
+ # replace letters according to algorithm
18
+ # algorithm conversion maps chars to ASCII value - 55
19
+ def transpose(iban)
20
+ iban.upcase.gsub(/[A-Z]/) do |s|
21
+ USE_ORD ? (s[0].ord - 55).to_s : (s[0].to_i - 55).to_s
22
+ end
23
+ end
24
+ end
25
+ end
@@ -1,20 +1,20 @@
1
1
  # -*- encoding: utf-8 -*-
2
2
  Gem::Specification.new do |s|
3
3
  s.name = 'romanianvalidators'
4
- s.version = '0.1.6'
4
+ s.version = '0.2.0'
5
5
  s.authors = ['Mihai Târnovan']
6
6
  s.email = ['mihai.tarnovan@cubus.ro']
7
7
  s.homepage = 'http://github.com/mtarnovan/romanianvalidators'
8
8
  s.license = 'MIT'
9
- s.summary = %q{Collection of validations for Cod Numeric Personal (CNP), Cod de identificare fiscală (CIF) and IBAN (only Romanian format, as published by Romanian National Bank)}
10
- s.description = %q{Collection of validations for Cod Numeric Personal (CNP), Cod de identificare fiscală (CIF) and IBAN (only Romanian format, as published by Romanian National Bank).}
9
+ s.summary = 'Collection of validations for Cod Numeric Personal (CNP), Cod de identificare fiscală (CIF) and IBAN (only Romanian format, as published by Romanian National Bank)'
10
+ s.description = s.summary
11
11
 
12
12
  s.add_development_dependency 'bundler'
13
13
  s.add_development_dependency 'minitest'
14
- s.add_dependency 'rake' , '>= 0.8.7'
15
- s.add_dependency 'activemodel' , '>= 3.0.0'
14
+ s.add_dependency 'rake', '>= 0.8.7'
15
+ s.add_dependency 'activemodel', '>= 3.0.0'
16
16
 
17
17
  s.files = `git ls-files`.split("\n")
18
18
  s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
19
- s.rubyforge_project = "romanianvalidators"
20
- end
19
+ s.rubyforge_project = 'romanianvalidators'
20
+ end
@@ -11,12 +11,14 @@ require 'minitest/autorun'
11
11
  $-w = old_w
12
12
 
13
13
  require 'romanianvalidators'
14
+ require 'romanianvalidators/active_model'
14
15
  require 'active_support/core_ext/array/wrap'
15
16
 
16
17
  I18n.enforce_available_locales = true
17
18
 
18
19
  class TestRecord
19
20
  include ActiveModel::Validations
21
+ include RomanianValidators::ActiveModel::Validations
20
22
  attr_accessor :cnp, :bic, :cif, :iban
21
23
 
22
24
  def initialize(attrs = {})
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: romanianvalidators
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.6
4
+ version: 0.2.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Mihai Târnovan
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2014-12-15 00:00:00.000000000 Z
11
+ date: 2018-04-12 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: bundler
@@ -68,7 +68,7 @@ dependencies:
68
68
  version: 3.0.0
69
69
  description: Collection of validations for Cod Numeric Personal (CNP), Cod de identificare
70
70
  fiscală (CIF) and IBAN (only Romanian format, as published by Romanian National
71
- Bank).
71
+ Bank)
72
72
  email:
73
73
  - mihai.tarnovan@cubus.ro
74
74
  executables: []
@@ -76,6 +76,7 @@ extensions: []
76
76
  extra_rdoc_files: []
77
77
  files:
78
78
  - ".gitignore"
79
+ - ".rubocop.yml"
79
80
  - ".ruby-gemset"
80
81
  - ".ruby-version"
81
82
  - ".travis.yml"
@@ -84,11 +85,16 @@ files:
84
85
  - LICENSE
85
86
  - README.md
86
87
  - Rakefile
87
- - lib/active_model/validations/bic_validator.rb
88
- - lib/active_model/validations/cif_validator.rb
89
- - lib/active_model/validations/cnp_validator.rb
90
- - lib/active_model/validations/iban_validator.rb
91
88
  - lib/romanianvalidators.rb
89
+ - lib/romanianvalidators/active_model.rb
90
+ - lib/romanianvalidators/active_model/validations/bic_validator.rb
91
+ - lib/romanianvalidators/active_model/validations/cif_validator.rb
92
+ - lib/romanianvalidators/active_model/validations/cnp_validator.rb
93
+ - lib/romanianvalidators/active_model/validations/iban_validator.rb
94
+ - lib/romanianvalidators/bic.rb
95
+ - lib/romanianvalidators/cif.rb
96
+ - lib/romanianvalidators/cnp.rb
97
+ - lib/romanianvalidators/iban.rb
92
98
  - romanianvalidators.gemspec
93
99
  - test/data/valid_bics.txt
94
100
  - test/data/valid_cifs.txt
@@ -119,7 +125,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
119
125
  version: '0'
120
126
  requirements: []
121
127
  rubyforge_project: romanianvalidators
122
- rubygems_version: 2.2.2
128
+ rubygems_version: 2.6.7
123
129
  signing_key:
124
130
  specification_version: 4
125
131
  summary: Collection of validations for Cod Numeric Personal (CNP), Cod de identificare
@@ -1,25 +0,0 @@
1
- module ActiveModel
2
- module Validations
3
- class BicValidator < EachValidator
4
- include ActiveModel::Validations::EmptyBlankEachValidator
5
- COUNTRY_CODES =
6
- %w(AF AL DZ AS AD AO AI AG AR AM AW AU AT AZ BS BH BD BB BY BE BZ BJ BM
7
- BT BO BA BW BR BN BG BF BI KH CM CA CV KY CF TD CL CN CO KM CG CD CK CR
8
- CI HR CU CY CZ DK DJ DM DO EC EG SV GQ ER EE ET FK FO FJ FI FR GF PF GA
9
- GM GE DE GH GI GR GL GD GP GU GT GN GW GY HT VA HN HK HU IS IN ID IR IQ
10
- IE IL IT JM JP JO KZ KE KI KP KR KW KG LA LV LB LS LR LY LI LT LU MO MK
11
- MG MW MY MV ML MT MH MQ MR MU MX FM MD MC MN MS MA MZ MM NA NR NP NL AN
12
- NC NZ NI NE NG NU NF MP NO OM PK PW PA PG PY PE PH PN PL PT PR QA RE RO
13
- RU RW SH KN LC PM VC WS SM ST SA SN SC SL SG SK SI SB SO ZA ES LK SD SR
14
- SJ SZ SE CH SY TW TJ TZ TH TG TK TO TT TN TR TM TC TV UG UA AE GB US UY
15
- UZ VU VE VN VG VI WF EH YE ZM ZW)
16
- # This is only a basic validation of a BIC
17
- # http://www.swift.com/biconline/index.cfm?fuseaction=display_aboutbic
18
- def valid?(bic)
19
- return false unless bic.size == 8 || bic.size == 11 # length 8 or 11
20
- return false unless (bic[0..3] =~ (/[^A-Z]/)).nil? # first 4 must be letters only
21
- COUNTRY_CODES.include?(bic[4..5])
22
- end
23
- end
24
- end
25
- end
@@ -1,30 +0,0 @@
1
- module ActiveModel
2
- module Validations
3
- class CifValidator < EachValidator
4
-
5
- # reversed test key (753217532)
6
- TEST_KEY = '235712357'.freeze
7
-
8
- include ActiveModel::Validations::EmptyBlankEachValidator
9
-
10
- # Algoritmul de validare al unui cod CUI
11
- # Pas preliminar: Se testeaza daca codul respecta formatul unui cod CUI. Adica lungimea maxima sa fie de 10 cifre si sa contina doar caractere numerice.
12
- # Pas 1: Se foloseste cheia de testare "753217532". Se inverseaza ordinea cifrelor codului CUI precum si a cheii de testare.
13
- # Pas 2: Se ignora prima cifra din codul CUI inversat (aceasta este cifra de control) si se inmulteste fiecare cifra cu cifra corespunzatoare din cheia de testare inversata.
14
- # Pas 3: Se aduna toate produsele obtinute. Suma rezultata se inmulteste cu 10 si apoi se afla restul impartirii la 11.
15
- # Pas 4: Pentru un CUI valid cifra obtinuta, in urma operatiei MODULO 11, va trebui sa corespunda cu cifra de control a codului CUI initial .
16
- def valid?(cif)
17
- return false unless well_formed?(cif)
18
- rc = cif.reverse.freeze
19
- (1..(cif.size - 1)).inject(0) {|sum, n| sum += TEST_KEY[n-1].chr.to_i * rc[n].chr.to_i} * 10 % 11 % 10 == rc[0].chr.to_i
20
- end
21
-
22
- private
23
-
24
- def well_formed?(cif)
25
- cif.present? && (2..10).include?(cif.size) && (cif=~(/[^0-9]/)).nil?
26
- end
27
-
28
- end
29
- end
30
- end
@@ -1,51 +0,0 @@
1
- module ActiveModel
2
- module Validations
3
- class CnpValidator < EachValidator
4
- TEST_KEY = '279146358279'.each_char.map(&:to_i)
5
-
6
- include ActiveModel::Validations::EmptyBlankEachValidator
7
-
8
- # Algoritm de validare CNP
9
- # Pas preliminar: Se testeaza daca codul respecta formatul unui cod CNP.
10
- # Adica prima cifra sa fie cuprinsa in intervalul 1 - 6 sau sa fie 9 pentru straini.
11
- # Urmatoarele sase cifre trebuie sa constituie o data calendaristica valida in formatul AALLZZ.
12
- #
13
- # Pas 1:
14
- # Se foloseste cheia de testare "279146358279". Primele douasprezece cifre se inmultesc pe rand de la
15
- # stanga spre dreapta cu cifra corespunzatoare din cheia de testare.
16
- #
17
- # Pas 2: Cele douasprezece produse obtinute se aduna si suma obtinuta se imparte la 11.
18
- # * Daca restul impartirii la 11 este mai mic ca 10, atunci acesta va reprezenta cifra de control.
19
- # * Daca restul impartirii este 10 atunci cifra de control este 1.
20
- # Restul impartirii reprezinta cifra de control. Pentru un CNP valid acest rest va trebui
21
- # sa coincida cu cifra de pe pozitia treisprezece din CNP-ul initial.
22
- def valid?(cnp)
23
- return false unless well_formed?(cnp) && valid_birthdate?(cnp)
24
- control = (0..11).reduce(0) { |a, e| a + TEST_KEY[e] * cnp[e].chr.to_i } % 11
25
- control = 1 if control == 10
26
- control == cnp[12].chr.to_i
27
- end
28
-
29
- private
30
-
31
- def well_formed?(cnp)
32
- (cnp =~ (/[^0-9]/)).nil? && cnp.size == 13
33
- end
34
-
35
- def valid_birthdate?(cnp)
36
- year_code = cnp[0].chr.to_i
37
- year = case year_code
38
- when 1..2 then '19'
39
- when 3..4 then '18'
40
- when 5..6 then '20'
41
- when 9 then '19' # oare se sare peste un an bisect intre 1800-2099 ?
42
- else return false
43
- end
44
- year = (year + cnp[1..2]).to_i
45
- Date.valid_civil?(year, cnp[3..4].to_i, cnp[5..6].to_i) ? true : false
46
- rescue ArgumentError
47
- return false
48
- end
49
- end
50
- end
51
- end
@@ -1,30 +0,0 @@
1
- module ActiveModel
2
- module Validations
3
- class IbanValidator < EachValidator
4
-
5
- # use ord for ruby >= 1.9
6
- USE_ORD = ''.respond_to?(:ord)
7
-
8
- include ActiveModel::Validations::EmptyBlankEachValidator
9
-
10
- # Descrierea algoritmului:
11
- # http://www.bnr.ro/files/d/Legislatie/EN/Reg_IBAN.pdf
12
- def valid?(iban)
13
- return false if iban.size < 3
14
- transpose((iban.slice(4, iban.size) + iban[0..3])).to_i % 97 == 1
15
- rescue
16
- false
17
- end
18
-
19
- private
20
-
21
- # replace letters according to algorithm
22
- # algorithm conversion maps chars to ASCII value - 55
23
- def transpose(iban)
24
- iban.upcase.gsub(/[A-Z]/) do |s|
25
- USE_ORD ? (s[0].ord - 55).to_s : (s[0].to_i - 55).to_s
26
- end
27
- end
28
- end
29
- end
30
- end