activerecord_json_validator 0.5.1 → 1.0.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.travis.yml +0 -1
- data/README.md +49 -64
- data/activerecord_json_validator.gemspec +1 -1
- data/lib/active_record/json_validator/validator.rb +13 -13
- data/lib/active_record/json_validator/version.rb +1 -1
- data/spec/json_validator_spec.rb +32 -0
- metadata +5 -6
- data/gemfiles/Gemfile.activerecord-4.1.x +0 -5
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 53b4aea1bc7007643f31d936e12b78804f96ab9f
|
4
|
+
data.tar.gz: 70f49f4c9bc9930dec7cdaede3d612cd387fd00b
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: c360ce94176ec1471287f51ad23224a4cd6fe8caeee92d62df27d04df6fa518af18cd92969167282a6e6886aca46ec0221196e825db5ad8758f657165c85f4c9
|
7
|
+
data.tar.gz: f1586c5cca10f3eef4dbb31d602b29f633daf2a778557642816026092db2bfc9c3ed54b672c39e9835bea877280129580d30bb55d9754a3ed47c70f6b2cac589
|
data/.travis.yml
CHANGED
data/README.md
CHANGED
@@ -1,9 +1,15 @@
|
|
1
|
-
|
2
|
-
|
3
|
-
|
4
|
-
|
5
|
-
|
6
|
-
|
1
|
+
<p align="center">
|
2
|
+
<a href="https://github.com/mirego/activerecord_json_validator">
|
3
|
+
<img src="https://cloud.githubusercontent.com/assets/11348/6099354/cffcf35e-afc3-11e4-9a4d-d872941bbcf6.png" alt="" />
|
4
|
+
</a>
|
5
|
+
<br />
|
6
|
+
<code>ActiveRecord::JSONValidator</code> makes it easy to validate<br /> JSON attributes against a <a href="http://json-schema.org/">JSON schema</a>.
|
7
|
+
<br /><br />
|
8
|
+
<a href="https://rubygems.org/gems/activerecord_json_validator"><img src="http://img.shields.io/gem/v/activerecord_json_validator.svg" /></a>
|
9
|
+
<a href="https://travis-ci.org/mirego/activerecord_json_validator"><img src="http://img.shields.io/travis/mirego/activerecord_json_validator.svg" /></a>
|
10
|
+
</p>
|
11
|
+
|
12
|
+
---
|
7
13
|
|
8
14
|
## Installation
|
9
15
|
|
@@ -20,11 +26,12 @@ gem 'activerecord_json_validator'
|
|
20
26
|
```json
|
21
27
|
{
|
22
28
|
"type": "object",
|
23
|
-
"$schema": "http://json-schema.org/draft-
|
29
|
+
"$schema": "http://json-schema.org/draft-04/schema",
|
24
30
|
"properties": {
|
25
|
-
"city": { "type": "string"
|
26
|
-
"country": { "type": "string"
|
27
|
-
}
|
31
|
+
"city": { "type": "string" },
|
32
|
+
"country": { "type": "string" }
|
33
|
+
},
|
34
|
+
"required": ["country"]
|
28
35
|
}
|
29
36
|
```
|
30
37
|
|
@@ -60,86 +67,64 @@ user.profile_invalid_json # => '{invalid JSON":}'
|
|
60
67
|
|
61
68
|
| Option | Description
|
62
69
|
|------------|-----------------------------------------------------
|
63
|
-
| `:schema` | The JSON schema to validate the data against (see **
|
64
|
-
| `:message` | The ActiveRecord message added to the record errors (
|
70
|
+
| `:schema` | The JSON schema to validate the data against (see **Schema** section)
|
71
|
+
| `:message` | The ActiveRecord message added to the record errors (see **Message** section)
|
65
72
|
|
66
|
-
#####
|
73
|
+
##### Schema
|
67
74
|
|
68
|
-
|
75
|
+
`ActiveRecord::JSONValidator` uses the `json-schema` gem to validate the JSON
|
76
|
+
data against a JSON schema. You can use [any value](https://github.com/ruby-json-schema/json-schema/tree/master#usage) that
|
77
|
+
`JSON::Validator.validate` would take as the `schema` argument.
|
69
78
|
|
70
|
-
|
79
|
+
Additionally, you can use a `Symbol` or a `Proc`. Both will be executed in the
|
80
|
+
context of the validated record (`Symbol` will be sent as a method and the
|
81
|
+
`Proc` will be `instance_exec`ed)
|
71
82
|
|
72
83
|
```ruby
|
73
84
|
class User < ActiveRecord::Base
|
74
85
|
# Constants
|
75
|
-
|
86
|
+
PROFILE_REGULAR_JSON_SCHEMA = Rails.root.join('config', 'schemas', 'profile.json_schema').to_s
|
87
|
+
PROFILE_ADMIN_JSON_SCHEMA = Rails.root.join('config', 'schemas', 'profile_admin.json_schema').to_s
|
76
88
|
|
77
89
|
# Validations
|
78
|
-
validates :profile, presence: true, json: { schema:
|
79
|
-
end
|
80
|
-
```
|
90
|
+
validates :profile, presence: true, json: { schema: lambda { dynamic_profile_schema } } # `schema: :dynamic_profile_schema` would also work
|
81
91
|
|
82
|
-
|
83
|
-
|
84
|
-
|
85
|
-
class User < ActiveRecord::Base
|
86
|
-
# Constants
|
87
|
-
PROFILE_JSON_SCHEMA = {
|
88
|
-
type: 'object',
|
89
|
-
:'$schema' => 'http://json-schema.org/draft-03/schema',
|
90
|
-
properties: {
|
91
|
-
city: { type: 'string', required: false },
|
92
|
-
country: { type: 'string', required: true }
|
93
|
-
}
|
94
|
-
}
|
95
|
-
|
96
|
-
# Validations
|
97
|
-
validates :profile, presence: true, json: { schema: PROFILE_JSON_SCHEMA }
|
92
|
+
def dynamic_profile_schema
|
93
|
+
admin? ? PROFILE_ADMIN_JSON_SCHEMA : PROFILE_REGULAR_JSON_SCHEMA
|
94
|
+
end
|
98
95
|
end
|
99
96
|
```
|
100
97
|
|
101
|
-
|
98
|
+
##### Message
|
102
99
|
|
103
|
-
|
104
|
-
|
105
|
-
# Constants
|
106
|
-
PROFILE_JSON_SCHEMA = '{
|
107
|
-
"type": "object",
|
108
|
-
"$schema": "http://json-schema.org/draft-03/schema",
|
109
|
-
"properties": {
|
110
|
-
"city": { "type": "string", "required": false },
|
111
|
-
"country": { "type": "string", "required": true }
|
112
|
-
}
|
113
|
-
}'
|
100
|
+
Like any other ActiveModel validation, you can specify either a `Symbol` or
|
101
|
+
`String` value for the `:message` option. The default value is `:invalid_json`.
|
114
102
|
|
115
|
-
|
116
|
-
|
117
|
-
|
118
|
-
|
119
|
-
|
120
|
-
###### A lambda that will get evaluated in the context of the validated record
|
121
|
-
|
122
|
-
The lambda must return a valid value for the `:schema` option (file path, JSON `String` or Ruby `Hash`).
|
103
|
+
However, you can also specify a `Proc` that returns an array of errors. The
|
104
|
+
`Proc` will be called with a single argument — an array of errors returned by
|
105
|
+
the JSON schema validator. So, if you’d like to add each of these errors as
|
106
|
+
a first-level error for the record, you can do this:
|
123
107
|
|
124
108
|
```ruby
|
125
109
|
class User < ActiveRecord::Base
|
126
|
-
# Constants
|
127
|
-
PROFILE_REGULAR_JSON_SCHEMA = Rails.root.join('config', 'schemas', 'profile.json_schema').to_s
|
128
|
-
PROFILE_ADMIN_JSON_SCHEMA = Rails.root.join('config', 'schemas', 'profile_admin.json_schema').to_s
|
129
|
-
|
130
110
|
# Validations
|
131
|
-
validates :profile, presence: true, json: {
|
132
|
-
|
133
|
-
def dynamic_profile_schema
|
134
|
-
admin? ? PROFILE_ADMIN_JSON_SCHEMA : PROFILE_REGULAR_JSON_SCHEMA
|
135
|
-
end
|
111
|
+
validates :profile, presence: true, json: { message: ->(errors) { errors }, schema: 'foo.json_schema' }
|
136
112
|
end
|
113
|
+
|
114
|
+
user = User.new.tap(&:valid?)
|
115
|
+
user.errors.full_messages
|
116
|
+
# => [
|
117
|
+
# 'The property '#/email' of type Fixnum did not match the following type: string in schema 2d44293f-cd9d-5dca-8a6a-fb9db1de722b#',
|
118
|
+
# 'The property '#/full_name' of type Fixnum did not match the following type: string in schema 2d44293f-cd9d-5dca-8a6a-fb9db1de722b#',
|
119
|
+
# ]
|
137
120
|
```
|
138
121
|
|
139
122
|
## License
|
140
123
|
|
141
124
|
`ActiveRecord::JSONValidator` is © 2013-2015 [Mirego](http://www.mirego.com) and may be freely distributed under the [New BSD license](http://opensource.org/licenses/BSD-3-Clause). See the [`LICENSE.md`](https://github.com/mirego/activerecord_json_validator/blob/master/LICENSE.md) file.
|
142
125
|
|
126
|
+
The tree logo is based on [this lovely icon](http://thenounproject.com/term/tree/51004/) by [Sara Quintana](http://thenounproject.com/sara.quintana.75), from The Noun Project. Used under a [Creative Commons BY 3.0](http://creativecommons.org/licenses/by/3.0/) license.
|
127
|
+
|
143
128
|
## About Mirego
|
144
129
|
|
145
130
|
[Mirego](http://mirego.com) is a team of passionate people who believe that work is a place where you can innovate and have fun. We're a team of [talented people](http://life.mirego.com) who imagine and build beautiful Web and mobile applications. We come together to share ideas and [change the world](http://mirego.org).
|
@@ -7,18 +7,7 @@ class JsonValidator < ActiveModel::EachValidator
|
|
7
7
|
|
8
8
|
super
|
9
9
|
|
10
|
-
|
11
|
-
if options[:class]
|
12
|
-
inject_setter_method(options[:class], @attributes)
|
13
|
-
|
14
|
-
# Rails 4.0 and below calls a `#setup` method
|
15
|
-
elsif !respond_to?(:setup)
|
16
|
-
class_eval do
|
17
|
-
define_method :setup do |model|
|
18
|
-
inject_setter_method(model, @attributes)
|
19
|
-
end
|
20
|
-
end
|
21
|
-
end
|
10
|
+
inject_setter_method(options[:class], @attributes)
|
22
11
|
end
|
23
12
|
|
24
13
|
# Validate the JSON value with a JSON schema path or String
|
@@ -30,7 +19,9 @@ class JsonValidator < ActiveModel::EachValidator
|
|
30
19
|
return if errors.empty? && record.send(:"#{attribute}_invalid_json").blank?
|
31
20
|
|
32
21
|
# Add error message to the attribute
|
33
|
-
|
22
|
+
message(errors).each do |error|
|
23
|
+
record.errors.add(attribute, error, value: value)
|
24
|
+
end
|
34
25
|
end
|
35
26
|
|
36
27
|
protected
|
@@ -72,4 +63,13 @@ protected
|
|
72
63
|
return value if value.is_a?(String)
|
73
64
|
::ActiveSupport::JSON.encode(value)
|
74
65
|
end
|
66
|
+
|
67
|
+
def message(errors)
|
68
|
+
message = options.fetch(:message)
|
69
|
+
|
70
|
+
case message
|
71
|
+
when Proc then [message.call(errors)].flatten if message.is_a?(Proc)
|
72
|
+
else [message]
|
73
|
+
end
|
74
|
+
end
|
75
75
|
end
|
data/spec/json_validator_spec.rb
CHANGED
@@ -86,6 +86,21 @@ describe JsonValidator do
|
|
86
86
|
|
87
87
|
specify { validate_each! }
|
88
88
|
end
|
89
|
+
|
90
|
+
context 'with multiple error messages' do
|
91
|
+
let(:options) { { attributes: [attribute], message: message, options: { strict: true } } }
|
92
|
+
let(:message) { ->(errors) { errors.to_a } }
|
93
|
+
|
94
|
+
before do
|
95
|
+
expect(validator_errors).to receive(:empty?).and_return(false)
|
96
|
+
expect(validator_errors).to receive(:to_a).and_return(%i(first_error second_error))
|
97
|
+
expect(record).not_to receive(:"#{attribute}_invalid_json")
|
98
|
+
expect(record_errors).to receive(:add).with(attribute, :first_error, value: value)
|
99
|
+
expect(record_errors).to receive(:add).with(attribute, :second_error, value: value)
|
100
|
+
end
|
101
|
+
|
102
|
+
specify { validate_each! }
|
103
|
+
end
|
89
104
|
end
|
90
105
|
|
91
106
|
describe :schema do
|
@@ -152,4 +167,21 @@ describe JsonValidator do
|
|
152
167
|
it { expect(validatable_value).to eql(value) }
|
153
168
|
end
|
154
169
|
end
|
170
|
+
|
171
|
+
describe :message do
|
172
|
+
let(:validator) { JsonValidator.new(options) }
|
173
|
+
let(:options) { { attributes: [:foo], message: message_option } }
|
174
|
+
let(:message) { validator.send(:message, errors) }
|
175
|
+
let(:errors) { %i(first_error second_error) }
|
176
|
+
|
177
|
+
context 'with Symbol message' do
|
178
|
+
let(:message_option) { :invalid_json }
|
179
|
+
it { expect(message).to eql([:invalid_json]) }
|
180
|
+
end
|
181
|
+
|
182
|
+
context 'with String value' do
|
183
|
+
let(:message_option) { ->(errors) { errors } }
|
184
|
+
it { expect(message).to eql(%i(first_error second_error)) }
|
185
|
+
end
|
186
|
+
end
|
155
187
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: activerecord_json_validator
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 1.0.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Rémi Prévost
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2015-
|
11
|
+
date: 2015-05-27 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: bundler
|
@@ -148,7 +148,7 @@ dependencies:
|
|
148
148
|
requirements:
|
149
149
|
- - ">="
|
150
150
|
- !ruby/object:Gem::Version
|
151
|
-
version: 4.
|
151
|
+
version: 4.2.0
|
152
152
|
- - "<"
|
153
153
|
- !ruby/object:Gem::Version
|
154
154
|
version: '5'
|
@@ -158,7 +158,7 @@ dependencies:
|
|
158
158
|
requirements:
|
159
159
|
- - ">="
|
160
160
|
- !ruby/object:Gem::Version
|
161
|
-
version: 4.
|
161
|
+
version: 4.2.0
|
162
162
|
- - "<"
|
163
163
|
- !ruby/object:Gem::Version
|
164
164
|
version: '5'
|
@@ -179,7 +179,6 @@ files:
|
|
179
179
|
- README.md
|
180
180
|
- Rakefile
|
181
181
|
- activerecord_json_validator.gemspec
|
182
|
-
- gemfiles/Gemfile.activerecord-4.1.x
|
183
182
|
- gemfiles/Gemfile.activerecord-4.2.x
|
184
183
|
- lib/active_record/json_validator/validator.rb
|
185
184
|
- lib/active_record/json_validator/version.rb
|
@@ -211,7 +210,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
211
210
|
version: '0'
|
212
211
|
requirements: []
|
213
212
|
rubyforge_project:
|
214
|
-
rubygems_version: 2.
|
213
|
+
rubygems_version: 2.4.5
|
215
214
|
signing_key:
|
216
215
|
specification_version: 4
|
217
216
|
summary: ActiveRecord::JSONValidator makes it easy to validate JSON attributes with
|