@@ -24,27 +24,27 @@ def visit_Arel_Nodes_UpdateStatement(o, a)
2424 end
2525
2626 def visit_Arel_Nodes_Offset ( o , a )
27- "WHERE [__rnt].[__rn] > (#{ visit o . expr } )"
27+ "WHERE [__rnt].[__rn] > (#{ visit o . expr , a } )"
2828 end
2929
3030 def visit_Arel_Nodes_Limit ( o , a )
31- "TOP (#{ visit o . expr } )"
31+ "TOP (#{ visit o . expr , a } )"
3232 end
3333
3434 def visit_Arel_Nodes_Lock ( o , a )
35- visit o . expr
35+ visit o . expr , a
3636 end
3737
3838 def visit_Arel_Nodes_Ordering ( o , a )
3939 if o . respond_to? ( :direction )
40- "#{ visit o . expr } #{ o . ascending? ? 'ASC' : 'DESC' } "
40+ "#{ visit o . expr , a } #{ o . ascending? ? 'ASC' : 'DESC' } "
4141 else
42- visit o . expr
42+ visit o . expr , a
4343 end
4444 end
4545
4646 def visit_Arel_Nodes_Bin ( o , a )
47- "#{ visit o . expr } #{ @connection . cs_equality_operator } "
47+ "#{ visit o . expr , a } #{ @connection . cs_equality_operator } "
4848 end
4949
5050 # SQLServer ToSql/Visitor (Additions)
@@ -56,28 +56,28 @@ def visit_Arel_Nodes_SelectStatementWithOutOffset(o, a, windowed = false)
5656 groups = core . groups
5757 orders = o . orders . uniq
5858 if windowed
59- projections = function_select_statement? ( o ) ? projections : projections . map { |x | projection_without_expression ( x ) }
60- groups = projections . map { |x | projection_without_expression ( x ) } if windowed_single_distinct_select_statement? ( o ) && groups . empty?
59+ projections = function_select_statement? ( o ) ? projections : projections . map { |x | projection_without_expression ( x , a ) }
60+ groups = projections . map { |x | projection_without_expression ( x , a ) } if windowed_single_distinct_select_statement? ( o ) && groups . empty?
6161 groups += orders . map { |x | Arel . sql ( x . expr ) } if windowed_single_distinct_select_statement? ( o )
62- elsif eager_limiting_select_statement? ( o )
63- projections = projections . map { |x | projection_without_expression ( x ) }
64- groups = projections . map { |x | projection_without_expression ( x ) }
62+ elsif eager_limiting_select_statement? ( o , a )
63+ projections = projections . map { |x | projection_without_expression ( x , a ) }
64+ groups = projections . map { |x | projection_without_expression ( x , a ) }
6565 orders = orders . map do |x |
66- expr = Arel . sql projection_without_expression ( x . expr )
66+ expr = Arel . sql projection_without_expression ( x . expr , a )
6767 x . descending? ? Arel ::Nodes ::Max . new ( [ expr ] ) : Arel ::Nodes ::Min . new ( [ expr ] )
6868 end
69- elsif top_one_everything_for_through_join? ( o )
70- projections = projections . map { |x | projection_without_expression ( x ) }
69+ elsif top_one_everything_for_through_join? ( o , a )
70+ projections = projections . map { |x | projection_without_expression ( x , a ) }
7171 end
7272 [ ( "SELECT" if !windowed ) ,
73- ( visit ( core . set_quantifier ) if core . set_quantifier && !windowed ) ,
74- ( visit ( o . limit ) if o . limit && !windowed ) ,
75- ( projections . map { |x | v = visit ( x ) ; v == "1" ? "1 AS [__wrp]" : v } . join ( ', ' ) ) ,
76- ( source_with_lock_for_select_statement ( o ) ) ,
77- ( "WHERE #{ core . wheres . map { |x | visit ( x ) } . join ' AND ' } " unless core . wheres . empty? ) ,
78- ( "GROUP BY #{ groups . map { |x | visit x } . join ', ' } " unless groups . empty? ) ,
79- ( visit ( core . having ) if core . having ) ,
80- ( "ORDER BY #{ orders . map { |x | visit ( x ) } . join ( ', ' ) } " if !orders . empty? && !windowed )
73+ ( visit ( core . set_quantifier , a ) if core . set_quantifier && !windowed ) ,
74+ ( visit ( o . limit , a ) if o . limit && !windowed ) ,
75+ ( projections . map { |x | v = visit ( x , a ) ; v == "1" ? "1 AS [__wrp]" : v } . join ( ', ' ) ) ,
76+ ( source_with_lock_for_select_statement ( o , a ) ) ,
77+ ( "WHERE #{ core . wheres . map { |x | visit ( x , a ) } . join ' AND ' } " unless core . wheres . empty? ) ,
78+ ( "GROUP BY #{ groups . map { |x | visit ( x , a ) } . join ', ' } " unless groups . empty? ) ,
79+ ( visit ( core . having , a ) if core . having ) ,
80+ ( "ORDER BY #{ orders . map { |x | visit ( x , a ) } . join ( ', ' ) } " if !orders . empty? && !windowed )
8181 ] . compact . join ' '
8282 end
8383
@@ -86,13 +86,13 @@ def visit_Arel_Nodes_SelectStatementWithOffset(o, a)
8686 o . limit ||= Arel ::Nodes ::Limit . new ( 9223372036854775807 )
8787 orders = rowtable_orders ( o )
8888 [ "SELECT" ,
89- ( visit ( o . limit ) if o . limit && !windowed_single_distinct_select_statement? ( o ) ) ,
90- ( rowtable_projections ( o ) . map { |x | visit ( x ) } . join ( ', ' ) ) ,
89+ ( visit ( o . limit , a ) if o . limit && !windowed_single_distinct_select_statement? ( o ) ) ,
90+ ( rowtable_projections ( o , a ) . map { |x | visit ( x , a ) } . join ( ', ' ) ) ,
9191 "FROM (" ,
92- "SELECT #{ core . set_quantifier ? 'DISTINCT DENSE_RANK()' : 'ROW_NUMBER()' } OVER (ORDER BY #{ orders . map { |x | visit ( x ) } . join ( ', ' ) } ) AS [__rn]," ,
92+ "SELECT #{ core . set_quantifier ? 'DISTINCT DENSE_RANK()' : 'ROW_NUMBER()' } OVER (ORDER BY #{ orders . map { |x | visit ( x , a ) } . join ( ', ' ) } ) AS [__rn]," ,
9393 visit_Arel_Nodes_SelectStatementWithOutOffset ( o , a , true ) ,
9494 ") AS [__rnt]" ,
95- ( visit ( o . offset ) if o . offset ) ,
95+ ( visit ( o . offset , a ) if o . offset ) ,
9696 "ORDER BY [__rnt].[__rn] ASC"
9797 ] . compact . join ' '
9898 end
@@ -104,27 +104,27 @@ def visit_Arel_Nodes_SelectStatementForComplexCount(o, a)
104104 [ "SELECT COUNT([count]) AS [count_id]" ,
105105 "FROM (" ,
106106 "SELECT" ,
107- ( visit ( o . limit ) if o . limit ) ,
108- "ROW_NUMBER() OVER (ORDER BY #{ orders . map { |x | visit ( x ) } . join ( ', ' ) } ) AS [__rn]," ,
107+ ( visit ( o . limit , a ) if o . limit ) ,
108+ "ROW_NUMBER() OVER (ORDER BY #{ orders . map { |x | visit ( x , a ) } . join ( ', ' ) } ) AS [__rn]," ,
109109 "1 AS [count]" ,
110- ( source_with_lock_for_select_statement ( o ) ) ,
111- ( "WHERE #{ core . wheres . map { |x | visit ( x ) } . join ' AND ' } " unless core . wheres . empty? ) ,
112- ( "GROUP BY #{ core . groups . map { |x | visit x } . join ', ' } " unless core . groups . empty? ) ,
113- ( visit ( core . having ) if core . having ) ,
114- ( "ORDER BY #{ o . orders . map { |x | visit ( x ) } . join ( ', ' ) } " if !o . orders . empty? ) ,
110+ ( source_with_lock_for_select_statement ( o , a ) ) ,
111+ ( "WHERE #{ core . wheres . map { |x | visit ( x , a ) } . join ' AND ' } " unless core . wheres . empty? ) ,
112+ ( "GROUP BY #{ core . groups . map { |x | visit ( x , a ) } . join ', ' } " unless core . groups . empty? ) ,
113+ ( visit ( core . having , a ) if core . having ) ,
114+ ( "ORDER BY #{ o . orders . map { |x | visit ( x , a ) } . join ( ', ' ) } " if !o . orders . empty? ) ,
115115 ") AS [__rnt]" ,
116- ( visit ( o . offset ) if o . offset )
116+ ( visit ( o . offset , a ) if o . offset )
117117 ] . compact . join ' '
118118 end
119119
120120
121121 # SQLServer Helpers
122122
123- def source_with_lock_for_select_statement ( o )
123+ def source_with_lock_for_select_statement ( o , a )
124124 core = o . cores . first
125- source = "FROM #{ visit ( core . source ) . strip } " if core . source
125+ source = "FROM #{ visit ( core . source , a ) . strip } " if core . source
126126 if source && o . lock
127- lock = visit o . lock
127+ lock = visit o . lock , a
128128 index = source . match ( /FROM [\w \[ \] \. ]+/ ) [ 0 ] . mb_chars . length
129129 source . insert index , " #{ lock } "
130130 else
@@ -164,23 +164,27 @@ def single_distinct_select_statement?(o)
164164 end
165165
166166 def windowed_single_distinct_select_statement? ( o )
167- o . limit && o . offset && single_distinct_select_statement? ( o )
167+
168+ o . limit &&
169+ o . offset &&
170+ single_distinct_select_statement? ( o )
168171 end
169172
170- def single_distinct_select_everything_statement? ( o )
171- single_distinct_select_statement? ( o ) && visit ( o . cores . first . projections . first ) . ends_with? ( ".*" )
173+ def single_distinct_select_everything_statement? ( o , a )
174+ single_distinct_select_statement? ( o ) &&
175+ visit ( o . cores . first . projections . first , a ) . ends_with? ( ".*" )
172176 end
173177
174- def top_one_everything_for_through_join? ( o )
175- single_distinct_select_everything_statement? ( o ) &&
178+ def top_one_everything_for_through_join? ( o , a )
179+ single_distinct_select_everything_statement? ( o , a ) &&
176180 ( o . limit && !o . offset ) &&
177181 join_in_select_statement? ( o )
178182 end
179183
180- def all_projections_aliased_in_select_statement? ( o )
184+ def all_projections_aliased_in_select_statement? ( o , a )
181185 projections = o . cores . first . projections
182186 projections . all? do |x |
183- visit ( x ) . split ( ',' ) . all? { |y | y . include? ( ' AS ' ) }
187+ visit ( x , a ) . split ( ',' ) . all? { |y | y . include? ( ' AS ' ) }
184188 end
185189 end
186190
@@ -189,12 +193,12 @@ def function_select_statement?(o)
189193 core . projections . any? { |x | Arel ::Nodes ::Function === x }
190194 end
191195
192- def eager_limiting_select_statement? ( o )
196+ def eager_limiting_select_statement? ( o , a )
193197 core = o . cores . first
194198 single_distinct_select_statement? ( o ) &&
195199 ( o . limit && !o . offset ) &&
196200 core . groups . empty? &&
197- !single_distinct_select_everything_statement? ( o )
201+ !single_distinct_select_everything_statement? ( o , a )
198202 end
199203
200204 def join_in_select_statement? ( o )
@@ -243,14 +247,15 @@ def find_and_fix_uncorrelated_joins_in_select_statement(o)
243247 j2 . sub! "[#{ j2_tn } ]." , "[#{ j2_tn } _crltd]."
244248 end
245249
246- def rowtable_projections ( o )
250+ def rowtable_projections ( o , a )
247251 core = o . cores . first
252+ puts "windowed_single_distinct_select_statement?(o)#{ windowed_single_distinct_select_statement? ( o ) } core.groups.blank?:#{ core . groups . blank? } "
248253 if windowed_single_distinct_select_statement? ( o ) && core . groups . blank?
249254 tn = table_from_select_statement ( o ) . name
250255 core . projections . map do |x |
251256 x . dup . tap do |p |
252257 p . sub! 'DISTINCT' , ''
253- p . insert 0 , visit ( o . limit ) if o . limit
258+ p . insert 0 , visit ( o . limit , a ) if o . limit
254259 p . gsub! /\[ ?#{ tn } \] ?\. / , '[__rnt].'
255260 p . strip!
256261 end
@@ -259,14 +264,14 @@ def rowtable_projections(o)
259264 tn = table_from_select_statement ( o ) . name
260265 core . projections . map do |x |
261266 x . dup . tap do |p |
262- p . sub! 'DISTINCT' , "DISTINCT #{ visit ( o . limit ) } " . strip if o . limit
267+ p . sub! 'DISTINCT' , "DISTINCT #{ visit ( o . limit , a ) } " . strip if o . limit
263268 p . gsub! /\[ ?#{ tn } \] ?\. / , '[__rnt].'
264269 p . strip!
265270 end
266271 end
267- elsif join_in_select_statement? ( o ) && all_projections_aliased_in_select_statement? ( o )
272+ elsif join_in_select_statement? ( o ) && all_projections_aliased_in_select_statement? ( o , a )
268273 core . projections . map do |x |
269- Arel . sql visit ( x ) . split ( ',' ) . map { |y | y . split ( ' AS ' ) . last . strip } . join ( ', ' )
274+ Arel . sql visit ( x , a ) . split ( ',' ) . map { |y | y . split ( ' AS ' ) . last . strip } . join ( ', ' )
270275 end
271276 elsif select_primary_key_sql? ( o )
272277 [ Arel . sql ( "[__rnt].#{ quote_column_name ( core . projections . first . name ) } " ) ]
@@ -287,8 +292,8 @@ def rowtable_orders(o)
287292 end
288293
289294 # TODO: We use this for grouping too, maybe make Grouping objects vs SqlLiteral.
290- def projection_without_expression ( projection )
291- Arel . sql ( visit ( projection ) . split ( ',' ) . map do |x |
295+ def projection_without_expression ( projection , a )
296+ Arel . sql ( visit ( projection , a ) . split ( ',' ) . map do |x |
292297 x . strip!
293298 x . sub! ( /^(COUNT|SUM|MAX|MIN|AVG)\s *(\( (.*)\) )?/ , '\3' )
294299 x . sub! ( /^DISTINCT\s */ , '' )
0 commit comments