@@ -105,197 +105,4 @@ def visit_column(expr)
105105 def visit_qualified_column ( expr )
106106 @columns << expr
107107 end
108- end
109-
110- class ExpressionValidatorVisitor < ExpressionVisitor
111- def initialize ( table_context , evaluator )
112- @table_context = table_context
113- @evaluator = evaluator
114- @errors = [ ]
115- end
116-
117- def errors
118- @errors
119- end
120-
121- def valid?
122- @errors . empty?
123- end
124-
125- protected
126-
127- def visit_column ( expr )
128- column_name = expr [ :name ]
129- found = false
130- count = 0
131-
132- table_context_hash = @table_context . is_a? ( Hash ) ? @table_context : @table_context . to_hash
133-
134- table_context_hash [ :aliases ] . each do |alias_name , table_name |
135- table_info = table_context_hash [ :tables ] [ table_name ]
136- if table_info [ :columns ] . any? { |col | col [ :name ] == column_name }
137- found = true
138- count += 1
139- end
140- end
141-
142- unless found
143- @errors << "Unknown column: #{ column_name } "
144- end
145-
146- if count > 1
147- @errors << "Ambiguous column: #{ column_name } "
148- end
149- end
150-
151- def visit_qualified_column ( expr )
152- table_ref = expr [ :table ]
153- column_name = expr [ :column ]
154-
155- table_context_hash = @table_context . is_a? ( Hash ) ? @table_context : @table_context . to_hash
156-
157- actual_table = table_context_hash [ :aliases ] [ table_ref ]
158- unless actual_table
159- @errors << "Unknown table: #{ table_ref } "
160- return
161- end
162-
163- table_info = table_context_hash [ :tables ] [ actual_table ]
164- unless table_info [ :columns ] . any? { |col | col [ :name ] == column_name }
165- @errors << "Unknown column: #{ table_ref } .#{ column_name } "
166- end
167- end
168-
169- def visit_binary_op ( expr )
170- super
171-
172- # Type validation for comparison operators
173- if expr [ :operator ] == :equal || expr [ :operator ] == :not_equal
174- left_type = get_expression_type ( expr [ :left ] )
175- right_type = get_expression_type ( expr [ :right ] )
176-
177- if ( left_type == :integer && right_type == :boolean ) ||
178- ( left_type == :boolean && right_type == :integer )
179- @errors << "Type mismatch in comparison"
180- end
181- end
182- end
183-
184- private
185-
186- def get_expression_type ( expr )
187- # Simplified type inference
188- case expr [ :type ]
189- when :literal
190- if expr [ :value ] . nil?
191- nil
192- elsif expr [ :value ] == true || expr [ :value ] == false
193- :boolean
194- else
195- :integer
196- end
197- when :column , :qualified_column
198- # Would need to look up column type in table context
199- :unknown
200- when :binary_op
201- case expr [ :operator ]
202- when :plus , :minus , :star , :slash
203- :integer
204- when :lt , :gt , :lte , :gte , :equal , :not_equal , :and , :or
205- :boolean
206- end
207- else
208- :unknown
209- end
210- end
211- end
212-
213- class ExpressionTransformVisitor < ExpressionVisitor
214- def visit ( expression )
215- return nil unless expression
216-
217- case expression [ :type ]
218- when :literal
219- transform_literal ( expression )
220- when :column
221- transform_column ( expression )
222- when :qualified_column
223- transform_qualified_column ( expression )
224- when :binary_op
225- transform_binary_op ( expression )
226- when :unary_op
227- transform_unary_op ( expression )
228- when :function
229- transform_function ( expression )
230- when :aggregate_function
231- transform_aggregate_function ( expression )
232- when :is_null
233- transform_is_null ( expression )
234- when :is_not_null
235- transform_is_not_null ( expression )
236- else
237- expression
238- end
239- end
240-
241- protected
242-
243- def transform_literal ( expr )
244- expr
245- end
246-
247- def transform_column ( expr )
248- expr
249- end
250-
251- def transform_qualified_column ( expr )
252- expr
253- end
254-
255- def transform_binary_op ( expr )
256- {
257- type : :binary_op ,
258- operator : expr [ :operator ] ,
259- left : visit ( expr [ :left ] ) ,
260- right : visit ( expr [ :right ] )
261- }
262- end
263-
264- def transform_unary_op ( expr )
265- {
266- type : :unary_op ,
267- operator : expr [ :operator ] ,
268- operand : visit ( expr [ :operand ] )
269- }
270- end
271-
272- def transform_function ( expr )
273- {
274- type : :function ,
275- name : expr [ :name ] ,
276- args : expr [ :args ] &.map { |arg | visit ( arg ) }
277- }
278- end
279-
280- def transform_aggregate_function ( expr )
281- {
282- type : :aggregate_function ,
283- name : expr [ :name ] ,
284- args : expr [ :args ] &.map { |arg | visit ( arg ) }
285- }
286- end
287-
288- def transform_is_null ( expr )
289- {
290- type : :is_null ,
291- operand : visit ( expr [ :operand ] )
292- }
293- end
294-
295- def transform_is_not_null ( expr )
296- {
297- type : :is_not_null ,
298- operand : visit ( expr [ :operand ] )
299- }
300- end
301108end
0 commit comments