can_has_validations 0.4.3 → 0.5.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,15 +1,7 @@
1
1
  ---
2
- !binary "U0hBMQ==":
3
- metadata.gz: !binary |-
4
- ZjBjODY1MTlkYjZlYzA1NmU4MWI3NWRlZWU2OWMxNzE2MDI1OTA2OA==
5
- data.tar.gz: !binary |-
6
- YzJiYzNiYmMyMjZmOWNlNjNlN2JkOTI2ODRhMWI5YmFlMjJhZTY0Yg==
2
+ SHA1:
3
+ metadata.gz: 9fedcbc24847be3ea9133d3b6fd4f46f5d702ad1
4
+ data.tar.gz: 296690743c12db64dacef74b96ac251289c9b3b1
7
5
  SHA512:
8
- metadata.gz: !binary |-
9
- OWYzMDhjMTc3MjgxMjBhMDY4M2MwYTQ5ZTI1MjIzNmU4MTcxNjg1NGZhNWFm
10
- ZjRmOWNlYjc4YTkxNjNmYThiZTkyODA4NzA0YTU4ZjhmOTVhYzhkM2Q1MWZh
11
- ZGFhNTdmNThhMjZmMDkwMTcyY2FkYzRiYWM4YTMyOThjNmZjMWM=
12
- data.tar.gz: !binary |-
13
- M2ZlYTc5OWJjODNlMGEzNDZjZjBlMzk0ZGM0NzljYzA2NjZiODg3YTNiMWY2
14
- OGIzOTAzY2Y1M2E5MTEwOWU1M2FmOTNiMjNlOTM4MTU3YzliYjVhMTYyY2U4
15
- ZDliMTUzNzFjNmM3NTRmNjgxYmZlZTY5N2EyMzcxY2JhOTE3NzE=
6
+ metadata.gz: 370506abcb60fc6a0ff4f8df9b36782927604c0604e95cdd9b8fcec48368114a4bb0e8b1dbe70a97ee9a154f03ab34752e6a4d05c7f44ef7b54fd9f1fa29118f
7
+ data.tar.gz: 1fccf97fd21b2c20c45f5dff224bd98325c0f7e662049489cea0c4b642be1ec858580c2aa575758f59055d33a856b47d5d00ec586fa995b55a56b09878dc0bc4
data/README.md CHANGED
@@ -8,6 +8,7 @@ Validations provided:
8
8
  * Email
9
9
  * Existence
10
10
  * Grandparent
11
+ * Hostname
11
12
  * Ordering
12
13
  * URL
13
14
  * Write Once
@@ -103,6 +104,27 @@ or the database foreign key (`:user_id`). You can also use any other field. The
103
104
  test is merely that they match, not that they are associations.
104
105
 
105
106
 
107
+ ## Hostname validator ##
108
+
109
+ Ensures an attribute is generally formatted as a hostname. It allows for any
110
+ TLD, so as to not fail as ICANN continues to add TLDs.
111
+
112
+ validates :domain, hostname: true
113
+
114
+ # allows '*.example.com'
115
+ validates :domain, hostname: {allow_wildcard: true}
116
+
117
+ # allows '_abc.example.com'
118
+ validates :domain, hostname: {allow_underscore: true}
119
+
120
+ # allows 'a.example.com', but not 'example.com'
121
+ validates :domain, hostname: {segments: 3..100}
122
+
123
+ # allows '1.2.3.4' or 'a.example.com'
124
+ validates :domain, hostname: {allow_ip: true}
125
+ # use 4 or 6 for ipv4 or ipv6 only
126
+
127
+
106
128
  ## Ordering validators ##
107
129
 
108
130
  Ensures two attribute values maintain a relative order to one another. This is
@@ -125,16 +147,18 @@ Always skips over nil values; use `:presence` to validate those.
125
147
  ## URL validator ##
126
148
 
127
149
  Ensure an attribute is generally formatted as a URL. If `addressable/uri` is
128
- already loaded, it will be used to parse IDN's.
150
+ already loaded, it will be used to parse IDN's. Additionally, allowed schemes
151
+ can be specified; they default to ['http','https'].
129
152
 
130
153
  validates :website, url: true
154
+ validates :secure_url, url: {scheme: 'https'}
131
155
 
132
156
  # With IDN parsing:
133
157
  require 'addressable/uri'
134
158
  validates :website, url: true
135
159
 
136
160
  # Or, as part of your Gemfile:
137
- gem 'addressable', require: 'addressable/uri'
161
+ gem 'addressable'
138
162
  gem 'can_has_validations'
139
163
 
140
164
 
@@ -166,6 +190,7 @@ Default messages are as follows:
166
190
  errors:
167
191
  messages:
168
192
  invalid_email: "is an invalid email"
193
+ invalid_hostname: "is an invalid hostname"
169
194
  invalid_url: "is an invalid URL"
170
195
  unchangeable: "cannot be changed"
171
196
  before: "must be before %{attribute2}"
@@ -174,4 +199,4 @@ Default messages are as follows:
174
199
 
175
200
  ## Compatibility ##
176
201
 
177
- Tested with Ruby 2.1 and ActiveSupport and ActiveModel 4.2.
202
+ Tested with Ruby 2.3-2.4 and ActiveSupport and ActiveModel 4.2-5.1.
@@ -1,4 +1,4 @@
1
- %w(email existence grandparent ordering url write_once).each do |validator|
1
+ %w(email existence grandparent hostname ordering url write_once).each do |validator|
2
2
  require "can_has_validations/validators/#{validator}_validator"
3
3
  end
4
4
 
@@ -2,6 +2,7 @@ en:
2
2
  errors:
3
3
  messages:
4
4
  invalid_email: "is an invalid email"
5
+ invalid_hostname: "is an invalid hostname"
5
6
  invalid_url: "is an invalid URL"
6
7
  unchangeable: "cannot be changed"
7
8
  before: "must be before %{attribute2}"
@@ -1,5 +1,5 @@
1
1
  # Ensure an attribute is generally formatted as an email.
2
- # eg: validates :user_email, :email=>true
2
+ # eg: validates :user_email, email: true
3
3
 
4
4
  module ActiveModel::Validations
5
5
  class EmailValidator < ActiveModel::EachValidator
@@ -1,8 +1,8 @@
1
1
  # Ensure two (or more) associations share a common parent
2
2
  # :allow_nil will not only allow the attribute/association to be nil, but
3
3
  # also any of the :scope's.
4
- # eg: validates :user, :grandparent=>{:scope=>:org, :parent=>:realm}
5
- # validates :user, :grandparent=>{:scope=>[:phone, :address], :parent=>:account_id}
4
+ # eg: validates :user, grandparent: {scope: :org, parent: :realm}
5
+ # validates :user, grandparent: {scope: [:phone, :address], parent: :account_id}
6
6
 
7
7
  module ActiveModel::Validations
8
8
  class GrandparentValidator < ActiveModel::EachValidator
@@ -0,0 +1,73 @@
1
+ # Ensure an attribute is generally formatted as a hostname/domain.
2
+ # What's validated and not:
3
+ # max length of entire hostname is 255
4
+ # max length of each label within the hostname is 63
5
+ # characters allowed: a-z, A-Z, 0-9, hyphen
6
+ # underscore is also allowed with allow_underscore: true
7
+ # the final label must be a-z,A-Z or an IDN
8
+ # labels may not begin with a hyphen
9
+ # labels may not end with a hyphen or underscore
10
+ # labels may be entirely numeric
11
+ # note: this is more common that you think (reverse dns, etc)
12
+ # If the addressable gem is present, will automatically turn unicode domains
13
+ # into their punycode (xn--) equivalent. Otherwise, unicode characters will
14
+ # cause the validation to fail.
15
+ #
16
+ # eg: validates :domain, hostname: true
17
+ # validates :domain, hostname: {allow_wildcard: true}
18
+ # allows '*.example.com'
19
+ # validates :domain, hostname: {allow_underscore: true}
20
+ # allows '_abc.example.com'
21
+ # validates :domain, hostname: {segments: 3..100}
22
+ # allows 'a.example.com', but not 'example.com'
23
+ # validates :domain, hostname: {allow_ip: true} # or 4 or 6 for ipv4 or ipv6 only
24
+ # allows '1.2.3.4' or 'a.example.com'
25
+
26
+ require 'resolv'
27
+
28
+ module ActiveModel::Validations
29
+ class HostnameValidator < ActiveModel::EachValidator
30
+
31
+ LABEL_REGEXP = /\A([a-zA-Z0-9_]([a-zA-Z0-9_-]+)?)?[a-zA-Z0-9]\z/
32
+ FINAL_LABEL_REGEXP = /\A(xn--[a-zA-Z0-9]{2,}|[a-zA-Z]{2,})\z/
33
+
34
+ def validate_each(record, attribute, value)
35
+ case options[:allow_ip]
36
+ when 4, '4'
37
+ return if value =~ Resolv::IPv4::Regex
38
+ when 6, '6'
39
+ return if value =~ Resolv::IPv6::Regex
40
+ when true
41
+ return if value =~ Resolv::IPv4::Regex || value =~ Resolv::IPv6::Regex
42
+ end
43
+
44
+ segments = options[:segments] || (2..100)
45
+ segments = segments..segments if segments.is_a?(Integer)
46
+ if defined?(Addressable::IDNA)
47
+ value &&= Addressable::IDNA.to_ascii(value)
48
+ end
49
+ labels = value.split('.')
50
+
51
+ is_valid = true
52
+ is_valid &&= value.length <= 255
53
+ is_valid &&= value !~ /\.\./
54
+ is_valid &&= value !~ /_/ unless options[:allow_underscore]
55
+ is_valid &&= labels.size.in? segments
56
+ labels.each_with_index do |label, idx|
57
+ is_valid &&= label.length <= 63
58
+ if idx+1==labels.size
59
+ is_valid &&= label =~ FINAL_LABEL_REGEXP
60
+ elsif options[:allow_wildcard] && idx==0
61
+ is_valid &&= label=='*' || label =~ LABEL_REGEXP
62
+ else
63
+ is_valid &&= label =~ LABEL_REGEXP
64
+ end
65
+ end
66
+
67
+ unless is_valid
68
+ record.errors.add(attribute, :invalid_hostname, options)
69
+ end
70
+ end
71
+
72
+ end
73
+ end
@@ -1,10 +1,10 @@
1
1
  # Attribute ordering
