bmg 0.9.1 → 0.10.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (92) hide show
  1. checksums.yaml +4 -4
  2. data/lib/bmg/algebra.rb +2 -26
  3. data/lib/bmg/algebra/shortcuts.rb +14 -0
  4. data/lib/bmg/operator/autowrap.rb +32 -2
  5. data/lib/bmg/operator/constants.rb +12 -0
  6. data/lib/bmg/operator/image.rb +10 -0
  7. data/lib/bmg/operator/rename.rb +8 -0
  8. data/lib/bmg/relation/spied.rb +4 -9
  9. data/lib/bmg/sequel.rb +53 -2
  10. data/lib/bmg/sequel/relation.rb +24 -19
  11. data/lib/bmg/sequel/translator.rb +153 -0
  12. data/lib/bmg/sequel/type_inference.rb +42 -0
  13. data/lib/bmg/sql.rb +20 -0
  14. data/lib/bmg/sql/builder.rb +177 -0
  15. data/lib/bmg/sql/dialect.rb +15 -0
  16. data/lib/bmg/sql/ext/predicate.rb +23 -0
  17. data/lib/bmg/sql/ext/predicate/and.rb +9 -0
  18. data/lib/bmg/sql/ext/predicate/contradiction.rb +10 -0
  19. data/lib/bmg/sql/ext/predicate/dyadic_comp.rb +12 -0
  20. data/lib/bmg/sql/ext/predicate/eq.rb +9 -0
  21. data/lib/bmg/sql/ext/predicate/exists.rb +12 -0
  22. data/lib/bmg/sql/ext/predicate/expr.rb +18 -0
  23. data/lib/bmg/sql/ext/predicate/gt.rb +9 -0
  24. data/lib/bmg/sql/ext/predicate/gte.rb +9 -0
  25. data/lib/bmg/sql/ext/predicate/identifier.rb +10 -0
  26. data/lib/bmg/sql/ext/predicate/in.rb +29 -0
  27. data/lib/bmg/sql/ext/predicate/literal.rb +10 -0
  28. data/lib/bmg/sql/ext/predicate/lt.rb +9 -0
  29. data/lib/bmg/sql/ext/predicate/lte.rb +9 -0
  30. data/lib/bmg/sql/ext/predicate/nadic_bool.rb +16 -0
  31. data/lib/bmg/sql/ext/predicate/native.rb +9 -0
  32. data/lib/bmg/sql/ext/predicate/neq.rb +9 -0
  33. data/lib/bmg/sql/ext/predicate/not.rb +12 -0
  34. data/lib/bmg/sql/ext/predicate/or.rb +9 -0
  35. data/lib/bmg/sql/ext/predicate/qualified_identifier.rb +12 -0
  36. data/lib/bmg/sql/ext/predicate/tautology.rb +10 -0
  37. data/lib/bmg/sql/grammar.rb +45 -0
  38. data/lib/bmg/sql/grammar.sexp.yml +96 -0
  39. data/lib/bmg/sql/nodes/column_name.rb +25 -0
  40. data/lib/bmg/sql/nodes/cross_join.rb +28 -0
  41. data/lib/bmg/sql/nodes/except.rb +14 -0
  42. data/lib/bmg/sql/nodes/expr.rb +94 -0
  43. data/lib/bmg/sql/nodes/from_clause.rb +24 -0
  44. data/lib/bmg/sql/nodes/inner_join.rb +37 -0
  45. data/lib/bmg/sql/nodes/intersect.rb +14 -0
  46. data/lib/bmg/sql/nodes/limit_clause.rb +19 -0
  47. data/lib/bmg/sql/nodes/literal.rb +18 -0
  48. data/lib/bmg/sql/nodes/name_intro.rb +23 -0
  49. data/lib/bmg/sql/nodes/native_table_as.rb +31 -0
  50. data/lib/bmg/sql/nodes/offset_clause.rb +19 -0
  51. data/lib/bmg/sql/nodes/order_by_clause.rb +25 -0
  52. data/lib/bmg/sql/nodes/order_by_term.rb +30 -0
  53. data/lib/bmg/sql/nodes/qualified_name.rb +32 -0
  54. data/lib/bmg/sql/nodes/range_var_name.rb +17 -0
  55. data/lib/bmg/sql/nodes/select_exp.rb +109 -0
  56. data/lib/bmg/sql/nodes/select_item.rb +37 -0
  57. data/lib/bmg/sql/nodes/select_list.rb +35 -0
  58. data/lib/bmg/sql/nodes/select_star.rb +22 -0
  59. data/lib/bmg/sql/nodes/set_operator.rb +68 -0
  60. data/lib/bmg/sql/nodes/set_quantifier.rb +20 -0
  61. data/lib/bmg/sql/nodes/subquery_as.rb +28 -0
  62. data/lib/bmg/sql/nodes/table_as.rb +31 -0
  63. data/lib/bmg/sql/nodes/table_name.rb +17 -0
  64. data/lib/bmg/sql/nodes/union.rb +14 -0
  65. data/lib/bmg/sql/nodes/where_clause.rb +20 -0
  66. data/lib/bmg/sql/nodes/with_exp.rb +51 -0
  67. data/lib/bmg/sql/nodes/with_spec.rb +24 -0
  68. data/lib/bmg/sql/processor.rb +85 -0
  69. data/lib/bmg/sql/processor/all.rb +17 -0
  70. data/lib/bmg/sql/processor/clip.rb +57 -0
  71. data/lib/bmg/sql/processor/distinct.rb +17 -0
  72. data/lib/bmg/sql/processor/flatten.rb +24 -0
  73. data/lib/bmg/sql/processor/from_self.rb +29 -0
  74. data/lib/bmg/sql/processor/join.rb +80 -0
  75. data/lib/bmg/sql/processor/join_support.rb +28 -0
  76. data/lib/bmg/sql/processor/limit_offset.rb +30 -0
  77. data/lib/bmg/sql/processor/merge.rb +49 -0
  78. data/lib/bmg/sql/processor/order_by.rb +32 -0
  79. data/lib/bmg/sql/processor/rename.rb +25 -0
  80. data/lib/bmg/sql/processor/reorder.rb +21 -0
  81. data/lib/bmg/sql/processor/requalify.rb +24 -0
  82. data/lib/bmg/sql/processor/semi_join.rb +68 -0
  83. data/lib/bmg/sql/processor/star.rb +17 -0
  84. data/lib/bmg/sql/processor/where.rb +25 -0
  85. data/lib/bmg/sql/relation.rb +141 -0
  86. data/lib/bmg/sql/version.rb +16 -0
  87. data/lib/bmg/support.rb +1 -0
  88. data/lib/bmg/support/keys.rb +59 -0
  89. data/lib/bmg/type.rb +95 -14
  90. data/lib/bmg/version.rb +2 -2
  91. data/tasks/test.rake +9 -2
  92. metadata +97 -5
