axiom-sql-generator 0.1.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 +7 -0
- data/.gemtest +0 -0
- data/.gitignore +37 -0
- data/.rspec +4 -0
- data/.rvmrc +1 -0
- data/.travis.yml +35 -0
- data/CONTRIBUTING.md +11 -0
- data/Gemfile +8 -0
- data/Gemfile.devtools +57 -0
- data/Guardfile +23 -0
- data/LICENSE +20 -0
- data/README.md +70 -0
- data/Rakefile +5 -0
- data/TODO +34 -0
- data/axiom-sql-generator.gemspec +25 -0
- data/config/flay.yml +3 -0
- data/config/flog.yml +2 -0
- data/config/mutant.yml +3 -0
- data/config/reek.yml +165 -0
- data/config/yardstick.yml +2 -0
- data/lib/axiom-sql-generator.rb +3 -0
- data/lib/axiom/sql/generator.rb +61 -0
- data/lib/axiom/sql/generator/attribute.rb +25 -0
- data/lib/axiom/sql/generator/core_ext/date.rb +20 -0
- data/lib/axiom/sql/generator/core_ext/date_time.rb +46 -0
- data/lib/axiom/sql/generator/direction.rb +38 -0
- data/lib/axiom/sql/generator/function.rb +55 -0
- data/lib/axiom/sql/generator/function/aggregate.rb +134 -0
- data/lib/axiom/sql/generator/function/connective.rb +53 -0
- data/lib/axiom/sql/generator/function/numeric.rb +135 -0
- data/lib/axiom/sql/generator/function/predicate.rb +266 -0
- data/lib/axiom/sql/generator/function/proposition.rb +38 -0
- data/lib/axiom/sql/generator/function/string.rb +29 -0
- data/lib/axiom/sql/generator/identifier.rb +28 -0
- data/lib/axiom/sql/generator/literal.rb +157 -0
- data/lib/axiom/sql/generator/relation.rb +240 -0
- data/lib/axiom/sql/generator/relation/base.rb +14 -0
- data/lib/axiom/sql/generator/relation/binary.rb +136 -0
- data/lib/axiom/sql/generator/relation/insertion.rb +62 -0
- data/lib/axiom/sql/generator/relation/materialized.rb +60 -0
- data/lib/axiom/sql/generator/relation/set.rb +107 -0
- data/lib/axiom/sql/generator/relation/unary.rb +379 -0
- data/lib/axiom/sql/generator/version.rb +12 -0
- data/lib/axiom/sql/generator/visitor.rb +121 -0
- data/spec/rcov.opts +7 -0
- data/spec/shared/generated_sql_behavior.rb +15 -0
- data/spec/spec_helper.rb +33 -0
- data/spec/support/config_alias.rb +3 -0
- data/spec/unit/axiom/sql/generator/attribute/visit_axiom_attribute_spec.rb +15 -0
- data/spec/unit/axiom/sql/generator/class_methods/parenthesize_spec.rb +18 -0
- data/spec/unit/axiom/sql/generator/direction/visit_axiom_relation_operation_order_ascending_spec.rb +15 -0
- data/spec/unit/axiom/sql/generator/direction/visit_axiom_relation_operation_order_descending_spec.rb +15 -0
- data/spec/unit/axiom/sql/generator/function/aggregate/visit_axiom_aggregate_count_spec.rb +16 -0
- data/spec/unit/axiom/sql/generator/function/aggregate/visit_axiom_aggregate_maximum_spec.rb +16 -0
- data/spec/unit/axiom/sql/generator/function/aggregate/visit_axiom_aggregate_mean_spec.rb +16 -0
- data/spec/unit/axiom/sql/generator/function/aggregate/visit_axiom_aggregate_minimum_spec.rb +16 -0
- data/spec/unit/axiom/sql/generator/function/aggregate/visit_axiom_aggregate_standard_deviation_spec.rb +16 -0
- data/spec/unit/axiom/sql/generator/function/aggregate/visit_axiom_aggregate_sum_spec.rb +16 -0
- data/spec/unit/axiom/sql/generator/function/aggregate/visit_axiom_aggregate_variance_spec.rb +16 -0
- data/spec/unit/axiom/sql/generator/function/connective/visit_axiom_function_connective_conjunction_spec.rb +20 -0
- data/spec/unit/axiom/sql/generator/function/connective/visit_axiom_function_connective_disjunction_spec.rb +20 -0
- data/spec/unit/axiom/sql/generator/function/connective/visit_axiom_function_connective_negation_spec.rb +20 -0
- data/spec/unit/axiom/sql/generator/function/numeric/visit_axiom_function_numeric_absolute_spec.rb +15 -0
- data/spec/unit/axiom/sql/generator/function/numeric/visit_axiom_function_numeric_addition_spec.rb +15 -0
- data/spec/unit/axiom/sql/generator/function/numeric/visit_axiom_function_numeric_division_spec.rb +15 -0
- data/spec/unit/axiom/sql/generator/function/numeric/visit_axiom_function_numeric_exponentiation_spec.rb +15 -0
- data/spec/unit/axiom/sql/generator/function/numeric/visit_axiom_function_numeric_modulo_spec.rb +15 -0
- data/spec/unit/axiom/sql/generator/function/numeric/visit_axiom_function_numeric_multiplication_spec.rb +15 -0
- data/spec/unit/axiom/sql/generator/function/numeric/visit_axiom_function_numeric_square_root_spec.rb +15 -0
- data/spec/unit/axiom/sql/generator/function/numeric/visit_axiom_function_numeric_subtraction_spec.rb +15 -0
- data/spec/unit/axiom/sql/generator/function/numeric/visit_axiom_function_numeric_unary_minus_spec.rb +15 -0
- data/spec/unit/axiom/sql/generator/function/numeric/visit_axiom_function_numeric_unary_plus_spec.rb +15 -0
- data/spec/unit/axiom/sql/generator/function/predicate/visit_axiom_function_predicate_equality_spec.rb +27 -0
- data/spec/unit/axiom/sql/generator/function/predicate/visit_axiom_function_predicate_exclusion_spec.rb +47 -0
- data/spec/unit/axiom/sql/generator/function/predicate/visit_axiom_function_predicate_greater_than_or_equal_to_spec.rb +15 -0
- data/spec/unit/axiom/sql/generator/function/predicate/visit_axiom_function_predicate_greater_than_spec.rb +15 -0
- data/spec/unit/axiom/sql/generator/function/predicate/visit_axiom_function_predicate_inclusion_spec.rb +47 -0
- data/spec/unit/axiom/sql/generator/function/predicate/visit_axiom_function_predicate_inequality_spec.rb +55 -0
- data/spec/unit/axiom/sql/generator/function/predicate/visit_axiom_function_predicate_less_than_or_equal_to_spec.rb +15 -0
- data/spec/unit/axiom/sql/generator/function/predicate/visit_axiom_function_predicate_less_than_spec.rb +15 -0
- data/spec/unit/axiom/sql/generator/function/proposition/visit_axiom_function_proposition_contradiction_spec.rb +15 -0
- data/spec/unit/axiom/sql/generator/function/proposition/visit_axiom_function_proposition_tautology_spec.rb +15 -0
- data/spec/unit/axiom/sql/generator/function/string/visit_axiom_function_string_length_spec.rb +15 -0
- data/spec/unit/axiom/sql/generator/identifier/visit_identifier_spec.rb +26 -0
- data/spec/unit/axiom/sql/generator/literal/class_methods/dup_frozen_spec.rb +23 -0
- data/spec/unit/axiom/sql/generator/literal/visit_class_spec.rb +31 -0
- data/spec/unit/axiom/sql/generator/literal/visit_date_spec.rb +15 -0
- data/spec/unit/axiom/sql/generator/literal/visit_date_time_spec.rb +55 -0
- data/spec/unit/axiom/sql/generator/literal/visit_enumerable_spec.rb +15 -0
- data/spec/unit/axiom/sql/generator/literal/visit_false_class_spec.rb +14 -0
- data/spec/unit/axiom/sql/generator/literal/visit_nil_class_spec.rb +14 -0
- data/spec/unit/axiom/sql/generator/literal/visit_numeric_spec.rb +34 -0
- data/spec/unit/axiom/sql/generator/literal/visit_string_spec.rb +26 -0
- data/spec/unit/axiom/sql/generator/literal/visit_time_spec.rb +97 -0
- data/spec/unit/axiom/sql/generator/literal/visit_true_class_spec.rb +14 -0
- data/spec/unit/axiom/sql/generator/relation/binary/base/to_subquery_spec.rb +35 -0
- data/spec/unit/axiom/sql/generator/relation/binary/base/visit_axiom_relation_base_spec.rb +22 -0
- data/spec/unit/axiom/sql/generator/relation/binary/to_s_spec.rb +35 -0
- data/spec/unit/axiom/sql/generator/relation/binary/to_subquery_spec.rb +35 -0
- data/spec/unit/axiom/sql/generator/relation/binary/visit_axiom_algebra_join_spec.rb +179 -0
- data/spec/unit/axiom/sql/generator/relation/binary/visit_axiom_algebra_product_spec.rb +183 -0
- data/spec/unit/axiom/sql/generator/relation/class_methods/visit_spec.rb +71 -0
- data/spec/unit/axiom/sql/generator/relation/insertion/to_subquery_spec.rb +15 -0
- data/spec/unit/axiom/sql/generator/relation/insertion/visit_axiom_relation_operation_insertion_spec.rb +187 -0
- data/spec/unit/axiom/sql/generator/relation/materialized/visit_axiom_relation_materialized_spec.rb +28 -0
- data/spec/unit/axiom/sql/generator/relation/materialized/visited_spec.rb +26 -0
- data/spec/unit/axiom/sql/generator/relation/name_spec.rb +30 -0
- data/spec/unit/axiom/sql/generator/relation/set/class_methods/normalize_operand_headers_spec.rb +35 -0
- data/spec/unit/axiom/sql/generator/relation/set/to_s_spec.rb +55 -0
- data/spec/unit/axiom/sql/generator/relation/set/to_subquery_spec.rb +55 -0
- data/spec/unit/axiom/sql/generator/relation/set/visit_axiom_algebra_difference_spec.rb +191 -0
- data/spec/unit/axiom/sql/generator/relation/set/visit_axiom_algebra_intersection_spec.rb +188 -0
- data/spec/unit/axiom/sql/generator/relation/set/visit_axiom_algebra_union_spec.rb +188 -0
- data/spec/unit/axiom/sql/generator/relation/to_s_spec.rb +50 -0
- data/spec/unit/axiom/sql/generator/relation/to_sql_spec.rb +52 -0
- data/spec/unit/axiom/sql/generator/relation/to_subquery_spec.rb +49 -0
- data/spec/unit/axiom/sql/generator/relation/unary/to_s_spec.rb +55 -0
- data/spec/unit/axiom/sql/generator/relation/unary/to_subquery_spec.rb +75 -0
- data/spec/unit/axiom/sql/generator/relation/unary/visit_axiom_algebra_extension_spec.rb +165 -0
- data/spec/unit/axiom/sql/generator/relation/unary/visit_axiom_algebra_projection_spec.rb +193 -0
- data/spec/unit/axiom/sql/generator/relation/unary/visit_axiom_algebra_rename_spec.rb +178 -0
- data/spec/unit/axiom/sql/generator/relation/unary/visit_axiom_algebra_restriction_spec.rb +199 -0
- data/spec/unit/axiom/sql/generator/relation/unary/visit_axiom_algebra_summarization_spec.rb +652 -0
- data/spec/unit/axiom/sql/generator/relation/unary/visit_axiom_relation_base_spec.rb +21 -0
- data/spec/unit/axiom/sql/generator/relation/unary/visit_axiom_relation_operation_limit_spec.rb +165 -0
- data/spec/unit/axiom/sql/generator/relation/unary/visit_axiom_relation_operation_offset_spec.rb +165 -0
- data/spec/unit/axiom/sql/generator/relation/unary/visit_axiom_relation_operation_order_spec.rb +183 -0
- data/spec/unit/axiom/sql/generator/relation/unary/visit_axiom_relation_operation_reverse_spec.rb +165 -0
- data/spec/unit/axiom/sql/generator/relation/visit_spec.rb +54 -0
- data/spec/unit/axiom/sql/generator/relation/visited_spec.rb +35 -0
- data/spec/unit/axiom/sql/generator/visitor/class_methods/handler_for_spec.rb +71 -0
- data/spec/unit/axiom/sql/generator/visitor/visit_spec.rb +12 -0
- data/spec/unit/axiom/sql/generator/visitor/visited_spec.rb +11 -0
- data/spec/unit/date/iso8601_spec.rb +23 -0
- data/spec/unit/date_time/iso8601_spec.rb +112 -0
- metadata +325 -0
|
@@ -0,0 +1,61 @@
|
|
|
1
|
+
# encoding: utf-8
|
|
2
|
+
|
|
3
|
+
require 'date'
|
|
4
|
+
require 'time'
|
|
5
|
+
|
|
6
|
+
require 'axiom'
|
|
7
|
+
|
|
8
|
+
require 'axiom/sql/generator/core_ext/date'
|
|
9
|
+
require 'axiom/sql/generator/core_ext/date_time'
|
|
10
|
+
|
|
11
|
+
require 'axiom/sql/generator/visitor'
|
|
12
|
+
|
|
13
|
+
require 'axiom/sql/generator/identifier'
|
|
14
|
+
require 'axiom/sql/generator/attribute'
|
|
15
|
+
require 'axiom/sql/generator/direction'
|
|
16
|
+
require 'axiom/sql/generator/literal'
|
|
17
|
+
|
|
18
|
+
require 'axiom/sql/generator/function'
|
|
19
|
+
require 'axiom/sql/generator/function/aggregate'
|
|
20
|
+
require 'axiom/sql/generator/function/connective'
|
|
21
|
+
require 'axiom/sql/generator/function/numeric'
|
|
22
|
+
require 'axiom/sql/generator/function/predicate'
|
|
23
|
+
require 'axiom/sql/generator/function/proposition'
|
|
24
|
+
require 'axiom/sql/generator/function/string'
|
|
25
|
+
|
|
26
|
+
require 'axiom/sql/generator/relation'
|
|
27
|
+
require 'axiom/sql/generator/relation/unary'
|
|
28
|
+
require 'axiom/sql/generator/relation/base'
|
|
29
|
+
require 'axiom/sql/generator/relation/binary'
|
|
30
|
+
require 'axiom/sql/generator/relation/materialized'
|
|
31
|
+
require 'axiom/sql/generator/relation/set'
|
|
32
|
+
|
|
33
|
+
require 'axiom/sql/generator/relation/insertion'
|
|
34
|
+
|
|
35
|
+
require 'axiom/sql/generator/version'
|
|
36
|
+
|
|
37
|
+
module Axiom
|
|
38
|
+
module SQL
|
|
39
|
+
module Generator
|
|
40
|
+
|
|
41
|
+
# Raised when an invalid relation is visited
|
|
42
|
+
class InvalidRelationError < StandardError; end
|
|
43
|
+
|
|
44
|
+
LEFT_PARENTHESIS = '('.freeze
|
|
45
|
+
RIGHT_PARENTHESIS = ')'.freeze
|
|
46
|
+
|
|
47
|
+
# Return a parenthesized SQL statement (inline modification)
|
|
48
|
+
#
|
|
49
|
+
# @param [#to_s] sql
|
|
50
|
+
#
|
|
51
|
+
# @return [#to_s]
|
|
52
|
+
# same instance as sql
|
|
53
|
+
#
|
|
54
|
+
# @api private
|
|
55
|
+
def self.parenthesize!(sql)
|
|
56
|
+
sql.insert(0, LEFT_PARENTHESIS) << RIGHT_PARENTHESIS
|
|
57
|
+
end
|
|
58
|
+
|
|
59
|
+
end # module Generator
|
|
60
|
+
end # module SQL
|
|
61
|
+
end # module Axiom
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
# encoding: utf-8
|
|
2
|
+
|
|
3
|
+
module Axiom
|
|
4
|
+
module SQL
|
|
5
|
+
module Generator
|
|
6
|
+
|
|
7
|
+
# Generates an SQL statement for an attribute
|
|
8
|
+
module Attribute
|
|
9
|
+
include Identifier
|
|
10
|
+
|
|
11
|
+
# Visit an Attribute
|
|
12
|
+
#
|
|
13
|
+
# @param [Attribute] attribute
|
|
14
|
+
#
|
|
15
|
+
# @return [#to_s]
|
|
16
|
+
#
|
|
17
|
+
# @api private
|
|
18
|
+
def visit_axiom_attribute(attribute)
|
|
19
|
+
visit_identifier(attribute.name)
|
|
20
|
+
end
|
|
21
|
+
|
|
22
|
+
end # module Attribute
|
|
23
|
+
end # module Generator
|
|
24
|
+
end # module SQL
|
|
25
|
+
end # module Axiom
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
# encoding: utf-8
|
|
2
|
+
|
|
3
|
+
# Extend Date with methods available in ruby 1.9
|
|
4
|
+
class Date
|
|
5
|
+
|
|
6
|
+
ISO_8601_FORMAT = '%F'.freeze
|
|
7
|
+
|
|
8
|
+
# Return the Date in ISO8601 date format
|
|
9
|
+
#
|
|
10
|
+
# @return [#to_s]
|
|
11
|
+
#
|
|
12
|
+
# @todo Remove once backports adds this method
|
|
13
|
+
#
|
|
14
|
+
# @api private
|
|
15
|
+
def iso8601
|
|
16
|
+
date = frozen? ? dup : self
|
|
17
|
+
date.strftime(ISO_8601_FORMAT)
|
|
18
|
+
end
|
|
19
|
+
|
|
20
|
+
end # class Date
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
# encoding: utf-8
|
|
2
|
+
|
|
3
|
+
# Extend DateTime with methods available in ruby 1.9
|
|
4
|
+
class DateTime
|
|
5
|
+
|
|
6
|
+
# TODO: remove the rbx guard when fractional seconds are handled properly in 1.9 mode
|
|
7
|
+
SEC_FRACTION_MULTIPLIER = RUBY_VERSION < '1.9' ? 60 * 60 * 24 : 1
|
|
8
|
+
|
|
9
|
+
# Return the DateTime in ISO8601 date-time format
|
|
10
|
+
#
|
|
11
|
+
# @param [Integer] time_scale
|
|
12
|
+
# the number of significant digits to use for fractional seconds
|
|
13
|
+
#
|
|
14
|
+
# @return [#to_s]
|
|
15
|
+
#
|
|
16
|
+
# @todo Remove once backports adds this method
|
|
17
|
+
#
|
|
18
|
+
# @api private
|
|
19
|
+
def iso8601(time_scale = 0)
|
|
20
|
+
super() + iso8601_timediv(time_scale)
|
|
21
|
+
end
|
|
22
|
+
|
|
23
|
+
private
|
|
24
|
+
|
|
25
|
+
# Return the time with fraction seconds
|
|
26
|
+
#
|
|
27
|
+
# @param [Integer] time_scale
|
|
28
|
+
# the number of significant digits to use for fractional seconds
|
|
29
|
+
#
|
|
30
|
+
# @return [#to_s]
|
|
31
|
+
#
|
|
32
|
+
# @api private
|
|
33
|
+
def iso8601_timediv(time_scale)
|
|
34
|
+
date_time = frozen? ? dup : self
|
|
35
|
+
|
|
36
|
+
fractional_seconds = unless time_scale.zero?
|
|
37
|
+
'.%0*d' % [
|
|
38
|
+
time_scale,
|
|
39
|
+
date_time.sec_fraction * SEC_FRACTION_MULTIPLIER * 10**time_scale
|
|
40
|
+
]
|
|
41
|
+
end
|
|
42
|
+
|
|
43
|
+
date_time.strftime("T%T#{fractional_seconds}%Z")
|
|
44
|
+
end
|
|
45
|
+
|
|
46
|
+
end # class DateTime
|
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
# encoding: utf-8
|
|
2
|
+
|
|
3
|
+
module Axiom
|
|
4
|
+
module SQL
|
|
5
|
+
module Generator
|
|
6
|
+
|
|
7
|
+
# Generates an SQL statement for a direction
|
|
8
|
+
module Direction
|
|
9
|
+
include Attribute
|
|
10
|
+
|
|
11
|
+
DESC = ' DESC'.freeze
|
|
12
|
+
|
|
13
|
+
# Visit an Ascending Direction
|
|
14
|
+
#
|
|
15
|
+
# @param [Relation::Operation::Order::Ascending] direction
|
|
16
|
+
#
|
|
17
|
+
# @return [#to_s]
|
|
18
|
+
#
|
|
19
|
+
# @api private
|
|
20
|
+
def visit_axiom_relation_operation_order_ascending(direction)
|
|
21
|
+
dispatch direction.attribute
|
|
22
|
+
end
|
|
23
|
+
|
|
24
|
+
# Visit an Descending Direction
|
|
25
|
+
#
|
|
26
|
+
# @param [Relation::Operation::Order::Descending] direction
|
|
27
|
+
#
|
|
28
|
+
# @return [#to_s]
|
|
29
|
+
#
|
|
30
|
+
# @api private
|
|
31
|
+
def visit_axiom_relation_operation_order_descending(direction)
|
|
32
|
+
dispatch(direction.attribute) << DESC
|
|
33
|
+
end
|
|
34
|
+
|
|
35
|
+
end # module Direction
|
|
36
|
+
end # module Generator
|
|
37
|
+
end # module SQL
|
|
38
|
+
end # module Axiom
|
|
@@ -0,0 +1,55 @@
|
|
|
1
|
+
# encoding: utf-8
|
|
2
|
+
|
|
3
|
+
module Axiom
|
|
4
|
+
module SQL
|
|
5
|
+
module Generator
|
|
6
|
+
|
|
7
|
+
# Generates an SQL statement for a function expression
|
|
8
|
+
module Function
|
|
9
|
+
include Attribute, Literal
|
|
10
|
+
|
|
11
|
+
private
|
|
12
|
+
|
|
13
|
+
# Return the SQL for a umary prefix operation
|
|
14
|
+
#
|
|
15
|
+
# @param [#to_s] operator
|
|
16
|
+
#
|
|
17
|
+
# @param [Function::Unary] function
|
|
18
|
+
#
|
|
19
|
+
# @return [#to_s]
|
|
20
|
+
#
|
|
21
|
+
# @api private
|
|
22
|
+
def unary_prefix_operation_sql(operator, function)
|
|
23
|
+
"#{operator} (#{dispatch(function.operand)})"
|
|
24
|
+
end
|
|
25
|
+
|
|
26
|
+
# Return the SQL for a binary prefix operation
|
|
27
|
+
#
|
|
28
|
+
# @param [#to_s] operator
|
|
29
|
+
#
|
|
30
|
+
# @param [Function::Binary] function
|
|
31
|
+
#
|
|
32
|
+
# @return [#to_s]
|
|
33
|
+
#
|
|
34
|
+
# @api private
|
|
35
|
+
def binary_prefix_operation_sql(operator, function)
|
|
36
|
+
"#{operator} (#{dispatch(function.left)}, #{dispatch(function.right)})"
|
|
37
|
+
end
|
|
38
|
+
|
|
39
|
+
# Return the SQL for a binary infix operation
|
|
40
|
+
#
|
|
41
|
+
# @param [#to_s] operator
|
|
42
|
+
#
|
|
43
|
+
# @param [Function::Binary] function
|
|
44
|
+
#
|
|
45
|
+
# @return [#to_s]
|
|
46
|
+
#
|
|
47
|
+
# @api private
|
|
48
|
+
def binary_infix_operation_sql(operator, function)
|
|
49
|
+
"#{dispatch(function.left)} #{operator} #{dispatch(function.right)}"
|
|
50
|
+
end
|
|
51
|
+
|
|
52
|
+
end # module Function
|
|
53
|
+
end # module Generator
|
|
54
|
+
end # module SQL
|
|
55
|
+
end # module Axiom
|
|
@@ -0,0 +1,134 @@
|
|
|
1
|
+
# encoding: utf-8
|
|
2
|
+
|
|
3
|
+
module Axiom
|
|
4
|
+
module SQL
|
|
5
|
+
module Generator
|
|
6
|
+
module Function
|
|
7
|
+
|
|
8
|
+
# Generates an SQL statement for an aggregate function
|
|
9
|
+
module Aggregate
|
|
10
|
+
include Function
|
|
11
|
+
|
|
12
|
+
COUNT = 'COUNT'.freeze
|
|
13
|
+
SUM = 'SUM'.freeze
|
|
14
|
+
MINIMUM = 'MIN'.freeze
|
|
15
|
+
MAXIMUM = 'MAX'.freeze
|
|
16
|
+
MEAN = 'AVG'.freeze
|
|
17
|
+
VARIANCE = 'VAR_POP'.freeze
|
|
18
|
+
STANDARD_DEVIATION = 'STDDEV_POP'.freeze
|
|
19
|
+
|
|
20
|
+
# Visit a count aggregate function
|
|
21
|
+
#
|
|
22
|
+
# @param [Axiom::Aggregate::Count] count
|
|
23
|
+
#
|
|
24
|
+
# @return [#to_s]
|
|
25
|
+
#
|
|
26
|
+
# @api private
|
|
27
|
+
def visit_axiom_aggregate_count(count)
|
|
28
|
+
unary_prefix_operation_sql(COUNT, count)
|
|
29
|
+
end
|
|
30
|
+
|
|
31
|
+
# Visit a sum aggregate function
|
|
32
|
+
#
|
|
33
|
+
# @param [Axiom::Aggregate::Sum] sum
|
|
34
|
+
#
|
|
35
|
+
# @return [#to_s]
|
|
36
|
+
#
|
|
37
|
+
# @api private
|
|
38
|
+
def visit_axiom_aggregate_sum(sum)
|
|
39
|
+
aggregate_function_sql(SUM, sum)
|
|
40
|
+
end
|
|
41
|
+
|
|
42
|
+
# Visit a minimum aggregate function
|
|
43
|
+
#
|
|
44
|
+
# @param [Axiom::Aggregate::Minimum] minimum
|
|
45
|
+
#
|
|
46
|
+
# @return [#to_s]
|
|
47
|
+
#
|
|
48
|
+
# @api private
|
|
49
|
+
def visit_axiom_aggregate_minimum(minimum)
|
|
50
|
+
# TODO: wrap this in a coalesce operation once the default can be made sane
|
|
51
|
+
unary_prefix_operation_sql(MINIMUM, minimum)
|
|
52
|
+
end
|
|
53
|
+
|
|
54
|
+
# Visit a maximum aggregate function
|
|
55
|
+
#
|
|
56
|
+
# @param [Axiom::Aggregate::Maximum] maximum
|
|
57
|
+
#
|
|
58
|
+
# @return [#to_s]
|
|
59
|
+
#
|
|
60
|
+
# @api private
|
|
61
|
+
def visit_axiom_aggregate_maximum(maximum)
|
|
62
|
+
# TODO: wrap this in a coalesce operation once the default can be made sane
|
|
63
|
+
unary_prefix_operation_sql(MAXIMUM, maximum)
|
|
64
|
+
end
|
|
65
|
+
|
|
66
|
+
# Visit a mean aggregate function
|
|
67
|
+
#
|
|
68
|
+
# @param [Axiom::Aggregate::Mean] mean
|
|
69
|
+
#
|
|
70
|
+
# @return [#to_s]
|
|
71
|
+
#
|
|
72
|
+
# @api private
|
|
73
|
+
def visit_axiom_aggregate_mean(mean)
|
|
74
|
+
unary_prefix_operation_sql(MEAN, mean)
|
|
75
|
+
end
|
|
76
|
+
|
|
77
|
+
# Visit a variance aggregate function
|
|
78
|
+
#
|
|
79
|
+
# @param [Axiom::Aggregate::Variance] variance
|
|
80
|
+
#
|
|
81
|
+
# @return [#to_s]
|
|
82
|
+
#
|
|
83
|
+
# @api private
|
|
84
|
+
def visit_axiom_aggregate_variance(variance)
|
|
85
|
+
unary_prefix_operation_sql(VARIANCE, variance)
|
|
86
|
+
end
|
|
87
|
+
|
|
88
|
+
# Visit a standard deviation aggregate function
|
|
89
|
+
#
|
|
90
|
+
# @param [Axiom::Aggregate::StandardDeviation] standard_deviation
|
|
91
|
+
#
|
|
92
|
+
# @return [#to_s]
|
|
93
|
+
#
|
|
94
|
+
# @api private
|
|
95
|
+
def visit_axiom_aggregate_standard_deviation(standard_deviation)
|
|
96
|
+
unary_prefix_operation_sql(STANDARD_DEVIATION, standard_deviation)
|
|
97
|
+
end
|
|
98
|
+
|
|
99
|
+
private
|
|
100
|
+
|
|
101
|
+
# Return the SQL
|
|
102
|
+
#
|
|
103
|
+
# @param [#to_s] operation
|
|
104
|
+
#
|
|
105
|
+
# @param [Axiom::Aggregate] aggregate
|
|
106
|
+
#
|
|
107
|
+
# @return [#to_s]
|
|
108
|
+
#
|
|
109
|
+
# @api private
|
|
110
|
+
def aggregate_function_sql(operation, aggregate)
|
|
111
|
+
default_when_null(
|
|
112
|
+
unary_prefix_operation_sql(operation, aggregate),
|
|
113
|
+
aggregate.finalize(aggregate.default)
|
|
114
|
+
)
|
|
115
|
+
end
|
|
116
|
+
|
|
117
|
+
# Specify a default value when SQL expression evaluates to NULL
|
|
118
|
+
#
|
|
119
|
+
# @param [#to_s] sql
|
|
120
|
+
#
|
|
121
|
+
# @param [Visitable] default
|
|
122
|
+
#
|
|
123
|
+
# @return [#to_s]
|
|
124
|
+
#
|
|
125
|
+
# @api private
|
|
126
|
+
def default_when_null(sql, default)
|
|
127
|
+
"COALESCE (#{sql}, #{dispatch(default)})"
|
|
128
|
+
end
|
|
129
|
+
|
|
130
|
+
end # module Aggregate
|
|
131
|
+
end # module Function
|
|
132
|
+
end # module Generator
|
|
133
|
+
end # module SQL
|
|
134
|
+
end # module Axiom
|
|
@@ -0,0 +1,53 @@
|
|
|
1
|
+
# encoding: utf-8
|
|
2
|
+
|
|
3
|
+
module Axiom
|
|
4
|
+
module SQL
|
|
5
|
+
module Generator
|
|
6
|
+
module Function
|
|
7
|
+
|
|
8
|
+
# Generates an SQL statement for a connective
|
|
9
|
+
module Connective
|
|
10
|
+
include Function
|
|
11
|
+
|
|
12
|
+
AND = 'AND'.freeze
|
|
13
|
+
OR = 'OR'.freeze
|
|
14
|
+
NOT = 'NOT'.freeze
|
|
15
|
+
|
|
16
|
+
# Visit an Conjunction connective
|
|
17
|
+
#
|
|
18
|
+
# @param [Function::Connective::Conjunction] conjunction
|
|
19
|
+
#
|
|
20
|
+
# @return [#to_s]
|
|
21
|
+
#
|
|
22
|
+
# @api private
|
|
23
|
+
def visit_axiom_function_connective_conjunction(conjunction)
|
|
24
|
+
Generator.parenthesize!(binary_infix_operation_sql(AND, conjunction))
|
|
25
|
+
end
|
|
26
|
+
|
|
27
|
+
# Visit an Disjunction connective
|
|
28
|
+
#
|
|
29
|
+
# @param [Function::Connective::Disjunction] disjunction
|
|
30
|
+
#
|
|
31
|
+
# @return [#to_s]
|
|
32
|
+
#
|
|
33
|
+
# @api private
|
|
34
|
+
def visit_axiom_function_connective_disjunction(disjunction)
|
|
35
|
+
Generator.parenthesize!(binary_infix_operation_sql(OR, disjunction))
|
|
36
|
+
end
|
|
37
|
+
|
|
38
|
+
# Visit an Negation connective
|
|
39
|
+
#
|
|
40
|
+
# @param [Function::Connective::Negation] negation
|
|
41
|
+
#
|
|
42
|
+
# @return [#to_s]
|
|
43
|
+
#
|
|
44
|
+
# @api private
|
|
45
|
+
def visit_axiom_function_connective_negation(negation)
|
|
46
|
+
unary_prefix_operation_sql(NOT, negation)
|
|
47
|
+
end
|
|
48
|
+
|
|
49
|
+
end # module Connective
|
|
50
|
+
end # module Function
|
|
51
|
+
end # module Generator
|
|
52
|
+
end # module SQL
|
|
53
|
+
end # module Axiom
|