2
2
  # Ensures one value is greater or lesser than another (set of) value(s).
3
3
  # Always skips over nil values; use :presence to validate those.
4
- # eg: validates :start_at, :before=>:finish_at
5
- # validates :start_at, :before=>{:value_of=>:finish_at, :if=>... }
6
- # validates :finish_at, :after => [:start_at, :alt_start_at]
7
- # validates :finish_at, :after=>{:values_of => [:start_at, :alt_start_at], :if=>... }
4
+ # eg: validates :start_at, before: :finish_at
5
+ # validates :start_at, before: {value_of: :finish_at, if: ... }
6
+ # validates :finish_at, after: [:start_at, :alt_start_at]
7
+ # validates :finish_at, after: {values_of: [:start_at, :alt_start_at], if: ... }
8
8
 
9
9
  module ActiveModel::Validations
10
10
  class BeforeValidator < ActiveModel::EachValidator
@@ -16,7 +16,7 @@ module ActiveModel::Validations
16
16
  next unless value && greater
17
17
  unless value < greater
18
18
  attr2 = record.class.human_attribute_name attr_name
19
- record.errors.add(attribute, :before, options.except(:before).merge!(:attribute2=>attr2))
19
+ record.errors.add(attribute, :before, options.except(:before).merge!(attribute2: attr2))
20
20
  end
21
21
  end
22
22
  end
@@ -30,7 +30,7 @@ module ActiveModel::Validations
30
30
  next unless value && lesser
31
31
  unless value > lesser
32
32
  attr2 = record.class.human_attribute_name attr_name
33
- record.errors.add(attribute, :after, options.except(:after).merge!(:attribute2=>attr2))
33
+ record.errors.add(attribute, :after, options.except(:after).merge!(attribute2: attr2))
34
34
  end
35
35
  end
36
36
  end
@@ -1,17 +1,21 @@
1
1
  # Ensure an attribute is generally formatted as a URL. If addressable/uri is
2
2
  # already loaded, will use it to parse IDN's.
3
- # eg: validates :website, :url=>true
3
+ # eg: validates :website, url: true
4
+ # validates :redis, url: {scheme: 'redis'}
5
+ # validates :database, url: {scheme: %w(postgres mysql)}
4
6
 
5
7
  module ActiveModel::Validations
6
8
  class UrlValidator < ActiveModel::EachValidator
7
9
  def validate_each(record, attribute, value)
10
+ allowed_schemes = Array.wrap(options[:scheme] || %w(http https))
11
+
8
12
  if defined?(Addressable::URI)
9
13
  u = Addressable::URI.parse(value) rescue nil
10
14
  u2 = u && URI.parse(u.normalize.to_s) rescue nil
11
15
  else
12
16
  u2 = u = URI.parse(value) rescue nil
13
17
  end
