bmg 0.18.8 → 0.18.12
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +5 -5
- data/lib/bmg/operator/autowrap.rb +21 -7
- data/lib/bmg/operator/page.rb +3 -2
- data/lib/bmg/reader/excel.rb +2 -1
- data/lib/bmg/relation/spied.rb +18 -4
- data/lib/bmg/sql/support/from_clause_orderer.rb +1 -2
- data/lib/bmg/summarizer/first.rb +25 -0
- data/lib/bmg/summarizer/last.rb +25 -0
- data/lib/bmg/summarizer/positional.rb +33 -0
- data/lib/bmg/summarizer.rb +3 -0
- data/lib/bmg/support/ordering.rb +23 -6
- data/lib/bmg/version.rb +1 -1
- metadata +15 -11
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
|
-
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
2
|
+
SHA1:
|
3
|
+
metadata.gz: f6017c8a4f02206eac582bbd66801976c7beeba0
|
4
|
+
data.tar.gz: 5e22c7739d0a16d79ec8a0871dfc9e4a60a4bd9d
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 6eb6a6e24b42e3b3651ea5f73d7481f3c7f22289bd8b450ec5cf5a4ab1ab07e9e63ad47c017ac3dd5d57a0c856e9c5834e2c26e4be6f7a56ece54b1045234fa4
|
7
|
+
data.tar.gz: 0b40fd858dbae47f1069ef1caef71357f9313a3ca0912f288f366ac65b3e32e8068cd0de4206d4822431f2156c680f5a71b18ac8dc0aee112314deb5a3435a5b
|
@@ -22,6 +22,7 @@ module Bmg
|
|
22
22
|
|
23
23
|
DEFAULT_OPTIONS = {
|
24
24
|
:postprocessor => :none,
|
25
|
+
:postprocessor_condition => :all,
|
25
26
|
:split => "_"
|
26
27
|
}
|
27
28
|
|
@@ -167,7 +168,7 @@ module Bmg
|
|
167
168
|
|
168
169
|
def normalize_options(options)
|
169
170
|
opts = DEFAULT_OPTIONS.merge(options)
|
170
|
-
opts[:postprocessor] = NoLeftJoinNoise.new(opts[:postprocessor])
|
171
|
+
opts[:postprocessor] = NoLeftJoinNoise.new(opts[:postprocessor], opts[:postprocessor_condition])
|
171
172
|
opts
|
172
173
|
end
|
173
174
|
|
@@ -209,17 +210,17 @@ module Bmg
|
|
209
210
|
class NoLeftJoinNoise
|
210
211
|
|
211
212
|
REMOVERS = {
|
212
|
-
nil:
|
213
|
-
delete:
|
214
|
-
none:
|
213
|
+
nil: ->(t,k){ t[k] = nil },
|
214
|
+
delete: ->(t,k){ t.delete(k) },
|
215
|
+
none: ->(t,k){ t }
|
215
216
|
}
|
216
217
|
|
217
|
-
def self.new(remover)
|
218
|
+
def self.new(remover, remover_condition = :all)
|
218
219
|
return remover if remover.is_a?(NoLeftJoinNoise)
|
219
220
|
super
|
220
221
|
end
|
221
222
|
|
222
|
-
def initialize(remover)
|
223
|
+
def initialize(remover, remover_condition = :all)
|
223
224
|
@remover_to_s = remover
|
224
225
|
@remover = case remover
|
225
226
|
when NilClass then REMOVERS[:none]
|
@@ -229,22 +230,35 @@ module Bmg
|
|
229
230
|
else
|
230
231
|
raise "Invalid remover `#{remover}`"
|
231
232
|
end
|
233
|
+
@remover_condition = case remover_condition
|
234
|
+
when :all then ->(tuple){ all_nil?(tuple) }
|
235
|
+
when :id then ->(tuple){ id_nil?(tuple) }
|
236
|
+
else
|
237
|
+
raise "Invalid remover condition `#{remover_condition}`"
|
238
|
+
end
|
232
239
|
end
|
233
240
|
attr_reader :remover
|
234
241
|
|
235
242
|
def call(tuple)
|
236
243
|
tuple.each_key do |k|
|
237
244
|
call(tuple[k]) if tuple[k].is_a?(Hash)
|
238
|
-
@remover.call(tuple, k) if tuple[k].is_a?(Hash) &&
|
245
|
+
@remover.call(tuple, k) if tuple[k].is_a?(Hash) && @remover_condition.call(tuple[k])
|
239
246
|
end
|
240
247
|
tuple
|
241
248
|
end
|
242
249
|
|
243
250
|
def all_nil?(tuple)
|
244
251
|
return false unless tuple.is_a?(Hash)
|
252
|
+
|
245
253
|
tuple.all?{|(k,v)| v.nil? || all_nil?(tuple[k]) }
|
246
254
|
end
|
247
255
|
|
256
|
+
def id_nil?(tuple)
|
257
|
+
return false unless tuple.is_a?(Hash)
|
258
|
+
|
259
|
+
tuple[:id].nil?
|
260
|
+
end
|
261
|
+
|
248
262
|
def inspect
|
249
263
|
@remover_to_s.inspect
|
250
264
|
end
|
data/lib/bmg/operator/page.rb
CHANGED
@@ -32,7 +32,8 @@ module Bmg
|
|
32
32
|
def each(&bl)
|
33
33
|
return to_enum unless block_given?
|
34
34
|
page_size = options[:page_size]
|
35
|
-
@operand
|
35
|
+
@operand
|
36
|
+
.to_a
|
36
37
|
.sort(&comparator)
|
37
38
|
.drop(page_size * (page_index-1))
|
38
39
|
.take(page_size)
|
@@ -46,7 +47,7 @@ module Bmg
|
|
46
47
|
protected ### inspect
|
47
48
|
|
48
49
|
def comparator
|
49
|
-
Ordering.new(@ordering).comparator
|
50
|
+
@comparator ||= Ordering.new(@ordering).comparator
|
50
51
|
end
|
51
52
|
|
52
53
|
def args
|
data/lib/bmg/reader/excel.rb
CHANGED
@@ -4,6 +4,7 @@ module Bmg
|
|
4
4
|
include Reader
|
5
5
|
|
6
6
|
DEFAULT_OPTIONS = {
|
7
|
+
sheet: 0,
|
7
8
|
skip: 0,
|
8
9
|
row_num: true
|
9
10
|
}
|
@@ -19,7 +20,7 @@ module Bmg
|
|
19
20
|
require 'roo'
|
20
21
|
xlsx = Roo::Spreadsheet.open(@path, @options)
|
21
22
|
headers = nil
|
22
|
-
xlsx.sheet(
|
23
|
+
xlsx.sheet(@options[:sheet])
|
23
24
|
.each
|
24
25
|
.drop(@options[:skip])
|
25
26
|
.each_with_index
|
data/lib/bmg/relation/spied.rb
CHANGED
@@ -24,13 +24,27 @@ module Bmg
|
|
24
24
|
protected :type=
|
25
25
|
|
26
26
|
def each(&bl)
|
27
|
-
|
28
|
-
|
27
|
+
return enum_for(:each) unless bl
|
28
|
+
|
29
|
+
if spy.respond_to?(:measure)
|
30
|
+
spy.measure(self) do
|
31
|
+
operand.each(&bl)
|
32
|
+
end
|
33
|
+
else
|
34
|
+
spy.call(self)
|
35
|
+
operand.each(&bl)
|
36
|
+
end
|
29
37
|
end
|
30
38
|
|
31
39
|
def count
|
32
|
-
spy.
|
33
|
-
|
40
|
+
if spy.respond_to?(:measure)
|
41
|
+
spy.measure(self) do
|
42
|
+
operand.count
|
43
|
+
end
|
44
|
+
else
|
45
|
+
spy.call(self)
|
46
|
+
operand.count
|
47
|
+
end
|
34
48
|
end
|
35
49
|
|
36
50
|
def to_ast
|
@@ -213,8 +213,7 @@ module Bmg
|
|
213
213
|
def _collect_joins(sexpr, joins)
|
214
214
|
case sexpr.first
|
215
215
|
when :and
|
216
|
-
|
217
|
-
_collect_joins(sexpr[2], joins)
|
216
|
+
sexpr[1..-1].each{ |term| _collect_joins(term, joins) }
|
218
217
|
when :eq
|
219
218
|
joins << sexpr
|
220
219
|
else
|
@@ -0,0 +1,25 @@
|
|
1
|
+
module Bmg
|
2
|
+
class Summarizer
|
3
|
+
#
|
4
|
+
# First summarizer.
|
5
|
+
#
|
6
|
+
# Example:
|
7
|
+
#
|
8
|
+
# # direct ruby usage
|
9
|
+
# Bmg::Summarizer.first(:qty, :order => [:id]).summarize(...)
|
10
|
+
#
|
11
|
+
class First < Positional
|
12
|
+
|
13
|
+
def choose(t1, t2)
|
14
|
+
t1
|
15
|
+
end
|
16
|
+
|
17
|
+
end # class First
|
18
|
+
|
19
|
+
# Factors a first summarizer
|
20
|
+
def self.first(*args, &bl)
|
21
|
+
First.new(*args, &bl)
|
22
|
+
end
|
23
|
+
|
24
|
+
end # class Summarizer
|
25
|
+
end # module Bmg
|
@@ -0,0 +1,25 @@
|
|
1
|
+
module Bmg
|
2
|
+
class Summarizer
|
3
|
+
#
|
4
|
+
# Last summarizer.
|
5
|
+
#
|
6
|
+
# Example:
|
7
|
+
#
|
8
|
+
# # direct ruby usage
|
9
|
+
# Bmg::Summarizer.last(:qty, :order => [:id]).summarize(...)
|
10
|
+
#
|
11
|
+
class Last < Positional
|
12
|
+
|
13
|
+
def choose(t1, t2)
|
14
|
+
t2
|
15
|
+
end
|
16
|
+
|
17
|
+
end # class Last
|
18
|
+
|
19
|
+
# Factors a last summarizer
|
20
|
+
def self.last(*args, &bl)
|
21
|
+
Last.new(*args, &bl)
|
22
|
+
end
|
23
|
+
|
24
|
+
end # class Summarizer
|
25
|
+
end # module Bmg
|
@@ -0,0 +1,33 @@
|
|
1
|
+
module Bmg
|
2
|
+
class Summarizer
|
3
|
+
# See First and Last
|
4
|
+
class Positional < Summarizer
|
5
|
+
|
6
|
+
def initialize(*args, &block)
|
7
|
+
super
|
8
|
+
raise ArgumentError, "Missing order" unless options[:order]
|
9
|
+
@ordering = Ordering.new(options[:order])
|
10
|
+
end
|
11
|
+
attr_reader :ordering
|
12
|
+
|
13
|
+
def least
|
14
|
+
nil
|
15
|
+
end
|
16
|
+
|
17
|
+
def happens(memo, tuple)
|
18
|
+
if memo.nil?
|
19
|
+
tuple
|
20
|
+
else
|
21
|
+
c = ordering.call(memo, tuple)
|
22
|
+
c <= 0 ? choose(memo, tuple) : choose(tuple, memo)
|
23
|
+
end
|
24
|
+
end
|
25
|
+
|
26
|
+
def finalize(memo)
|
27
|
+
return nil if memo.nil?
|
28
|
+
extract_value(memo)
|
29
|
+
end
|
30
|
+
|
31
|
+
end # class Positional
|
32
|
+
end # class Summarizer
|
33
|
+
end # module Bmg
|
data/lib/bmg/summarizer.rb
CHANGED
@@ -169,3 +169,6 @@ require_relative 'summarizer/concat'
|
|
169
169
|
require_relative 'summarizer/by_proc'
|
170
170
|
require_relative 'summarizer/multiple'
|
171
171
|
require_relative 'summarizer/value_by'
|
172
|
+
require_relative 'summarizer/positional'
|
173
|
+
require_relative 'summarizer/first'
|
174
|
+
require_relative 'summarizer/last'
|
data/lib/bmg/support/ordering.rb
CHANGED
@@ -6,14 +6,31 @@ module Bmg
|
|
6
6
|
end
|
7
7
|
attr_reader :attrs
|
8
8
|
|
9
|
+
def call(t1, t2)
|
10
|
+
comparator.call(t1, t2)
|
11
|
+
end
|
12
|
+
|
9
13
|
def comparator
|
10
|
-
->(t1, t2) {
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
+
@comparator ||= ->(t1, t2) { compare_attrs(t1, t2) }
|
15
|
+
end
|
16
|
+
|
17
|
+
def compare_attrs(t1, t2)
|
18
|
+
attrs.each do |(attr,direction)|
|
19
|
+
a1, a2 = t1[attr], t2[attr]
|
20
|
+
if a1.nil? && a2.nil?
|
21
|
+
0
|
22
|
+
elsif a1.nil?
|
23
|
+
return direction == :desc ? -1 : 1
|
24
|
+
elsif a2.nil?
|
25
|
+
return direction == :desc ? 1 : -1
|
26
|
+
elsif a1.respond_to?(:<=>)
|
27
|
+
c = a1 <=> a2
|
28
|
+
unless c.nil? || c==0
|
29
|
+
return direction == :desc ? -c : c
|
30
|
+
end
|
14
31
|
end
|
15
|
-
|
16
|
-
|
32
|
+
end
|
33
|
+
0
|
17
34
|
end
|
18
35
|
|
19
36
|
end # class Ordering
|
data/lib/bmg/version.rb
CHANGED
metadata
CHANGED
@@ -1,35 +1,35 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: bmg
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.18.
|
4
|
+
version: 0.18.12
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Bernard Lambeau
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2022-01-24 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: predicate
|
15
15
|
requirement: !ruby/object:Gem::Requirement
|
16
16
|
requirements:
|
17
|
-
- - ">="
|
18
|
-
- !ruby/object:Gem::Version
|
19
|
-
version: 2.5.0
|
20
17
|
- - "~>"
|
21
18
|
- !ruby/object:Gem::Version
|
22
|
-
version: '2.
|
19
|
+
version: '2.6'
|
20
|
+
- - ">="
|
21
|
+
- !ruby/object:Gem::Version
|
22
|
+
version: 2.6.0
|
23
23
|
type: :runtime
|
24
24
|
prerelease: false
|
25
25
|
version_requirements: !ruby/object:Gem::Requirement
|
26
26
|
requirements:
|
27
|
-
- - ">="
|
28
|
-
- !ruby/object:Gem::Version
|
29
|
-
version: 2.5.0
|
30
27
|
- - "~>"
|
31
28
|
- !ruby/object:Gem::Version
|
32
|
-
version: '2.
|
29
|
+
version: '2.6'
|
30
|
+
- - ">="
|
31
|
+
- !ruby/object:Gem::Version
|
32
|
+
version: 2.6.0
|
33
33
|
- !ruby/object:Gem::Dependency
|
34
34
|
name: path
|
35
35
|
requirement: !ruby/object:Gem::Requirement
|
@@ -274,10 +274,13 @@ files:
|
|
274
274
|
- lib/bmg/summarizer/count.rb
|
275
275
|
- lib/bmg/summarizer/distinct.rb
|
276
276
|
- lib/bmg/summarizer/distinct_count.rb
|
277
|
+
- lib/bmg/summarizer/first.rb
|
278
|
+
- lib/bmg/summarizer/last.rb
|
277
279
|
- lib/bmg/summarizer/max.rb
|
278
280
|
- lib/bmg/summarizer/min.rb
|
279
281
|
- lib/bmg/summarizer/multiple.rb
|
280
282
|
- lib/bmg/summarizer/percentile.rb
|
283
|
+
- lib/bmg/summarizer/positional.rb
|
281
284
|
- lib/bmg/summarizer/stddev.rb
|
282
285
|
- lib/bmg/summarizer/sum.rb
|
283
286
|
- lib/bmg/summarizer/value_by.rb
|
@@ -314,7 +317,8 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
314
317
|
- !ruby/object:Gem::Version
|
315
318
|
version: '0'
|
316
319
|
requirements: []
|
317
|
-
|
320
|
+
rubyforge_project:
|
321
|
+
rubygems_version: 2.6.14.4
|
318
322
|
signing_key:
|
319
323
|
specification_version: 4
|
320
324
|
summary: Bmg is Alf's successor.
|