rubanok 0.1.1 → 0.4.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 +4 -4
- data/CHANGELOG.md +59 -0
- data/LICENSE.txt +1 -1
- data/README.md +231 -33
- data/lib/rubanok.rb +8 -4
- data/lib/rubanok/dsl/mapping.rb +22 -5
- data/lib/rubanok/dsl/matching.rb +40 -16
- data/lib/rubanok/processor.rb +144 -0
- data/lib/rubanok/rails/controller.rb +59 -14
- data/lib/rubanok/railtie.rb +6 -0
- data/lib/rubanok/rspec.rb +25 -11
- data/lib/rubanok/rule.rb +32 -24
- data/lib/rubanok/version.rb +1 -1
- data/sig/rubanok.rbs +6 -0
- data/sig/rubanok/dsl/mapping.rbs +18 -0
- data/sig/rubanok/dsl/matching.rbs +44 -0
- data/sig/rubanok/processor.rbs +53 -0
- data/sig/rubanok/rule.rbs +29 -0
- data/sig/rubanok/version.rbs +3 -0
- data/sig/typeprof.rb +25 -0
- metadata +27 -58
- data/.gitignore +0 -12
- data/.rspec +0 -3
- data/.rubocop.yml +0 -63
- data/.travis.yml +0 -24
- data/Gemfile +0 -13
- data/Gemfile.local +0 -2
- data/Rakefile +0 -10
- data/bin/console +0 -8
- data/bin/setup +0 -8
- data/gemfiles/rails42.gemfile +0 -6
- data/gemfiles/rails52.gemfile +0 -6
- data/gemfiles/railsmaster.gemfile +0 -5
- data/lib/rubanok/ext/symbolize_keys.rb +0 -13
- data/lib/rubanok/plane.rb +0 -92
- data/rubanok.gemspec +0 -35
data/lib/rubanok/rule.rb
CHANGED
@@ -1,23 +1,39 @@
|
|
1
1
|
# frozen_string_literal: true
|
2
2
|
|
3
3
|
module Rubanok
|
4
|
+
using(Module.new do
|
5
|
+
refine NilClass do
|
6
|
+
def empty?
|
7
|
+
true
|
8
|
+
end
|
9
|
+
end
|
10
|
+
|
11
|
+
refine Object do
|
12
|
+
def empty?
|
13
|
+
false
|
14
|
+
end
|
15
|
+
end
|
16
|
+
end)
|
17
|
+
|
4
18
|
class Rule # :nodoc:
|
5
|
-
UNDEFINED =
|
19
|
+
UNDEFINED = Object.new
|
6
20
|
|
7
|
-
attr_reader :fields, :activate_on, :activate_always
|
21
|
+
attr_reader :fields, :activate_on, :activate_always, :ignore_empty_values, :filter_with
|
8
22
|
|
9
|
-
def initialize(fields, activate_on: fields, activate_always: false)
|
23
|
+
def initialize(fields, activate_on: fields, activate_always: false, ignore_empty_values: Rubanok.ignore_empty_values, filter_with: nil)
|
10
24
|
@fields = fields.freeze
|
11
|
-
@activate_on
|
25
|
+
# @type var activate_on: Array[Symbol]
|
26
|
+
activate_on = Array(activate_on)
|
27
|
+
@activate_on = activate_on.freeze
|
12
28
|
@activate_always = activate_always
|
29
|
+
@ignore_empty_values = ignore_empty_values
|
30
|
+
@filter_with = filter_with
|
13
31
|
end
|
14
32
|
|
15
33
|
def project(params)
|
16
34
|
fields.each_with_object({}) do |field, acc|
|
17
35
|
val = fetch_value params, field
|
18
|
-
|
19
|
-
|
20
|
-
acc[field] = val
|
36
|
+
acc[field] = val if val != UNDEFINED
|
21
37
|
acc
|
22
38
|
end
|
23
39
|
end
|
@@ -25,7 +41,7 @@ module Rubanok
|
|
25
41
|
def applicable?(params)
|
26
42
|
return true if activate_always == true
|
27
43
|
|
28
|
-
activate_on.all? { |field| params
|
44
|
+
activate_on.all? { |field| fetch_value(params, field) != UNDEFINED }
|
29
45
|
end
|
30
46
|
|
31
47
|
def to_method_name
|
@@ -39,27 +55,19 @@ module Rubanok
|
|
39
55
|
end
|
40
56
|
|
41
57
|
def fetch_value(params, field)
|
42
|
-
return UNDEFINED
|
58
|
+
return UNDEFINED unless params.key?(field)
|
43
59
|
|
44
|
-
params[field]
|
45
|
-
end
|
60
|
+
val = params[field]
|
46
61
|
|
47
|
-
|
48
|
-
refine NilClass do
|
49
|
-
def empty?
|
50
|
-
true
|
51
|
-
end
|
52
|
-
end
|
62
|
+
val = filter_with&.call(val) if filter_with
|
53
63
|
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
end
|
59
|
-
end)
|
64
|
+
return UNDEFINED if empty?(val)
|
65
|
+
|
66
|
+
val
|
67
|
+
end
|
60
68
|
|
61
69
|
def empty?(val)
|
62
|
-
return false unless
|
70
|
+
return false unless ignore_empty_values
|
63
71
|
|
64
72
|
val.empty?
|
65
73
|
end
|
data/lib/rubanok/version.rb
CHANGED
data/sig/rubanok.rbs
ADDED
@@ -0,0 +1,18 @@
|
|
1
|
+
module Rubanok
|
2
|
+
module DSL
|
3
|
+
module Mapping : Processor
|
4
|
+
class Rule < Rubanok::Rule
|
5
|
+
METHOD_PREFIX: String
|
6
|
+
|
7
|
+
private
|
8
|
+
def build_method_name: () -> String
|
9
|
+
end
|
10
|
+
|
11
|
+
module ClassMethods : Module, _RulesAdding
|
12
|
+
def map: (*field fields, ?activate_on: (field | Array[field]), ?activate_always: bool, ?ignore_empty_values: bool, ?filter_with: Symbol) { () -> input } -> void
|
13
|
+
end
|
14
|
+
|
15
|
+
def self.included: (singleton(Processor) base) -> void
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
@@ -0,0 +1,44 @@
|
|
1
|
+
module Rubanok
|
2
|
+
class UnexpectedInputError < StandardError
|
3
|
+
end
|
4
|
+
|
5
|
+
module DSL
|
6
|
+
module Matching : Processor
|
7
|
+
class Rule < Rubanok::Rule
|
8
|
+
METHOD_PREFIX: String
|
9
|
+
@method_name: String
|
10
|
+
@fields: Array[field]
|
11
|
+
|
12
|
+
class Clause < Rubanok::Rule
|
13
|
+
@fields: Array[field]
|
14
|
+
|
15
|
+
attr_reader values: params
|
16
|
+
attr_reader id: String
|
17
|
+
attr_reader block: ^() -> input
|
18
|
+
|
19
|
+
def initialize: (String id, Array[field] fields, untyped values, ?activate_on: field | Array[field], ?activate_always: bool) { () -> input } -> void
|
20
|
+
def applicable?: (params) -> bool
|
21
|
+
|
22
|
+
alias to_method_name id
|
23
|
+
end
|
24
|
+
|
25
|
+
attr_reader clauses: Array[Clause]
|
26
|
+
|
27
|
+
def matching_clause: (hash params) -> Clause?
|
28
|
+
def having: (*untyped values) { () -> input } -> void
|
29
|
+
def default: () { () -> input } -> void
|
30
|
+
|
31
|
+
private
|
32
|
+
def build_method_name: () -> String
|
33
|
+
end
|
34
|
+
|
35
|
+
module ClassMethods : Module, _RulesAdding, Matching
|
36
|
+
def match: (*field fields, ?activate_on: field | Array[field], ?activate_always: bool, ?fail_when_no_matches: bool?) { (Rule) -> void } -> void
|
37
|
+
end
|
38
|
+
|
39
|
+
def self.included: (singleton(Processor) base) -> void
|
40
|
+
|
41
|
+
def default_match_handler: (Rule rule, hash params, bool? fail_when_no_matches) -> void
|
42
|
+
end
|
43
|
+
end
|
44
|
+
end
|
@@ -0,0 +1,53 @@
|
|
1
|
+
module Rubanok
|
2
|
+
# Transformation parameters
|
3
|
+
type params = Hash[Symbol | String, untyped]
|
4
|
+
# Untyped Hash
|
5
|
+
type hash = Hash[untyped, untyped]
|
6
|
+
type field = Symbol
|
7
|
+
# Transformation target (we assume that input and output types are the same)
|
8
|
+
type input = Object?
|
9
|
+
|
10
|
+
interface _RulesAdding
|
11
|
+
def add_rule: (Rule rule) -> void
|
12
|
+
end
|
13
|
+
|
14
|
+
class Processor
|
15
|
+
extend DSL::Matching::ClassMethods
|
16
|
+
|
17
|
+
extend DSL::Mapping::ClassMethods
|
18
|
+
|
19
|
+
extend _RulesAdding
|
20
|
+
|
21
|
+
UNDEFINED: Object
|
22
|
+
|
23
|
+
self.@rules: Array[Rule]
|
24
|
+
self.@fields_set: Set[field]
|
25
|
+
|
26
|
+
def self.superclass: () -> singleton(Processor)
|
27
|
+
|
28
|
+
def self.call: (input, params) -> input
|
29
|
+
| (params) -> input
|
30
|
+
def self.rules: () -> Array[Rule]
|
31
|
+
def self.fields_set: () -> Set[field]
|
32
|
+
def self.project: (params) -> params
|
33
|
+
def self.prepare: () { () -> input } -> void
|
34
|
+
|
35
|
+
def initialize: (input) -> void
|
36
|
+
def call: (params) -> input
|
37
|
+
|
38
|
+
attr_accessor input: input
|
39
|
+
|
40
|
+
private
|
41
|
+
attr_accessor prepared: bool
|
42
|
+
|
43
|
+
alias raw input
|
44
|
+
alias prepared? prepared
|
45
|
+
|
46
|
+
def apply_rule!: (Rule rule, params) -> void
|
47
|
+
def prepare: () -> input
|
48
|
+
def prepare!: () -> void
|
49
|
+
def rules: () -> Array[Rule]
|
50
|
+
end
|
51
|
+
|
52
|
+
Plane: singleton(Processor)
|
53
|
+
end
|
@@ -0,0 +1,29 @@
|
|
1
|
+
module Rubanok
|
2
|
+
class Rule
|
3
|
+
UNDEFINED: Object
|
4
|
+
|
5
|
+
@method_name: String
|
6
|
+
|
7
|
+
attr_reader fields: Array[field]
|
8
|
+
attr_reader activate_on: Array[field]
|
9
|
+
attr_reader activate_always: bool
|
10
|
+
attr_reader ignore_empty_values: bool
|
11
|
+
attr_reader filter_with: Method?
|
12
|
+
|
13
|
+
%a{rbs:test:skip} def initialize: (
|
14
|
+
Array[field] fields,
|
15
|
+
?activate_on: field | Array[field],
|
16
|
+
?activate_always: bool,
|
17
|
+
?ignore_empty_values: bool,
|
18
|
+
?filter_with: Method?
|
19
|
+
) -> void
|
20
|
+
def project: (params) -> params
|
21
|
+
def applicable?: (params) -> bool
|
22
|
+
def to_method_name: () -> String
|
23
|
+
|
24
|
+
private
|
25
|
+
def build_method_name: () -> String
|
26
|
+
def fetch_value: (params, field) -> Object
|
27
|
+
def empty?: (untyped) -> bool
|
28
|
+
end
|
29
|
+
end
|
data/sig/typeprof.rb
ADDED
@@ -0,0 +1,25 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
# Run typeprofiler:
|
4
|
+
#
|
5
|
+
# typeprof -Ilib sig/typeprof.rb
|
6
|
+
require "rubanok"
|
7
|
+
|
8
|
+
processor = Class.new(Rubanok::Processor) do
|
9
|
+
map :q do |q:|
|
10
|
+
raw
|
11
|
+
end
|
12
|
+
|
13
|
+
match :sort_by, :sort, activate_on: :sort_by do
|
14
|
+
having "status", "asc" do
|
15
|
+
raw
|
16
|
+
end
|
17
|
+
|
18
|
+
default do |sort_by:, sort: "asc"|
|
19
|
+
raw
|
20
|
+
end
|
21
|
+
end
|
22
|
+
end
|
23
|
+
|
24
|
+
processor.project({q: "search", sort_by: "name"})
|
25
|
+
processor.call([], {q: "search", sort_by: "name"})
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: rubanok
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.4.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Vladimir Dementyev
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2021-03-05 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: actionpack
|
@@ -16,28 +16,28 @@ dependencies:
|
|
16
16
|
requirements:
|
17
17
|
- - ">="
|
18
18
|
- !ruby/object:Gem::Version
|
19
|
-
version: '
|
19
|
+
version: '5.2'
|
20
20
|
type: :development
|
21
21
|
prerelease: false
|
22
22
|
version_requirements: !ruby/object:Gem::Requirement
|
23
23
|
requirements:
|
24
24
|
- - ">="
|
25
25
|
- !ruby/object:Gem::Version
|
26
|
-
version: '
|
26
|
+
version: '5.2'
|
27
27
|
- !ruby/object:Gem::Dependency
|
28
28
|
name: actionview
|
29
29
|
requirement: !ruby/object:Gem::Requirement
|
30
30
|
requirements:
|
31
31
|
- - ">="
|
32
32
|
- !ruby/object:Gem::Version
|
33
|
-
version: '
|
33
|
+
version: '5.2'
|
34
34
|
type: :development
|
35
35
|
prerelease: false
|
36
36
|
version_requirements: !ruby/object:Gem::Requirement
|
37
37
|
requirements:
|
38
38
|
- - ">="
|
39
39
|
- !ruby/object:Gem::Version
|
40
|
-
version: '
|
40
|
+
version: '5.2'
|
41
41
|
- !ruby/object:Gem::Dependency
|
42
42
|
name: bundler
|
43
43
|
requirement: !ruby/object:Gem::Requirement
|
@@ -54,62 +54,34 @@ dependencies:
|
|
54
54
|
version: '1.16'
|
55
55
|
- !ruby/object:Gem::Dependency
|
56
56
|
name: rake
|
57
|
-
requirement: !ruby/object:Gem::Requirement
|
58
|
-
requirements:
|
59
|
-
- - "~>"
|
60
|
-
- !ruby/object:Gem::Version
|
61
|
-
version: '10.0'
|
62
|
-
type: :development
|
63
|
-
prerelease: false
|
64
|
-
version_requirements: !ruby/object:Gem::Requirement
|
65
|
-
requirements:
|
66
|
-
- - "~>"
|
67
|
-
- !ruby/object:Gem::Version
|
68
|
-
version: '10.0'
|
69
|
-
- !ruby/object:Gem::Dependency
|
70
|
-
name: rspec
|
71
|
-
requirement: !ruby/object:Gem::Requirement
|
72
|
-
requirements:
|
73
|
-
- - "~>"
|
74
|
-
- !ruby/object:Gem::Version
|
75
|
-
version: '3.0'
|
76
|
-
type: :development
|
77
|
-
prerelease: false
|
78
|
-
version_requirements: !ruby/object:Gem::Requirement
|
79
|
-
requirements:
|
80
|
-
- - "~>"
|
81
|
-
- !ruby/object:Gem::Version
|
82
|
-
version: '3.0'
|
83
|
-
- !ruby/object:Gem::Dependency
|
84
|
-
name: rspec-rails
|
85
57
|
requirement: !ruby/object:Gem::Requirement
|
86
58
|
requirements:
|
87
59
|
- - ">="
|
88
60
|
- !ruby/object:Gem::Version
|
89
|
-
version: '0'
|
61
|
+
version: '13.0'
|
90
62
|
type: :development
|
91
63
|
prerelease: false
|
92
64
|
version_requirements: !ruby/object:Gem::Requirement
|
93
65
|
requirements:
|
94
66
|
- - ">="
|
95
67
|
- !ruby/object:Gem::Version
|
96
|
-
version: '0'
|
68
|
+
version: '13.0'
|
97
69
|
- !ruby/object:Gem::Dependency
|
98
|
-
name:
|
70
|
+
name: rspec
|
99
71
|
requirement: !ruby/object:Gem::Requirement
|
100
72
|
requirements:
|
101
73
|
- - ">="
|
102
74
|
- !ruby/object:Gem::Version
|
103
|
-
version: '0'
|
75
|
+
version: '3.0'
|
104
76
|
type: :development
|
105
77
|
prerelease: false
|
106
78
|
version_requirements: !ruby/object:Gem::Requirement
|
107
79
|
requirements:
|
108
80
|
- - ">="
|
109
81
|
- !ruby/object:Gem::Version
|
110
|
-
version: '0'
|
82
|
+
version: '3.0'
|
111
83
|
- !ruby/object:Gem::Dependency
|
112
|
-
name:
|
84
|
+
name: rspec-rails
|
113
85
|
requirement: !ruby/object:Gem::Requirement
|
114
86
|
requirements:
|
115
87
|
- - ">="
|
@@ -129,36 +101,34 @@ executables: []
|
|
129
101
|
extensions: []
|
130
102
|
extra_rdoc_files: []
|
131
103
|
files:
|
132
|
-
- ".gitignore"
|
133
|
-
- ".rspec"
|
134
|
-
- ".rubocop.yml"
|
135
|
-
- ".travis.yml"
|
136
104
|
- CHANGELOG.md
|
137
|
-
- Gemfile
|
138
|
-
- Gemfile.local
|
139
105
|
- LICENSE.txt
|
140
106
|
- README.md
|
141
|
-
- Rakefile
|
142
|
-
- bin/console
|
143
|
-
- bin/setup
|
144
|
-
- gemfiles/rails42.gemfile
|
145
|
-
- gemfiles/rails52.gemfile
|
146
|
-
- gemfiles/railsmaster.gemfile
|
147
107
|
- lib/rubanok.rb
|
148
108
|
- lib/rubanok/dsl/mapping.rb
|
149
109
|
- lib/rubanok/dsl/matching.rb
|
150
|
-
- lib/rubanok/
|
151
|
-
- lib/rubanok/plane.rb
|
110
|
+
- lib/rubanok/processor.rb
|
152
111
|
- lib/rubanok/rails/controller.rb
|
153
112
|
- lib/rubanok/railtie.rb
|
154
113
|
- lib/rubanok/rspec.rb
|
155
114
|
- lib/rubanok/rule.rb
|
156
115
|
- lib/rubanok/version.rb
|
157
|
-
- rubanok.
|
116
|
+
- sig/rubanok.rbs
|
117
|
+
- sig/rubanok/dsl/mapping.rbs
|
118
|
+
- sig/rubanok/dsl/matching.rbs
|
119
|
+
- sig/rubanok/processor.rbs
|
120
|
+
- sig/rubanok/rule.rbs
|
121
|
+
- sig/rubanok/version.rbs
|
122
|
+
- sig/typeprof.rb
|
158
123
|
homepage: https://github.com/palkan/rubanok
|
159
124
|
licenses:
|
160
125
|
- MIT
|
161
|
-
metadata:
|
126
|
+
metadata:
|
127
|
+
bug_tracker_uri: http://github.com/palkan/rubanok/issues
|
128
|
+
changelog_uri: https://github.com/palkan/rubanok/blob/master/CHANGELOG.md
|
129
|
+
documentation_uri: http://github.com/palkan/rubanok
|
130
|
+
homepage_uri: http://github.com/palkan/rubanok
|
131
|
+
source_code_uri: http://github.com/palkan/rubanok
|
162
132
|
post_install_message:
|
163
133
|
rdoc_options: []
|
164
134
|
require_paths:
|
@@ -174,8 +144,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
174
144
|
- !ruby/object:Gem::Version
|
175
145
|
version: '0'
|
176
146
|
requirements: []
|
177
|
-
|
178
|
-
rubygems_version: 2.7.6
|
147
|
+
rubygems_version: 3.0.6
|
179
148
|
signing_key:
|
180
149
|
specification_version: 4
|
181
150
|
summary: Parameters-based transformation DSL
|