diff options
Diffstat (limited to 'lib')
-rw-r--r-- | lib/arel/visitors/depth_first.rb | 17 | ||||
-rw-r--r-- | lib/arel/visitors/dot.rb | 3 | ||||
-rw-r--r-- | lib/arel/visitors/reduce.rb | 25 | ||||
-rw-r--r-- | lib/arel/visitors/to_sql.rb | 3 | ||||
-rw-r--r-- | lib/arel/visitors/visitor.rb | 8 |
5 files changed, 36 insertions, 20 deletions
diff --git a/lib/arel/visitors/depth_first.rb b/lib/arel/visitors/depth_first.rb index 458934f854..4d2ecfa5e1 100644 --- a/lib/arel/visitors/depth_first.rb +++ b/lib/arel/visitors/depth_first.rb @@ -5,22 +5,11 @@ module Arel @block = block || Proc.new end - def accept object - visit object - end - private - def visit object - send dispatch[object.class], object - rescue NoMethodError => e - raise e if respond_to?(dispatch[object.class], true) - superklass = object.class.ancestors.find { |klass| - respond_to?(dispatch[klass], true) - } - raise(TypeError, "Cannot visit #{object.class}") unless superklass - dispatch[object.class] = dispatch[superklass] - retry + def visit o + super + @block.call o end def unary o diff --git a/lib/arel/visitors/dot.rb b/lib/arel/visitors/dot.rb index 99f4c467d2..ba35223ac9 100644 --- a/lib/arel/visitors/dot.rb +++ b/lib/arel/visitors/dot.rb @@ -23,11 +23,12 @@ module Arel end def accept object - super + visit object to_dot end private + def visit_Arel_Nodes_Ordering o visit_edge o, "expr" end diff --git a/lib/arel/visitors/reduce.rb b/lib/arel/visitors/reduce.rb new file mode 100644 index 0000000000..9670cad27c --- /dev/null +++ b/lib/arel/visitors/reduce.rb @@ -0,0 +1,25 @@ +require 'arel/visitors/visitor' + +module Arel + module Visitors + class Reduce < Arel::Visitors::Visitor + def accept object, collector + visit object, collector + end + + private + + def visit object, collector + send dispatch[object.class], object, collector + rescue NoMethodError => e + raise e if respond_to?(dispatch[object.class], true) + superklass = object.class.ancestors.find { |klass| + respond_to?(dispatch[klass], true) + } + raise(TypeError, "Cannot visit #{object.class}") unless superklass + dispatch[object.class] = dispatch[superklass] + retry + end + end + end +end diff --git a/lib/arel/visitors/to_sql.rb b/lib/arel/visitors/to_sql.rb index f8b8a9a07c..0dbec61212 100644 --- a/lib/arel/visitors/to_sql.rb +++ b/lib/arel/visitors/to_sql.rb @@ -1,9 +1,10 @@ require 'bigdecimal' require 'date' +require 'arel/visitors/reduce' module Arel module Visitors - class ToSql < Arel::Visitors::Visitor + class ToSql < Arel::Visitors::Reduce ## # This is some roflscale crazy stuff. I'm roflscaling this because # building SQL queries is a hotspot. I will explain the roflscale so that diff --git a/lib/arel/visitors/visitor.rb b/lib/arel/visitors/visitor.rb index 2d4b472ea3..0730c15794 100644 --- a/lib/arel/visitors/visitor.rb +++ b/lib/arel/visitors/visitor.rb @@ -1,8 +1,8 @@ module Arel module Visitors class Visitor - def accept object, collector - visit object, collector + def accept object + visit object end private @@ -18,8 +18,8 @@ module Arel DISPATCH[self.class] end - def visit object, collector - send dispatch[object.class], object, collector + def visit object + send dispatch[object.class], object rescue NoMethodError => e raise e if respond_to?(dispatch[object.class], true) superklass = object.class.ancestors.find { |klass| |