params_ready 0.0.7 → 0.0.8
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/params_ready/builder.rb +17 -0
- data/lib/params_ready/extensions/delegation.rb +1 -0
- data/lib/params_ready/extensions/freezer.rb +2 -0
- data/lib/params_ready/extensions/undefined.rb +8 -0
- data/lib/params_ready/helpers/arel_builder.rb +96 -35
- data/lib/params_ready/helpers/callable.rb +14 -0
- data/lib/params_ready/helpers/interface_definer.rb +48 -0
- data/lib/params_ready/helpers/memo.rb +0 -1
- data/lib/params_ready/helpers/options.rb +77 -9
- data/lib/params_ready/helpers/parameter_storage_class_methods.rb +27 -0
- data/lib/params_ready/helpers/parameter_user_class_methods.rb +18 -14
- data/lib/params_ready/helpers/rule.rb +30 -11
- data/lib/params_ready/helpers/usage_rule.rb +21 -3
- data/lib/params_ready/marshaller/array_marshallers.rb +4 -3
- data/lib/params_ready/marshaller/{hash_set_marshallers.rb → enum_set_marshallers.rb} +5 -5
- data/lib/params_ready/marshaller/polymorph_marshallers.rb +2 -2
- data/lib/params_ready/marshaller/{hash_marshallers.rb → struct_marshallers.rb} +5 -5
- data/lib/params_ready/marshaller/tuple_marshallers.rb +2 -2
- data/lib/params_ready/ordering/column.rb +1 -1
- data/lib/params_ready/output_parameters.rb +11 -0
- data/lib/params_ready/pagination/keyset_pagination.rb +5 -5
- data/lib/params_ready/parameter/{abstract_hash_parameter.rb → abstract_struct_parameter.rb} +5 -5
- data/lib/params_ready/parameter/array_parameter.rb +2 -2
- data/lib/params_ready/parameter/definition.rb +17 -2
- data/lib/params_ready/parameter/{hash_set_parameter.rb → enum_set_parameter.rb} +11 -10
- data/lib/params_ready/parameter/parameter.rb +25 -11
- data/lib/params_ready/parameter/state.rb +4 -4
- data/lib/params_ready/parameter/{hash_parameter.rb → struct_parameter.rb} +11 -10
- data/lib/params_ready/parameter/tuple_parameter.rb +1 -1
- data/lib/params_ready/parameter/value_parameter.rb +1 -1
- data/lib/params_ready/parameter_user.rb +7 -15
- data/lib/params_ready/query/array_grouping.rb +4 -4
- data/lib/params_ready/query/exists_predicate.rb +3 -3
- data/lib/params_ready/query/grouping.rb +8 -2
- data/lib/params_ready/query/join_clause.rb +91 -28
- data/lib/params_ready/query/predicate.rb +3 -3
- data/lib/params_ready/query/relation.rb +29 -14
- data/lib/params_ready/query/structured_grouping.rb +4 -4
- data/lib/params_ready/query/variable_operator_predicate.rb +10 -10
- data/lib/params_ready/value/coder.rb +7 -2
- data/lib/params_ready/version.rb +7 -0
- data/lib/params_ready.rb +3 -11
- metadata +10 -7
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: f153e27fbce45bc4e81a566ef856825db2dea6a144e2122202728e6f937e7b9f
|
4
|
+
data.tar.gz: 1d5c56bcc909fa607022cb1f236a91ab4707dbf6753cd4f8ed1d1702a80be997
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: a8f822219c2fa60a422bf9afb4d483e882eb61aa25a16491534feadf351c8eae8648576e3efcd9bc4e45889701946d8c48a1b5870b440d8e2eb2692cb9368c9a
|
7
|
+
data.tar.gz: 93ce29aafd6b755cc9a628f8ee7ff58c4d2b7c8f5f0b9dede9a75f8fb67e1255dd6e89ae9890ab61ef3737dcdf1d4d9c847dcab9ddd371250ed71a729f135e39
|
data/lib/params_ready/builder.rb
CHANGED
@@ -28,6 +28,23 @@ module ParamsReady
|
|
28
28
|
register_builder(name, self)
|
29
29
|
end
|
30
30
|
|
31
|
+
def self.register_deprecated(name, use:)
|
32
|
+
raise ParamsReadyError, 'Recommended replacement must not be nil' if use.nil?
|
33
|
+
@deprecated ||= {}
|
34
|
+
@deprecated[name] = use.to_s.freeze
|
35
|
+
register_builder(name, self)
|
36
|
+
end
|
37
|
+
|
38
|
+
class << self
|
39
|
+
alias_method :fetch_builder, :builder
|
40
|
+
end
|
41
|
+
|
42
|
+
def self.builder(name)
|
43
|
+
use = @deprecated[name] if @deprecated&.key? name
|
44
|
+
warn "Builder name deprecated: #{name}, use: #{use}" unless use.nil?
|
45
|
+
fetch_builder(name)
|
46
|
+
end
|
47
|
+
|
31
48
|
def self.define_parameter(type, *args, **opts, &block)
|
32
49
|
builder_class = builder(type)
|
33
50
|
builder = builder_class.instance(*args, **opts)
|
@@ -25,6 +25,8 @@ module ParamsReady
|
|
25
25
|
next if frozen?
|
26
26
|
self.class.variables_to_freeze.each do |(ivar, block)|
|
27
27
|
variable = instance_variable_get ivar
|
28
|
+
next if Extensions::Undefined.value_indefinite?(variable)
|
29
|
+
|
28
30
|
block.call(variable) unless block.nil?
|
29
31
|
variable.freeze
|
30
32
|
end
|
@@ -2,26 +2,7 @@ require_relative '../error'
|
|
2
2
|
|
3
3
|
module ParamsReady
|
4
4
|
module Helpers
|
5
|
-
|
6
|
-
def self.instance(object, arel_table: nil)
|
7
|
-
case object
|
8
|
-
when Arel::Nodes::Node, Arel::Nodes::SqlLiteral, Arel::Attribute
|
9
|
-
raise ParamsReadyError, "Arel table unexpected" unless arel_table.nil? || arel_table == :none
|
10
|
-
ArelObject.new(object)
|
11
|
-
when Proc
|
12
|
-
raise ParamsReadyError, "Arel table unexpected" unless arel_table.nil? || arel_table == :none
|
13
|
-
Callable.new(object)
|
14
|
-
when String, Symbol
|
15
|
-
Literal.new(object, arel_table)
|
16
|
-
else
|
17
|
-
raise ParamsReadyError, "Unexpected type for arel builder: #{object.class.name}"
|
18
|
-
end
|
19
|
-
end
|
20
|
-
|
21
|
-
def self.safe_name(name)
|
22
|
-
name[0...64]
|
23
|
-
end
|
24
|
-
|
5
|
+
module ArelBuilder
|
25
6
|
class Callable
|
26
7
|
def initialize(proc)
|
27
8
|
@proc = proc
|
@@ -31,38 +12,118 @@ module ParamsReady
|
|
31
12
|
result = @proc.call(*args)
|
32
13
|
case result
|
33
14
|
when String, Symbol
|
34
|
-
|
15
|
+
to_literal(result).to_arel(*args)
|
35
16
|
else
|
36
17
|
result
|
37
18
|
end
|
38
19
|
end
|
20
|
+
|
21
|
+
def to_literal(*)
|
22
|
+
raise ParamsReadyError, "Unimplemented: #{self.class.name}##{__callee__}"
|
23
|
+
end
|
24
|
+
end
|
25
|
+
|
26
|
+
class ArelObject
|
27
|
+
def initialize(node)
|
28
|
+
@node = node
|
29
|
+
end
|
30
|
+
|
31
|
+
def to_arel(*)
|
32
|
+
@node
|
33
|
+
end
|
34
|
+
end
|
35
|
+
|
36
|
+
def self.safe_name(name)
|
37
|
+
name[0...64]
|
39
38
|
end
|
40
39
|
|
41
40
|
class Literal
|
42
|
-
def initialize(literal
|
43
|
-
@literal = literal.to_s
|
44
|
-
@arel_table = arel_table
|
41
|
+
def initialize(literal)
|
42
|
+
@literal = literal.to_s.freeze
|
45
43
|
end
|
46
44
|
|
47
|
-
def to_arel(
|
48
|
-
|
49
|
-
|
50
|
-
|
45
|
+
def to_arel(*)
|
46
|
+
Arel::Nodes::SqlLiteral.new(@literal)
|
47
|
+
end
|
48
|
+
end
|
49
|
+
|
50
|
+
class Attribute
|
51
|
+
def self.instance(object, arel_table: nil)
|
52
|
+
case object
|
53
|
+
when Arel::Nodes::Node, Arel::Nodes::SqlLiteral, Arel::Attribute
|
54
|
+
raise ParamsReadyError, "Arel table unexpected" unless arel_table.nil? || arel_table == :none
|
55
|
+
ArelObject.new(object)
|
56
|
+
when Proc
|
57
|
+
raise ParamsReadyError, "Arel table unexpected" unless arel_table.nil? || arel_table == :none
|
58
|
+
Callable.new(object)
|
59
|
+
when String, Symbol
|
60
|
+
Literal.new(object, arel_table)
|
51
61
|
else
|
52
|
-
|
62
|
+
raise ParamsReadyError, "Unexpected type for arel builder: #{object.class.name}"
|
63
|
+
end
|
64
|
+
end
|
65
|
+
|
66
|
+
class Callable < ArelBuilder::Callable
|
67
|
+
def to_literal(string)
|
68
|
+
Helpers::ArelBuilder::Attribute.instance(string)
|
69
|
+
end
|
70
|
+
end
|
71
|
+
|
72
|
+
class Literal < ArelBuilder::Literal
|
73
|
+
def initialize(literal, arel_table)
|
74
|
+
super literal
|
75
|
+
@arel_table = arel_table
|
76
|
+
end
|
77
|
+
|
78
|
+
def to_arel(default_table, *args)
|
79
|
+
arel_table = @arel_table || default_table
|
80
|
+
if arel_table == :none
|
81
|
+
super(*args)
|
82
|
+
else
|
83
|
+
arel_table[@literal]
|
84
|
+
end
|
53
85
|
end
|
54
86
|
end
|
55
87
|
end
|
56
88
|
|
57
|
-
class
|
58
|
-
def
|
59
|
-
|
89
|
+
class Table
|
90
|
+
def self.instance(object, table_alias: nil)
|
91
|
+
case object
|
92
|
+
when Arel::Table, Arel::Nodes::TableAlias
|
93
|
+
raise ParamsReadyError, "Table alias unexpected" unless table_alias.nil?
|
94
|
+
ArelObject.new(object)
|
95
|
+
when Proc
|
96
|
+
Callable.new(object, table_alias)
|
97
|
+
when String, Symbol
|
98
|
+
Literal.new(object, table_alias)
|
99
|
+
else
|
100
|
+
raise ParamsReadyError, "Unexpected type for arel builder: #{object.class.name}"
|
101
|
+
end
|
60
102
|
end
|
61
103
|
|
62
|
-
|
63
|
-
|
104
|
+
class Callable < ArelBuilder::Callable
|
105
|
+
def initialize(proc, table_alias)
|
106
|
+
super proc
|
107
|
+
@table_alias = table_alias
|
108
|
+
end
|
109
|
+
|
110
|
+
def to_literal(string)
|
111
|
+
Helpers::ArelBuilder::Table.instance(string, table_alias: @table_alias)
|
112
|
+
end
|
113
|
+
end
|
114
|
+
|
115
|
+
class Literal < ArelBuilder::Literal
|
116
|
+
def initialize(literal, table_alias)
|
117
|
+
super literal
|
118
|
+
raise "Table alias must be present" if table_alias.nil?
|
119
|
+
@table_alias = table_alias.to_s.freeze
|
120
|
+
end
|
121
|
+
|
122
|
+
def to_arel(*)
|
123
|
+
Arel::Table.new(@literal).as(@table_alias)
|
124
|
+
end
|
64
125
|
end
|
65
126
|
end
|
66
127
|
end
|
67
128
|
end
|
68
|
-
end
|
129
|
+
end
|
@@ -0,0 +1,48 @@
|
|
1
|
+
module ParamsReady
|
2
|
+
module Helpers
|
3
|
+
class InterfaceDefiner
|
4
|
+
def initialize(action_names, user)
|
5
|
+
@action_names = action_names
|
6
|
+
@user = user
|
7
|
+
end
|
8
|
+
|
9
|
+
def parameters(*names)
|
10
|
+
names.each do |name|
|
11
|
+
parameter(name)
|
12
|
+
end
|
13
|
+
end
|
14
|
+
|
15
|
+
def relations(*names)
|
16
|
+
names.each do |name|
|
17
|
+
relation(name)
|
18
|
+
end
|
19
|
+
end
|
20
|
+
|
21
|
+
def parameter(name)
|
22
|
+
@user.use_parameter(name, only: @action_names)
|
23
|
+
end
|
24
|
+
|
25
|
+
def relation(name)
|
26
|
+
@user.use_relation(name, only: @action_names)
|
27
|
+
end
|
28
|
+
|
29
|
+
def define(parameter: nil, relation: nil, parameters: [], relations: [], &block)
|
30
|
+
parameters = self.class.complete_list(parameter, parameters)
|
31
|
+
parameters(*parameters)
|
32
|
+
relations = self.class.complete_list(relation, relations)
|
33
|
+
relations(*relations)
|
34
|
+
instance_eval(&block) unless block.nil?
|
35
|
+
@option
|
36
|
+
end
|
37
|
+
|
38
|
+
def self.complete_list(singular, plural)
|
39
|
+
list = singular.nil? ? plural : [singular, *plural]
|
40
|
+
normalize_list(list)
|
41
|
+
end
|
42
|
+
|
43
|
+
def self.normalize_list(list)
|
44
|
+
list.map(&:to_sym)
|
45
|
+
end
|
46
|
+
end
|
47
|
+
end
|
48
|
+
end
|
@@ -3,37 +3,105 @@ require_relative 'usage_rule'
|
|
3
3
|
|
4
4
|
module ParamsReady
|
5
5
|
module Helpers
|
6
|
-
class Options
|
6
|
+
class Options
|
7
7
|
attr_reader :parameters, :relations
|
8
8
|
|
9
9
|
def initialize
|
10
|
-
super
|
11
10
|
@parameter_rules = Hash.new
|
12
11
|
@relation_rules = Hash.new
|
13
|
-
@
|
12
|
+
@memo = { definitions: {} }
|
13
|
+
end
|
14
|
+
|
15
|
+
def reset_memo!(*args)
|
16
|
+
args.each do |key|
|
17
|
+
@memo[key].clear
|
18
|
+
end
|
19
|
+
end
|
20
|
+
|
21
|
+
def dup
|
22
|
+
duplicate = Options.new
|
23
|
+
@parameter_rules.each do |_, rule|
|
24
|
+
duplicate.merge_parameter_rule(rule)
|
25
|
+
end
|
26
|
+
@relation_rules.each do |_, rule|
|
27
|
+
duplicate.merge_relation_rule(rule)
|
28
|
+
end
|
29
|
+
duplicate
|
30
|
+
end
|
31
|
+
|
32
|
+
def relation_definitions_for(name)
|
33
|
+
definitions_for(name, relation_rules)
|
34
|
+
end
|
35
|
+
|
36
|
+
def parameter_definitions_for(name)
|
37
|
+
definitions_for(name, parameter_rules)
|
38
|
+
end
|
39
|
+
|
40
|
+
def definitions_for(name, rules)
|
41
|
+
rules.each_with_object([]) do |(_, rule), result|
|
42
|
+
next unless rule.valid_for?(name)
|
43
|
+
|
44
|
+
result << rule.parameter_definition
|
45
|
+
end
|
14
46
|
end
|
15
47
|
|
16
48
|
def use_parameter(param, rule_args = :all)
|
17
49
|
rule = UsageRule.new(param, rule_args)
|
18
|
-
|
50
|
+
merge_parameter_rule(rule)
|
51
|
+
end
|
52
|
+
|
53
|
+
def merge_parameter_rule(rule)
|
54
|
+
reset_memo!(:definitions)
|
55
|
+
@parameter_rules = self.class.merge_rule(rule, @parameter_rules)
|
19
56
|
end
|
20
57
|
|
21
58
|
def use_relation(relation, rule_args = :all)
|
22
59
|
rule = UsageRule.new(relation, rule_args)
|
23
|
-
|
60
|
+
merge_relation_rule(rule)
|
61
|
+
end
|
62
|
+
|
63
|
+
def merge_relation_rule(rule)
|
64
|
+
reset_memo!(:definitions)
|
65
|
+
@relation_rules = self.class.merge_rule(rule, @relation_rules)
|
24
66
|
end
|
25
67
|
|
26
68
|
def parameter_rules
|
27
|
-
|
28
|
-
|
69
|
+
if block_given?
|
70
|
+
@parameter_rules.each_value do |rule|
|
71
|
+
yield rule
|
72
|
+
end
|
29
73
|
end
|
74
|
+
@parameter_rules
|
30
75
|
end
|
31
76
|
|
32
77
|
def relation_rules
|
33
|
-
|
34
|
-
|
78
|
+
if block_given?
|
79
|
+
@relation_rules.each_value do |rule|
|
80
|
+
yield rule
|
81
|
+
end
|
82
|
+
end
|
83
|
+
@relation_rules
|
84
|
+
end
|
85
|
+
|
86
|
+
def create_state_for(key)
|
87
|
+
@memo[:definitions][key] ||= begin
|
88
|
+
builder = Parameter::StateBuilder.instance
|
89
|
+
parameter_definitions_for(key).each do |definition|
|
90
|
+
builder.add definition
|
91
|
+
end
|
92
|
+
relation_definitions_for(key).each do |definition|
|
93
|
+
builder.relation definition
|
94
|
+
end
|
95
|
+
builder.build
|
35
96
|
end
|
36
97
|
end
|
98
|
+
|
99
|
+
def self.merge_rule(rule, rules)
|
100
|
+
existing = rules[rule.name]
|
101
|
+
merged = rule.merge(existing)
|
102
|
+
rules[rule.name] = merged
|
103
|
+
rules
|
104
|
+
end
|
37
105
|
end
|
38
106
|
end
|
39
107
|
end
|
@@ -1,5 +1,6 @@
|
|
1
1
|
require_relative 'storage'
|
2
2
|
require_relative '../error'
|
3
|
+
require_relative 'rule'
|
3
4
|
|
4
5
|
module ParamsReady
|
5
6
|
module Helpers
|
@@ -31,6 +32,32 @@ module ParamsReady
|
|
31
32
|
raise ParamsReadyError, "Unknown parameter '#{sym_key}'"
|
32
33
|
end
|
33
34
|
end
|
35
|
+
|
36
|
+
def include_parameters(parameter_definer, rule = nil)
|
37
|
+
rule = Helpers::Rule(rule)
|
38
|
+
parameter_definer.all_parameters.each do |key, definition|
|
39
|
+
next if rule && !rule.include?(key)
|
40
|
+
|
41
|
+
add_parameter(definition)
|
42
|
+
end
|
43
|
+
end
|
44
|
+
|
45
|
+
def add_parameter(definition)
|
46
|
+
params_ready_storage.add_parameter(definition)
|
47
|
+
end
|
48
|
+
|
49
|
+
def include_relations(parameter_definer, rule = nil)
|
50
|
+
rule = Helpers::Rule(rule)
|
51
|
+
parameter_definer.all_relations.each do |key, definition|
|
52
|
+
next if rule && !rule.include?(key)
|
53
|
+
|
54
|
+
add_relation(definition)
|
55
|
+
end
|
56
|
+
end
|
57
|
+
|
58
|
+
def add_relation(definition)
|
59
|
+
params_ready_storage.add_relation(definition)
|
60
|
+
end
|
34
61
|
end
|
35
62
|
end
|
36
63
|
end
|
@@ -1,31 +1,35 @@
|
|
1
|
+
require_relative 'interface_definer'
|
2
|
+
|
1
3
|
module ParamsReady
|
2
4
|
module Helpers
|
3
5
|
module ParameterUserClassMethods
|
4
|
-
def
|
5
|
-
@
|
6
|
+
def params_ready_option
|
7
|
+
@params_ready_option ||= begin
|
8
|
+
if superclass.respond_to? :params_ready_option
|
9
|
+
# This works on assumption that superclass
|
10
|
+
# definition doesn't change during execution
|
11
|
+
superclass.params_ready_option.dup
|
12
|
+
else
|
13
|
+
ParamsReady::Helpers::Options.new
|
14
|
+
end
|
15
|
+
end
|
6
16
|
end
|
7
17
|
|
8
18
|
def use_parameter(name, rule = :all)
|
9
19
|
parameter = parameter_definition name
|
10
|
-
|
20
|
+
params_ready_option.use_parameter parameter, rule
|
11
21
|
end
|
12
22
|
|
13
23
|
def use_relation(name, rule = :all)
|
14
24
|
relation = relation_definition name
|
15
|
-
|
25
|
+
params_ready_option.use_relation relation, rule
|
16
26
|
end
|
17
27
|
|
18
|
-
def
|
19
|
-
|
20
|
-
params_ready_storage.add_parameter(p)
|
21
|
-
end
|
22
|
-
end
|
28
|
+
def action_interface(*action_names, **opts, &block)
|
29
|
+
definer = InterfaceDefiner.new(action_names, self)
|
23
30
|
|
24
|
-
|
25
|
-
parameter_definer.all_relations.values.each do |d|
|
26
|
-
params_ready_storage.add_relation(d)
|
27
|
-
end
|
31
|
+
definer.define(**opts, &block)
|
28
32
|
end
|
29
33
|
end
|
30
34
|
end
|
31
|
-
end
|
35
|
+
end
|
@@ -6,33 +6,52 @@ module ParamsReady
|
|
6
6
|
return input if input.nil?
|
7
7
|
return input if input.is_a? Rule
|
8
8
|
|
9
|
-
Rule.
|
9
|
+
Rule.instance(input).freeze
|
10
10
|
end
|
11
11
|
|
12
|
-
|
13
|
-
attr_reader :hash
|
12
|
+
class Rule
|
13
|
+
attr_reader :hash, :mode, :values
|
14
14
|
|
15
|
-
def
|
16
|
-
|
17
|
-
when :none, :all then [
|
15
|
+
def self.instance(input)
|
16
|
+
mode, values = case input
|
17
|
+
when :none, :all then [input, nil]
|
18
18
|
when Hash
|
19
|
-
if
|
20
|
-
raise ParamsReadyError, "Unexpected hash for rule: '#{
|
19
|
+
if input.length > 1 || input.length < 1
|
20
|
+
raise ParamsReadyError, "Unexpected hash for rule: '#{input}'"
|
21
21
|
end
|
22
|
-
key, values =
|
22
|
+
key, values = input.first
|
23
23
|
case key
|
24
24
|
when :except, :only then [key, values.to_set.freeze]
|
25
25
|
else
|
26
26
|
raise ParamsReadyError, "Unexpected mode for rule: '#{key}'"
|
27
27
|
end
|
28
28
|
else
|
29
|
-
raise ParamsReadyError, "Unexpected input for rule: '#{
|
29
|
+
raise ParamsReadyError, "Unexpected input for rule: '#{input}'"
|
30
30
|
end
|
31
|
-
|
31
|
+
new(mode, values)
|
32
|
+
end
|
33
|
+
|
34
|
+
def initialize(mode, values)
|
35
|
+
@mode = mode
|
36
|
+
@values = values.freeze
|
32
37
|
@hash = [@mode, @values].hash
|
33
38
|
freeze
|
34
39
|
end
|
35
40
|
|
41
|
+
def merge(other)
|
42
|
+
return self if other.nil?
|
43
|
+
raise ParamsReadyError, "Can't merge with #{other.class.name}" unless other.is_a? Rule
|
44
|
+
raise ParamsReadyError, "Can't merge incompatible rules: #{mode}/#{other.mode}" if other.mode != mode
|
45
|
+
|
46
|
+
case mode
|
47
|
+
when :all, :none
|
48
|
+
self
|
49
|
+
when :only, :except
|
50
|
+
values = self.values + other.values
|
51
|
+
Rule.new(mode, values)
|
52
|
+
end
|
53
|
+
end
|
54
|
+
|
36
55
|
def include?(name)
|
37
56
|
case @mode
|
38
57
|
when :none then false
|
@@ -3,16 +3,34 @@ require_relative 'rule'
|
|
3
3
|
module ParamsReady
|
4
4
|
module Helpers
|
5
5
|
class UsageRule
|
6
|
-
attr_reader :parameter_definition
|
6
|
+
attr_reader :parameter_definition, :rule
|
7
7
|
|
8
8
|
def initialize(parameter_definition, rule = :all)
|
9
9
|
@parameter_definition = parameter_definition
|
10
10
|
@rule = ParamsReady::Helpers::Rule(rule)
|
11
|
+
freeze
|
11
12
|
end
|
12
13
|
|
13
|
-
def valid_for(method)
|
14
|
+
def valid_for?(method)
|
14
15
|
@rule.include? method
|
15
16
|
end
|
17
|
+
|
18
|
+
def name
|
19
|
+
parameter_definition.name
|
20
|
+
end
|
21
|
+
|
22
|
+
def merge(other)
|
23
|
+
return self if other.nil?
|
24
|
+
raise ParamsReadyError, "Can't merge into #{other.class.name}" unless other.is_a? UsageRule
|
25
|
+
|
26
|
+
unless parameter_definition == other.parameter_definition
|
27
|
+
message = "Can't merge incompatible rules: #{parameter_definition.name}/#{other.parameter_definition.name}"
|
28
|
+
raise ParamsReadyError, message
|
29
|
+
end
|
30
|
+
|
31
|
+
rule = self.rule.merge(other.rule)
|
32
|
+
UsageRule.new(parameter_definition, rule)
|
33
|
+
end
|
16
34
|
end
|
17
35
|
end
|
18
|
-
end
|
36
|
+
end
|
@@ -47,7 +47,7 @@ module ParamsReady
|
|
47
47
|
freeze
|
48
48
|
end
|
49
49
|
|
50
|
-
module
|
50
|
+
module StructMarshaller
|
51
51
|
extend AbstractMarshaller
|
52
52
|
|
53
53
|
def self.canonicalize(definition, hash, context, validator)
|
@@ -58,7 +58,8 @@ module ParamsReady
|
|
58
58
|
found, count = Helpers::FindInHash.find_in_hash hash, count_key
|
59
59
|
raise ParamsReadyError, "Count not found" unless found
|
60
60
|
|
61
|
-
|
61
|
+
base = 10 if count.is_a? String
|
62
|
+
count = Integer(count, base)
|
62
63
|
array = (0...count).map do |index|
|
63
64
|
found, value = Helpers::FindInHash.find_in_hash hash, index
|
64
65
|
element = definition.prototype.create
|
@@ -120,7 +121,7 @@ module ParamsReady
|
|
120
121
|
@collection ||= begin
|
121
122
|
c = ClassCollection.new Array
|
122
123
|
c.add_instance Array, ArrayMarshaller
|
123
|
-
c.add_instance Hash,
|
124
|
+
c.add_instance Hash, StructMarshaller
|
124
125
|
c.add_factory :string, StringMarshaller
|
125
126
|
c.default!(Hash)
|
126
127
|
c.freeze
|
@@ -1,9 +1,9 @@
|
|
1
1
|
require_relative 'collection'
|
2
|
-
require_relative '
|
2
|
+
require_relative 'struct_marshallers'
|
3
3
|
|
4
4
|
module ParamsReady
|
5
5
|
module Marshaller
|
6
|
-
class
|
6
|
+
class EnumSetMarshallers
|
7
7
|
module AbstractMarshaller
|
8
8
|
def canonicalize_collection(definition, context, validator, freeze: false)
|
9
9
|
hash = {}
|
@@ -18,7 +18,7 @@ module ParamsReady
|
|
18
18
|
end
|
19
19
|
end
|
20
20
|
|
21
|
-
module
|
21
|
+
module StructMarshaller
|
22
22
|
extend AbstractMarshaller
|
23
23
|
|
24
24
|
def self.canonicalize(definition, hash, context, validator)
|
@@ -30,7 +30,7 @@ module ParamsReady
|
|
30
30
|
|
31
31
|
def self.marshal(parameter, intent)
|
32
32
|
if intent.marshal? parameter.name_for_formatter
|
33
|
-
|
33
|
+
StructMarshallers::StructMarshaller.marshal(parameter, intent)
|
34
34
|
else
|
35
35
|
SetMarshaller.marshal(parameter, intent)
|
36
36
|
end
|
@@ -83,7 +83,7 @@ module ParamsReady
|
|
83
83
|
def self.collection
|
84
84
|
@collection ||= begin
|
85
85
|
c = ClassCollection.new Hash
|
86
|
-
c.add_instance Hash,
|
86
|
+
c.add_instance Hash, StructMarshaller
|
87
87
|
c.add_instance Set, SetMarshaller
|
88
88
|
c.add_instance Array, ArrayMarshaller
|
89
89
|
c.default!(Hash)
|