@@ -0,0 +1,14 @@
1
+ module Bmg
2
+ module Sql
3
+ module Intersect
4
+ include SetOperator
5
+
6
+ INTERSECT = "INTERSECT".freeze
7
+
8
+ def keyword
9
+ INTERSECT
10
+ end
11
+
12
+ end # module Intersect
13
+ end # module Sql
14
+ end # module Bmg
@@ -0,0 +1,19 @@
1
+ module Bmg
2
+ module Sql
3
+ module LimitClause
4
+ include Expr
5
+
6
+ LIMIT = "LIMIT"
7
+
8
+ def limit
9
+ last.to_i
10
+ end
11
+
12
+ def to_sql(buffer, dialect)
13
+ buffer << LIMIT << SPACE << limit.to_s
14
+ buffer
15
+ end
16
+
17
+ end # module LimitClause
18
+ end # module Sql
19
+ end # module Bmg
@@ -0,0 +1,18 @@
1
+ module Bmg
2
+ module Sql
3
+ module Literal
4
+ include Expr
5
+ include Predicate::Expr
6
+
7
+ def would_be_name
8
+ nil
9
+ end
10
+
11
+ def to_sql(buffer, dialect)
12
+ to_sql_literal(buffer, last)
13
+ buffer
14
+ end
15
+
16
+ end # module Literal
17
+ end # module Sql
18
+ end # module Bmg
@@ -0,0 +1,23 @@
1
+ module Bmg
2
+ module Sql
3
+ module NameIntro
4
+ include Expr
5
+
6
+ def table_name
7
+ self[1]
8
+ end
9
+
10
+ def subquery
11
+ self[2]
12
+ end
13
+
14
+ def to_sql(buffer, dialect)
15
+ table_name.to_sql(buffer, dialect)
16
+ buffer << SPACE << AS << SPACE
17
+ subquery.to_sql(buffer, dialect, true)
18
+ buffer
19
+ end
20
+
21
+ end # module WithSpec
22
+ end # module Sql
23
+ end # module Bmg
@@ -0,0 +1,31 @@
1
+ module Bmg
2
+ module Sql
3
+ module NativeTableAs
4
+ include Expr
5
+
6
+ def left
7
+ self[1]
8
+ end
9
+
10
+ def right
11
+ self[2]
12
+ end
13
+
14
+ def native_table
15
+ self[1].last
16
+ end
17
+
18
+ def as_name
19
+ self[2].last
20
+ end
21
+
22
+ def to_sql(buffer, dialect)
23
+ buffer << self[1].to_s
24
+ buffer << SPACE << AS << SPACE
25
+ self[2].to_sql(buffer, dialect)
26
+ buffer
27
+ end
28
+
29
+ end # module NativeTableAs
30
+ end # module Sql
31
+ end # module Bmg
@@ -0,0 +1,19 @@
1
+ module Bmg
2
+ module Sql
3
+ module OffsetClause
4
+ include Expr
5
+
6
+ OFFSET = "OFFSET"
7
+
8
+ def offset
9
+ last.to_i
10
+ end
11
+
12
+ def to_sql(buffer, dialect)
13
+ buffer << OFFSET << SPACE << offset.to_s
14
+ buffer
15
+ end
16
+
17
+ end # module OffsetClause
18
+ end # module Sql
19
+ end # module Bmg
@@ -0,0 +1,25 @@
1
+ module Bmg
2
+ module Sql
3
+ module OrderByClause
4
+ include Expr
5
+
6
+ ORDER_BY = "ORDER BY".freeze
7
+
8
+ def to_ordering
9
+ @ordering ||= sexpr_body.map{|x|
10
+ [x.as_name.to_sym, x.direction.to_sym]
11
+ }
12
+ end
13
+
14
+ def to_sql(buffer, dialect)
15
+ buffer << ORDER_BY << SPACE
16
+ each_child do |item,index|
17
+ buffer << COMMA << SPACE unless index == 0
18
+ item.to_sql(buffer, dialect)
19
+ end
20
+ buffer
21
+ end
22
+
23
+ end # module OrderByClause
24
+ end # module Sql
25
+ end # module Bmg
@@ -0,0 +1,30 @@
1
+ module Bmg
2
+ module Sql
3
+ module OrderByTerm
4
+ include Expr
5
+
6
+ def qualified_name
7
+ self[1]
8
+ end
9
+
10
+ def qualifier
11
+ qualified_name.qualifier
12
+ end
13
+
14
+ def as_name
15
+ qualified_name.as_name
16
+ end
17
+
18
+ def direction
19
+ last
20
+ end
21
+
22
+ def to_sql(buffer, dialect)
23
+ self[1].to_sql(buffer, dialect)
24
+ buffer << SPACE << direction.upcase
25
+ buffer
26
+ end
27
+
28
+ end # module OrderByTerm
29
+ end # module Sql
30
+ end # module Bmg
@@ -0,0 +1,32 @@
1
+ module Bmg
2
+ module Sql
3
+ #
4
+ # [:qualified_name,
5
+ # [:range_var_name `qualifier`],
6
+ # [:column_name, `as_name`] ]
7
+ #
8
+ module QualifiedName
9
+ include Expr
10
+
11
+ def qualifier
12
+ self[1].qualifier
13
+ end
14
+
15
+ def as_name
16
+ last.as_name
17
+ end
18
+
19
+ def would_be_name
20
+ as_name
21
+ end
22
+
23
+ def to_sql(buffer, dialect)
24
+ self[1].to_sql(buffer, dialect)
25
+ buffer << '.'
26
+ self[2].to_sql(buffer, dialect)
27
+ buffer
28
+ end
29
+
30
+ end # module QualifiedName
31
+ end # module Sql
32
+ end # module Bmg
@@ -0,0 +1,17 @@
1
+ module Bmg
2
+ module Sql
3
+ module RangeVarName
4
+ include Expr
5
+
6
+ def qualifier
7
+ last
8
+ end
9
+
10
+ def to_sql(buffer, dialect)
11
+ buffer << dialect.quote_identifier(last)
12
+ buffer
13
+ end
14
+
15
+ end # module RangeVarName
16
+ end # module Sql
17
+ end # module Bmg
@@ -0,0 +1,109 @@
1
+ module Bmg
2
+ module Sql
3
+ module SelectExp
4
+ include Expr
5
+
6
+ SELECT_DISTINCT = "SELECT DISTINCT".freeze
7
+
8
+ SELECT = "SELECT".freeze
9
+
10
+ def set_quantifier
11
+ self[1]
12
+ end
13
+
14
+ def with_exp?
15
+ false
16
+ end
17
+
18
+ def is_table_dee?
19
+ from_clause.nil? && select_list.is_table_dee?
20
+ end
21
+
22
+ def distinct?
23
+ set_quantifier.distinct?
24
+ end
25
+
26
+ def all?
27
+ set_quantifier.all?
28
+ end
29
+
30
+ def join?
31
+ from_clause && from_clause.join?
32
+ end
33
+
34
+ def should_be_reused?
35
+ join? or distinct? or complex_clause?
36
+ end
37
+
38
+ def complex_clause?
39
+ where_clause or order_by_clause or limit_clause or offset_clause
40
+ end
41
+
42
+ def select_exp
43
+ self
44
+ end
45
+
46
+ def select_list
47
+ self[2]
48
+ end
49
+
50
+ def is_select_star?
51
+ self[2].first == :select_star
52
+ end
53
+
54
+ def where_clause
55
+ find_child(:where_clause)
56
+ end
57
+
58
+ def predicate
59
+ where_clause && where_clause.predicate
60
+ end
61
+
62
+ def from_clause
63
+ find_child(:from_clause)
64
+ end
65
+
66
+ def table_spec
67
+ from_clause.table_spec
68
+ end
69
+
70
+ def order_by_clause
71
+ find_child(:order_by_clause)
72
+ end
73
+
74
+ def limit_clause
75
+ find_child(:limit_clause)
76
+ end
77
+
78
+ def offset_clause
79
+ find_child(:offset_clause)
80
+ end
81
+
82
+ def desaliaser
83
+ select_list.desaliaser
84
+ end
85
+
86
+ ### to_xxx
87
+
88
+ def to_attr_list
89
+ select_list.to_attr_list
90
+ end
91
+
92
+ ### to_sql
93
+
94
+ def to_sql(buffer, dialect, parenthesize = !buffer.empty?)
95
+ if parenthesize
96
+ sql_parenthesized(buffer){|b| to_sql(b, dialect, false) }
97
+ else
98
+ buffer << (distinct? ? SELECT_DISTINCT : SELECT)
99
+ each_child(1) do |elm,i|
100
+ buffer << SPACE
101
+ elm.to_sql(buffer, dialect)
102
+ end
103
+ buffer
104
+ end
105
+ end
106
+
107
+ end # module SelectExp
108
+ end # module Sql
109
+ end # module Bmg
@@ -0,0 +1,37 @@
1
+ module Bmg
2
+ module Sql
3
+ module SelectItem
4
+ include Expr
5
+
6
+ def left
7
+ self[1]
8
+ end
9
+
10
+ def right
11
+ self[2]
12
+ end
13
+
14
+ def qualifier
15
+ left.qualifier
16
+ end
17
+
18
+ def would_be_name
19
+ left.would_be_name
20
+ end
21
+
22
+ def as_name
23
+ last.as_name
24
+ end
25
+
26
+ def to_sql(buffer, dialect)
27
+ self[1].to_sql(buffer, dialect)
28
+ unless would_be_name == as_name
29
+ buffer << SPACE << AS << SPACE
30
+ last.to_sql(buffer, dialect)
31
+ end
32
+ buffer
33
+ end
34
+
35
+ end # module SelectItem
36
+ end # module Sql
37
+ end # module Bmg
@@ -0,0 +1,35 @@
1
+ module Bmg
2
+ module Sql
3
+ module SelectList
4
+ include Expr
5
+
6
+ def desaliaser
7
+ ->(a){
8
+ item = sexpr_body.find{|item| item.as_name.to_s == a.to_s }
9
+ item && item.left
10
+ }
11
+ end
12
+
13
+ def is_table_dee?
14
+ Builder::IS_TABLE_DEE == self
15
+ end
16
+
17
+ def knows?(as_name)
18
+ find_child{|child| child.as_name == as_name }
19
+ end
20
+
21
+ def to_attr_list
22
+ sexpr_body.map{|a| a.as_name.to_sym }
23
+ end
24
+
25
+ def to_sql(buffer, dialect)
26
+ sexpr_body.each_with_index do |item,index|
27
+ buffer << COMMA << SPACE unless index == 0
28
+ item.to_sql(buffer, dialect)
29
+ end
30
+ buffer
31
+ end
32
+
33
+ end # module SelectList
34
+ end # module Sql
35
+ end # module Bmg
@@ -0,0 +1,22 @@
1
+ module Bmg
2
+ module Sql
3
+ module SelectStar
4
+ include Expr
5
+
6
+ STAR = "*".freeze
7
+
8
+ def desaliaser
9
+ ->(a){
10
+ Predicate::Grammar.sexpr [ :qualified_identifier, last[1], a.to_s ]
11
+ }
12
+ end
13
+
14
+ def to_sql(buffer, dialect)
15
+ last.to_sql(buffer, dialect)
16
+ buffer << DOT << STAR
17
+ buffer
18
+ end
19
+
20
+ end # module SelectStar
21
+ end # module Sql
22
+ end # module Bmg