sinatra-my-params 0.0.6 → 0.0.10
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 +4 -4
- data/lib/permit_params.rb +79 -18
- data/spec/permit_params_shape_spec.rb +50 -0
- data/spec/permit_params_spec.rb +129 -72
- metadata +4 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: e8b53c81f8e6331c9f40d1b36cd45393132c6345478ae80132def61c44f5e6bd
|
4
|
+
data.tar.gz: d049d0ec154d84196d13ac5db1ffe7d07ca8926e8c9a8e84f1ae0d7707b9a79c
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: c424f3ff45c18ada07d4e9377177793849c665ae69b6198ab1742c533b3c1dc647ff302b69e987e1d10caa87024787fa9197c940807e8c2367e54db9a31f1661
|
7
|
+
data.tar.gz: 4ea6c14c51e42bc649ad6251503173a9765188f3281bd7c56e3cd7aa2bb8aa62dc2c0e24b2fb8560c0fe06ed6868ad60675b0ea34c3462bae4cb520823250309
|
data/lib/permit_params.rb
CHANGED
@@ -1,18 +1,25 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
module PermitParams
|
2
4
|
class InvalidParameterError < StandardError
|
3
5
|
attr_accessor :param, :options
|
4
6
|
end
|
5
7
|
|
6
|
-
def permitted_params(params, permitted = {}, strong_validation = false)
|
8
|
+
def permitted_params(params, permitted = {}, strong_validation = false, options = {})
|
7
9
|
return params if permitted.empty?
|
8
|
-
|
10
|
+
|
9
11
|
coerced_params = Hash.new({})
|
10
12
|
|
11
13
|
params.each do |key, value|
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
14
|
+
next unless permitted?(permitted: permitted, key: key, value: value)
|
15
|
+
|
16
|
+
coerced = coerce(
|
17
|
+
param: value,
|
18
|
+
type: permitted[key.to_sym],
|
19
|
+
strong_validation: strong_validation,
|
20
|
+
options: options
|
21
|
+
)
|
22
|
+
coerced_params[key] = coerced unless coerced.nil?
|
16
23
|
end
|
17
24
|
coerced_params
|
18
25
|
end
|
@@ -21,40 +28,94 @@ module PermitParams
|
|
21
28
|
|
22
29
|
Boolean = :boolean
|
23
30
|
Any = :any
|
31
|
+
Shape = :shape
|
24
32
|
|
25
|
-
def
|
33
|
+
def permitted?(permitted:, key:, value:)
|
34
|
+
permitted.keys.map(&:to_s).include?(key.to_s) && !value.nil?
|
35
|
+
end
|
36
|
+
|
37
|
+
def coerce(param:, type:, strong_validation: false, options: {})
|
26
38
|
return param if type == Any
|
27
39
|
|
28
40
|
begin
|
29
41
|
return nil if param.nil?
|
30
|
-
return param if
|
31
|
-
|
42
|
+
return param if begin
|
43
|
+
param.is_a?(type)
|
44
|
+
rescue StandardError
|
45
|
+
false
|
46
|
+
end
|
47
|
+
return coerce_integer(param, options) if type == Integer
|
32
48
|
return Float(param) if type == Float
|
33
49
|
return String(param) if type == String
|
34
50
|
return Date.parse(param) if type == Date
|
35
51
|
return Time.parse(param) if type == Time
|
36
52
|
return DateTime.parse(param) if type == DateTime
|
37
|
-
return coerce_array(param) if type == Array
|
38
|
-
return
|
53
|
+
return coerce_array(param, options) if type == Array
|
54
|
+
return coerce_shape(param, options) if type == Shape
|
55
|
+
return coerce_hash(param, options) if type == Hash
|
39
56
|
return coerce_boolean(param) if [TrueClass, FalseClass, Boolean].include? type
|
40
|
-
|
57
|
+
|
58
|
+
nil
|
41
59
|
rescue ArgumentError
|
42
60
|
raise InvalidParameterError, "'#{param}' is not a valid #{type}" if strong_validation
|
43
61
|
end
|
44
62
|
end
|
45
63
|
|
46
|
-
def
|
47
|
-
|
64
|
+
def coerce_integer(param, options = {})
|
65
|
+
Integer(param, options[:integer_precision] || 10)
|
66
|
+
end
|
67
|
+
|
68
|
+
def coerce_array(param, options = {})
|
69
|
+
delimiter = valid_delimiter?(param, options[:delimiter])
|
70
|
+
return unless delimiter
|
71
|
+
|
72
|
+
Array(param.split(delimiter).map(&:strip))
|
48
73
|
end
|
49
74
|
|
50
|
-
def coerce_hash(param)
|
51
|
-
|
75
|
+
def coerce_hash(param, options = {})
|
76
|
+
return param if param.is_a?(Hash)
|
77
|
+
|
78
|
+
delimiter = valid_delimiter?(param, options[:delimiter])
|
79
|
+
return unless delimiter
|
80
|
+
|
81
|
+
separator = valid_separator?(param, options[:separator])
|
82
|
+
return unless separator
|
83
|
+
|
84
|
+
key_value = param.split(delimiter).map(&:strip).map do |c|
|
85
|
+
c.split(separator).map(&:strip)
|
86
|
+
end
|
87
|
+
Hash[key_value]
|
52
88
|
end
|
53
89
|
|
54
90
|
def coerce_boolean(param)
|
55
|
-
coerced = /^(false|f|no|n|0)$/i === param.to_s
|
91
|
+
coerced = if /^(false|f|no|n|0)$/i === param.to_s
|
92
|
+
false
|
93
|
+
else
|
94
|
+
/^(true|t|yes|y|1)$/i === param.to_s ? true : nil
|
95
|
+
end
|
56
96
|
raise ArgumentError if coerced.nil?
|
97
|
+
|
57
98
|
coerced
|
58
99
|
end
|
59
|
-
end
|
60
100
|
|
101
|
+
def valid_delimiter?(param, delimiter)
|
102
|
+
delimiter ||= ','
|
103
|
+
delimiter if delimiter && param.include?(delimiter)
|
104
|
+
end
|
105
|
+
|
106
|
+
def valid_separator?(param, separator)
|
107
|
+
separator ||= ':'
|
108
|
+
separator if separator && param.include?(separator)
|
109
|
+
end
|
110
|
+
|
111
|
+
def coerce_shape(param, options = {})
|
112
|
+
hash = coerce_hash(param)
|
113
|
+
has_shape?(hash, options[:shape]) ? hash : nil
|
114
|
+
end
|
115
|
+
|
116
|
+
def has_shape?(hash, shape)
|
117
|
+
hash.all? do |k, v|
|
118
|
+
v.is_a?(Hash) ? has_shape?(v, shape[k]) : shape[k] === v
|
119
|
+
end
|
120
|
+
end
|
121
|
+
end
|
@@ -0,0 +1,50 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require 'test/unit'
|
4
|
+
require 'permit_params'
|
5
|
+
require 'rspec'
|
6
|
+
require 'rack/test'
|
7
|
+
|
8
|
+
include PermitParams
|
9
|
+
|
10
|
+
describe 'shape behaviours' do
|
11
|
+
it 'should return a hash when a pemitted is of shape' do
|
12
|
+
input = { param: { a: 1, b: 2 } }
|
13
|
+
expect(input).to eq permitted_params(
|
14
|
+
input,
|
15
|
+
{ param: Shape },
|
16
|
+
false,
|
17
|
+
{ shape: { a: Integer, b: Integer } }
|
18
|
+
)
|
19
|
+
end
|
20
|
+
|
21
|
+
it 'should return a hash when a pemitted is of Integer shape(deep)' do
|
22
|
+
input = { param: { a: { b: 2 } } }
|
23
|
+
expect(input).to eq permitted_params(
|
24
|
+
input,
|
25
|
+
{ param: Shape },
|
26
|
+
false,
|
27
|
+
{ shape: { a: { b: Integer } } }
|
28
|
+
)
|
29
|
+
end
|
30
|
+
|
31
|
+
it 'should return a hash when a pemitted is of Array shape(deep)' do
|
32
|
+
input = { param: { a: { b: [1, 2] } } }
|
33
|
+
expect(input).to eq permitted_params(
|
34
|
+
input,
|
35
|
+
{ param: Shape },
|
36
|
+
false,
|
37
|
+
{ shape: { a: { b: Array } } }
|
38
|
+
)
|
39
|
+
end
|
40
|
+
|
41
|
+
it 'should return a empty object when a pemitted is shape not defined' do
|
42
|
+
input = { param: { a: 1, b: 2 } }
|
43
|
+
expect({}).to eq permitted_params(
|
44
|
+
input,
|
45
|
+
{ param: Shape },
|
46
|
+
false,
|
47
|
+
{ shape: { a: Integer } }
|
48
|
+
)
|
49
|
+
end
|
50
|
+
end
|
data/spec/permit_params_spec.rb
CHANGED
@@ -1,91 +1,142 @@
|
|
1
|
-
|
2
|
-
|
3
|
-
require
|
4
|
-
require
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require 'test/unit'
|
4
|
+
require 'permit_params'
|
5
|
+
require 'rspec'
|
6
|
+
require 'rack/test'
|
5
7
|
|
6
8
|
include PermitParams
|
7
9
|
|
8
|
-
describe
|
9
|
-
|
10
|
-
|
10
|
+
describe 'behaviours' do
|
11
|
+
it 'should raise error when at least one param is invalid' do
|
12
|
+
input = { param: 'a' }
|
13
|
+
expect do
|
14
|
+
permitted_params(input, { param: Integer }, true)
|
15
|
+
end.to raise_error(InvalidParameterError, "'a' is not a valid Integer")
|
16
|
+
end
|
17
|
+
|
18
|
+
it 'should allow all params when no restriction is given' do
|
19
|
+
input = { param: 'a string' }
|
20
|
+
expect(input).to eq permitted_params(input)
|
21
|
+
end
|
22
|
+
|
23
|
+
it 'should remove a string when permitted param is integer' do
|
24
|
+
input = { param: 'a string' }
|
25
|
+
output = {}
|
26
|
+
expect(output).to eq permitted_params(input, { param: Integer })
|
27
|
+
end
|
28
|
+
|
29
|
+
it 'should return an integer when permitted param is integer' do
|
30
|
+
input = { param: 1 }
|
31
|
+
expect(input).to eq permitted_params(input, { param: Integer })
|
32
|
+
end
|
33
|
+
|
34
|
+
it 'should return an integer when permitted param can be cast into integer' do
|
35
|
+
input = { param: '1' }
|
36
|
+
output = { param: 1 }
|
37
|
+
expect(output).to eq permitted_params(input, { param: Integer })
|
38
|
+
end
|
39
|
+
|
40
|
+
it 'should return a string when permitted param is string' do
|
41
|
+
input = { param: 'a string' }
|
42
|
+
expect(input).to eq permitted_params(input, { param: String })
|
43
|
+
end
|
44
|
+
|
45
|
+
it 'should return a float when permitted param is float' do
|
46
|
+
input = { param: 10.0 }
|
47
|
+
expect(input).to eq permitted_params(input, { param: Float })
|
48
|
+
end
|
49
|
+
|
50
|
+
it 'should return a date when permitted param is date' do
|
51
|
+
input = { param: Date.new }
|
52
|
+
expect(input).to eq permitted_params(input, { param: Date })
|
11
53
|
end
|
12
54
|
|
13
|
-
it
|
14
|
-
input = {
|
15
|
-
expect{
|
16
|
-
permitted_params(input, { param_1: Integer }, true)
|
17
|
-
}.to raise_error(InvalidParameterError, "'a' is not a valid Integer")
|
55
|
+
it 'should return a time when permitted param is time' do
|
56
|
+
input = { param: Time.new }
|
57
|
+
expect(input).to eq permitted_params(input, { param: Time })
|
18
58
|
end
|
19
59
|
|
20
|
-
it
|
21
|
-
input = {
|
22
|
-
|
60
|
+
it 'should return a false(boolean) when permitted param is boolean' do
|
61
|
+
input = { param: 'false' }
|
62
|
+
output = { param: false }
|
63
|
+
expect(output).to eq permitted_params(input, { param: Boolean })
|
23
64
|
end
|
24
65
|
|
25
|
-
it
|
26
|
-
input = {
|
27
|
-
|
66
|
+
it 'should return a true(boolean) when permitted param is boolean' do
|
67
|
+
input = { param: 'true' }
|
68
|
+
output = { param: true }
|
69
|
+
expect(output).to eq permitted_params(input, { param: Boolean })
|
28
70
|
end
|
29
71
|
|
30
|
-
it
|
31
|
-
input = {
|
32
|
-
expect(input).to eq permitted_params(input, {
|
72
|
+
it 'should return an array when permitted param is array' do
|
73
|
+
input = { param: [1, 2] }
|
74
|
+
expect(input).to eq permitted_params(input, { param: Array })
|
33
75
|
end
|
34
76
|
|
35
|
-
it
|
36
|
-
input = {
|
37
|
-
|
77
|
+
it 'should return an array when permitted param is array' do
|
78
|
+
input = { param: '1, 2' }
|
79
|
+
output = { param: %w[1 2] }
|
80
|
+
expect(output).to eq permitted_params(input, { param: Array })
|
38
81
|
end
|
39
82
|
|
40
|
-
it
|
41
|
-
input = {
|
42
|
-
|
83
|
+
it 'should return an array when permitted param is array' do
|
84
|
+
input = { param: '1; 2' }
|
85
|
+
output = { param: %w[1 2] }
|
86
|
+
expect(output).to eq permitted_params(input, { param: Array }, false, { delimiter: ';' })
|
43
87
|
end
|
44
88
|
|
45
|
-
it
|
46
|
-
input = {
|
47
|
-
output = {
|
48
|
-
expect(output).to eq permitted_params(input, {
|
89
|
+
it 'should return an empty hash when permitted param is array with wrong delimiter' do
|
90
|
+
input = { param: '1; 2' }
|
91
|
+
output = {}
|
92
|
+
expect(output).to eq permitted_params(input, { param: Array }, false, { delimiter: ',' })
|
49
93
|
end
|
50
94
|
|
51
|
-
it
|
52
|
-
input = {
|
53
|
-
output = {
|
54
|
-
expect(output).to eq permitted_params(input, {
|
95
|
+
it 'should return a hash when permitted param is hash' do
|
96
|
+
input = { param: 'a: 1, b: 2' }
|
97
|
+
output = { param: { 'a' => '1', 'b' => '2' } }
|
98
|
+
expect(output).to eq permitted_params(input, { param: Hash })
|
55
99
|
end
|
56
100
|
|
57
|
-
it
|
58
|
-
input = {
|
59
|
-
output = {
|
60
|
-
expect(output).to eq permitted_params(input, {
|
101
|
+
it 'should return a hash when permitted param is hash' do
|
102
|
+
input = { param: 'a: 1; b: 2' }
|
103
|
+
output = { param: { 'a' => '1', 'b' => '2' } }
|
104
|
+
expect(output).to eq permitted_params(input, { param: Hash }, false, { delimiter: ';' })
|
105
|
+
end
|
106
|
+
|
107
|
+
it 'should return an empty hash when permitted param is hash with wrong separator' do
|
108
|
+
input = { param: 'a: 1; b: 2' }
|
109
|
+
output = {}
|
110
|
+
expect(output).to eq permitted_params(input, { param: Hash }, false, { separator: '.' })
|
61
111
|
end
|
62
112
|
|
63
|
-
it
|
64
|
-
input = {
|
65
|
-
|
113
|
+
it 'should return an empty hash when permitted param is hash with wrong delimiter' do
|
114
|
+
input = { param: 'a: 1; b: 2' }
|
115
|
+
output = {}
|
116
|
+
expect(output).to eq permitted_params(input, { param: Hash }, false, { delimiter: ',' })
|
66
117
|
end
|
67
118
|
|
68
|
-
it
|
69
|
-
input = {
|
70
|
-
expect(input).to eq permitted_params(input, {
|
119
|
+
it 'should return a hash when permitted param is hash' do
|
120
|
+
input = { param: { a: 1 } }
|
121
|
+
expect(input).to eq permitted_params(input, { param: Hash })
|
71
122
|
end
|
72
123
|
|
73
|
-
it
|
74
|
-
input = {
|
75
|
-
expect(input).to eq permitted_params(input, {
|
124
|
+
it 'should return a hash when permitted param is hash' do
|
125
|
+
input = { param: { a: { b: 1 } } }
|
126
|
+
expect(input).to eq permitted_params(input, { param: Hash })
|
76
127
|
end
|
77
128
|
|
78
|
-
it
|
79
|
-
input = {
|
80
|
-
expect(input).to eq permitted_params(input, {
|
129
|
+
it 'should return a hash when permitted param is hash' do
|
130
|
+
input = { param: { "a": 1 } }
|
131
|
+
expect(input).to eq permitted_params(input, { param: Hash })
|
81
132
|
end
|
82
133
|
|
83
|
-
it
|
84
|
-
input = { number: 1, string:
|
85
|
-
output = { number: 1, string:
|
134
|
+
it 'should return a several types for several inputs' do
|
135
|
+
input = { number: 1, string: 'string', bol: 'true', array: [1, 2], hsh: { a: 3 } }
|
136
|
+
output = { number: 1, string: 'string', bol: true, array: [1, 2], hsh: { a: 3 } }
|
86
137
|
expect(output).to eq permitted_params(
|
87
|
-
input,
|
88
|
-
{
|
138
|
+
input,
|
139
|
+
{
|
89
140
|
number: Integer,
|
90
141
|
string: String,
|
91
142
|
bol: Boolean,
|
@@ -95,24 +146,30 @@ describe "exceptions" do
|
|
95
146
|
)
|
96
147
|
end
|
97
148
|
|
98
|
-
it
|
99
|
-
|
100
|
-
|
101
|
-
expect(output).to eq permitted_params(input, { param_1: Any })
|
149
|
+
it 'returns the paramter without casting if Any' do
|
150
|
+
class TestClass
|
151
|
+
attr_accessor :some_attribute
|
102
152
|
|
103
|
-
|
104
|
-
|
105
|
-
|
153
|
+
def initialize(some_attribute: nil)
|
154
|
+
@some_attribute = some_attribute
|
155
|
+
end
|
156
|
+
end
|
106
157
|
|
107
|
-
|
108
|
-
|
109
|
-
output
|
110
|
-
expect(output).to eq permitted_params(input, { param_1: Integer })
|
111
|
-
end
|
158
|
+
input = { param: '1' }
|
159
|
+
output = { param: '1' }
|
160
|
+
expect(output).to eq permitted_params(input, { param: Any })
|
112
161
|
|
113
|
-
|
114
|
-
|
115
|
-
|
162
|
+
input = {
|
163
|
+
param: TestClass.new(some_attribute: 'a string')
|
164
|
+
}
|
165
|
+
output = permitted_params(input, { param: Any })
|
166
|
+
expect(input[:param].some_attribute).to eq output[:param].some_attribute
|
167
|
+
|
168
|
+
input = {
|
169
|
+
param: TestClass.new(some_attribute: 1),
|
170
|
+
antoher_param: 2
|
171
|
+
}
|
172
|
+
output = permitted_params(input, { param: Any })
|
173
|
+
expect(input[:param].some_attribute).to eq output[:param].some_attribute
|
116
174
|
end
|
117
175
|
end
|
118
|
-
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: sinatra-my-params
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0.
|
4
|
+
version: 0.0.10
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Marco Aviles
|
@@ -10,7 +10,7 @@ bindir: bin
|
|
10
10
|
cert_chain: []
|
11
11
|
date: 2021-09-19 00:00:00.000000000 Z
|
12
12
|
dependencies: []
|
13
|
-
description: A simple
|
13
|
+
description: A simple params sanitizer (originally created for sinatra)
|
14
14
|
email: gdmarav374@gmail.com
|
15
15
|
executables: []
|
16
16
|
extensions: []
|
@@ -19,6 +19,7 @@ files:
|
|
19
19
|
- Rakefile
|
20
20
|
- bin/permit_params
|
21
21
|
- lib/permit_params.rb
|
22
|
+
- spec/permit_params_shape_spec.rb
|
22
23
|
- spec/permit_params_spec.rb
|
23
24
|
homepage: https://github.com/mhero/sinatra-my-params
|
24
25
|
licenses: []
|
@@ -44,3 +45,4 @@ specification_version: 3
|
|
44
45
|
summary: permit_params!
|
45
46
|
test_files:
|
46
47
|
- spec/permit_params_spec.rb
|
48
|
+
- spec/permit_params_shape_spec.rb
|