14
- if !u || !u2 || u.relative? || %w(http https).exclude?(u.scheme)
18
+ if !u || !u2 || u.relative? || allowed_schemes.exclude?(u.scheme)
15
19
  record.errors.add(attribute, :invalid_url, options)
16
20
  end
17
21
  end
@@ -1,6 +1,6 @@
1
1
  # write-once, read-many
2
2
  # Allows a value to be set to a non-nil value once, and then makes it immutable.
3
- # Combine with :existence=>true to accomplish the same thing as attr_readonly,
3
+ # Combine with existence: true to accomplish the same thing as attr_readonly,
4
4
  # except with error messages (instead of silently refusing to save the change).
5
5
  # eg: validates :user_id, write_once: true
6
6
  # Optionally refuses changing from nil => non-nil, always making field immutable.
@@ -8,7 +8,7 @@
8
8
 
9
9
  module ActiveModel::Validations
10
10
  class WriteOnceValidator < ActiveModel::EachValidator
11
- # as of ActiveModel 4, :allow_nil=>true causes a change from a value back to
11
+ # as of ActiveModel 4, allow_nil: true causes a change from a value back to
12
12
  # nil to be allowed. prevent this.
13
13
  def validate(record)
14
14
  attributes.each do |attribute|
@@ -1,3 +1,3 @@
1
1
  module CanHasValidations
2
- VERSION = '0.4.3'
2
+ VERSION = '0.5.0'
3
3
  end
metadata CHANGED
@@ -1,47 +1,47 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: can_has_validations
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.4.3
4
+ version: 0.5.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - thomas morgan
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2016-08-26 00:00:00.000000000 Z
11
+ date: 2017-05-13 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rails
15
15
  requirement: !ruby/object:Gem::Requirement
16
16
  requirements:
17
- - - ! '>='
17
+ - - ">="
18
18
  - !ruby/object:Gem::Version
19
19
  version: '3.0'
20
- - - <
20
+ - - "<"
21
21
  - !ruby/object:Gem::Version
22
- version: '5.1'
22
+ version: '6'
23
23
  type: :runtime
24
24
  prerelease: false
25
25
  version_requirements: !ruby/object:Gem::Requirement
26
26
  requirements:
27
- - - ! '>='
27
+ - - ">="
28
28
  - !ruby/object:Gem::Version
29
29
  version: '3.0'
30
- - - <
30
+ - - "<"
31
31
  - !ruby/object:Gem::Version
32
- version: '5.1'
32
+ version: '6'
33
33
  - !ruby/object:Gem::Dependency
34
34
  name: sqlite3
35
35
  requirement: !ruby/object:Gem::Requirement
36
36
  requirements:
37
- - - ! '>='
37
+ - - ">="
38
38
  - !ruby/object:Gem::Version
39
39
  version: '0'
40
40
  type: :development
41
41
  prerelease: false
42
42
  version_requirements: !ruby/object:Gem::Requirement
43
43
  requirements:
44
- - - ! '>='
44
+ - - ">="
45
45
  - !ruby/object:Gem::Version
46
46
  version: '0'
47
47
  description: Assorted Rails 4.x-5.x validators.
@@ -59,6 +59,7 @@ files:
59
59
  - lib/can_has_validations/validators/email_validator.rb
60
60
  - lib/can_has_validations/validators/existence_validator.rb
61
61
  - lib/can_has_validations/validators/grandparent_validator.rb
62
+ - lib/can_has_validations/validators/hostname_validator.rb
62
63
  - lib/can_has_validations/validators/ordering_validator.rb
63
64
  - lib/can_has_validations/validators/url_validator.rb
64
65
  - lib/can_has_validations/validators/write_once_validator.rb
@@ -103,17 +104,17 @@ require_paths:
103
104
  - lib
104
105
  required_ruby_version: !ruby/object:Gem::Requirement
105
106
  requirements:
106
- - - ! '>='
107
+ - - ">="
107
108
  - !ruby/object:Gem::Version
108
109
  version: '0'
109
110
  required_rubygems_version: !ruby/object:Gem::Requirement
110
111
  requirements:
111
- - - ! '>='
112
+ - - ">="
112
113
  - !ruby/object:Gem::Version
113
114
  version: '0'
114
115
  requirements: []
115
116
  rubyforge_project:
116
- rubygems_version: 2.4.6
117
+ rubygems_version: 2.6.12
117
118
  signing_key:
118
119
  specification_version: 4
119
120
  summary: Assorted Rails 4.x-5.x validators