DeveelDB  20151217
complete SQL database system, primarly developed for .NET/Mono frameworks
SqlExpressionVisitor.cs
Go to the documentation of this file.
1 //
2 // Copyright 2010-2015 Deveel
3 //
4 // Licensed under the Apache License, Version 2.0 (the "License");
5 // you may not use this file except in compliance with the License.
6 // You may obtain a copy of the License at
7 //
8 // http://www.apache.org/licenses/LICENSE-2.0
9 //
10 // Unless required by applicable law or agreed to in writing, software
11 // distributed under the License is distributed on an "AS IS" BASIS,
12 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 // See the License for the specific language governing permissions and
14 // limitations under the License.
15 //
16 
17 using System;
18 using System.Collections.Generic;
19 using System.Linq;
20 
21 namespace Deveel.Data.Sql.Expressions {
25  public class SqlExpressionVisitor {
33  public virtual SqlExpression Visit(SqlExpression expression) {
34  if (expression == null)
35  return null;
36 
37  var expressionType = expression.ExpressionType;
38  switch (expressionType) {
39  case SqlExpressionType.Add:
40  case SqlExpressionType.Subtract:
41  case SqlExpressionType.Divide:
42  case SqlExpressionType.Multiply:
43  case SqlExpressionType.Modulo:
44  case SqlExpressionType.And:
45  case SqlExpressionType.Or:
46  case SqlExpressionType.XOr:
47  case SqlExpressionType.Equal:
48  case SqlExpressionType.NotEqual:
49  case SqlExpressionType.Like:
50  case SqlExpressionType.NotLike:
51  case SqlExpressionType.GreaterThan:
52  case SqlExpressionType.GreaterOrEqualThan:
53  case SqlExpressionType.SmallerThan:
54  case SqlExpressionType.SmallerOrEqualThan:
55  case SqlExpressionType.Is:
56  case SqlExpressionType.IsNot:
57  case SqlExpressionType.AllEqual:
58  case SqlExpressionType.AllNotEqual:
59  case SqlExpressionType.AllGreaterThan:
60  case SqlExpressionType.AllSmallerThan:
61  case SqlExpressionType.AllGreaterOrEqualThan:
62  case SqlExpressionType.AllSmallerOrEqualThan:
63  case SqlExpressionType.AnyEqual:
64  case SqlExpressionType.AnyNotEqual:
65  case SqlExpressionType.AnyGreaterThan:
66  case SqlExpressionType.AnySmallerThan:
67  case SqlExpressionType.AnyGreaterOrEqualThan:
68  case SqlExpressionType.AnySmallerOrEqualThan:
69  return VisitBinary((SqlBinaryExpression) expression);
70  case SqlExpressionType.Negate:
71  case SqlExpressionType.Not:
72  case SqlExpressionType.UnaryPlus:
73  return VisitUnary((SqlUnaryExpression) expression);
74  case SqlExpressionType.Cast:
75  return VisitCast((SqlCastExpression) expression);
76  case SqlExpressionType.Reference:
77  return VisitReference((SqlReferenceExpression) expression);
78  case SqlExpressionType.VariableReference:
79  return VisitVariableReference((SqlVariableReferenceExpression) expression);
80  case SqlExpressionType.Assign:
81  return VisitAssign((SqlAssignExpression) expression);
82  case SqlExpressionType.FunctionCall:
83  return VisitFunctionCall((SqlFunctionCallExpression) expression);
84  case SqlExpressionType.Constant:
85  return VisitConstant((SqlConstantExpression) expression);
86  case SqlExpressionType.Conditional:
87  return VisitConditional((SqlConditionalExpression) expression);
88  case SqlExpressionType.Query:
89  return VisitQuery((SqlQueryExpression) expression);
90  case SqlExpressionType.Tuple:
91  return VisitTuple((SqlTupleExpression) expression);
92  default:
93  return expression.Accept(this);
94  }
95  }
96 
110  if (list == null)
111  return new SqlExpression[0];
112 
113  var result = new SqlExpression[list.Length];
114  for (int i = 0; i < list.Length; i++) {
115  result[i] = Visit(list[i]);
116  }
117 
118  return result;
119  }
120 
127  var ags = VisitExpressionList(expression.Arguments);
128  return SqlExpression.FunctionCall(expression.FunctioName, ags);
129  }
130 
136  public virtual SqlExpression VisitBinary(SqlBinaryExpression binaryEpression) {
137  var left = binaryEpression.Left;
138  var right = binaryEpression.Right;
139  if (left != null)
140  left = Visit(left);
141  if (right != null)
142  right = Visit(right);
143 
144  return SqlExpression.Binary(left, binaryEpression.ExpressionType, right);
145  }
146 
153  var operand = unary.Operand;
154  if (operand != null)
155  operand = Visit(operand);
156 
157  return SqlExpression.Unary(unary.ExpressionType, operand);
158  }
159 
165  public virtual SqlExpression VisitCast(SqlCastExpression castExpression) {
166  // TODO:
167  return castExpression;
168  }
169 
176  return SqlExpression.Reference(reference.ReferenceName);
177  }
178 
180  return SqlExpression.VariableReference(reference.VariableName);
181  }
182 
189  var reference = assign.ReferenceExpression;
190  if (reference != null)
191  reference = Visit(reference);
192 
193  var expression = assign.ValueExpression;
194  if (expression != null)
195  expression = Visit(expression);
196 
197  return SqlExpression.Assign(reference, expression);
198  }
199 
206  return SqlExpression.Constant(constant.Value);
207  }
208 
215  var test = conditional.TestExpression;
216  var ifTrue = conditional.TrueExpression;
217  var ifFalse = conditional.FalseExpression;
218 
219  if (test != null)
220  test = Visit(test);
221  if (ifTrue != null)
222  ifTrue = Visit(ifTrue);
223  if (ifFalse != null)
224  ifFalse = Visit(ifFalse);
225 
226  return SqlExpression.Conditional(test, ifTrue, ifFalse);
227  }
228 
234  public virtual SqlExpression VisitTuple(SqlTupleExpression expression) {
235  var list = expression.Expressions;
236  if (list != null)
237  list = VisitExpressionList(list);
238 
239  return SqlExpression.Tuple(list);
240  }
241 
248  var selectColumns = new List<SelectColumn>();
249  foreach (var column in query.SelectColumns) {
250  var newColumn = new SelectColumn(Visit(column.Expression), column.Alias);
251  newColumn.InternalName = column.InternalName;
252  newColumn.ResolvedName = column.ResolvedName;
253  selectColumns.Add(newColumn);
254  }
255 
256  var newQuery = new SqlQueryExpression(selectColumns);
257 
258  if (query.FromClause != null)
259  newQuery.FromClause = VisitFromClause(query.FromClause);
260 
261  if (query.WhereExpression != null)
262  newQuery.WhereExpression = Visit(query.WhereExpression);
263  if (query.HavingExpression != null)
264  newQuery.HavingExpression = Visit(query.HavingExpression);
265 
266  if (query.GroupBy != null)
267  newQuery.GroupBy = VisitExpressionList(newQuery.GroupBy.ToArray());
268 
269  newQuery.GroupMax = query.GroupMax;
270  newQuery.Distinct = query.Distinct;
271 
272  if (query.NextComposite != null) {
273  var visitedComposite = Visit(query.NextComposite);
274  if (visitedComposite.ExpressionType == SqlExpressionType.Query)
275  newQuery.NextComposite = (SqlQueryExpression) visitedComposite;
276 
277  newQuery.CompositeFunction = query.CompositeFunction;
278  newQuery.IsCompositeAll = query.IsCompositeAll;
279  }
280 
281  return query;
282  }
283 
284  private FromClause VisitFromClause(FromClause fromClause) {
285  // TODO:
286  return fromClause;
287  }
288  }
289 }
ObjectName ReferenceName
Gets the name of the object referenced by the expression.
SqlExpression Operand
Gets the operand expression that is computed.
FromClause VisitFromClause(FromClause fromClause)
An expression that references an object within a context.
Handles expressions computed against an unary operator.
virtual SqlExpression VisitFunctionCall(SqlFunctionCallExpression expression)
Visits the expression that calls the function defined.
virtual SqlExpression VisitUnary(SqlUnaryExpression unary)
static SqlTupleExpression Tuple(SqlExpression[] expressions)
virtual SqlExpression VisitTuple(SqlTupleExpression expression)
An SqlExpression that will cast a value retrieved by the evaluation of another expression into a give...
static SqlVariableReferenceExpression VariableReference(string varName)
static SqlAssignExpression Assign(SqlExpression reference, SqlExpression valueExpression)
static SqlConditionalExpression Conditional(SqlExpression testExpression, SqlExpression ifTrue)
SqlExpressionType
All the possible type of SqlExpression supported
DataObject Value
Gets the constant value of the expression.
virtual SqlExpression[] VisitExpressionList(SqlExpression[] list)
Visits a list of expressions given.
virtual SqlExpression VisitQuery(SqlQueryExpression query)
virtual SqlExpression VisitBinary(SqlBinaryExpression binaryEpression)
A container for the FROM clause of a select statement.
Definition: FromClause.cs:32
virtual SqlExpression VisitCast(SqlCastExpression castExpression)
virtual SqlExpression VisitReference(SqlReferenceExpression reference)
Represents a column selected to be in the output of a select statement.
Definition: SelectColumn.cs:31
virtual SqlExpression VisitConditional(SqlConditionalExpression conditional)
An expression that holds a constant value.
virtual SqlExpression VisitConstant(SqlConstantExpression constant)
static SqlReferenceExpression Reference(ObjectName objectName)
virtual SqlExpression Accept(SqlExpressionVisitor visitor)
static SqlBinaryExpression Binary(SqlExpression left, SqlExpressionType expressionType, SqlExpression right)
Defines the base class for instances that represent SQL expression tree nodes.
static SqlConstantExpression Constant(object value)
static SqlFunctionCallExpression FunctionCall(ObjectName functionName)
abstract SqlExpressionType ExpressionType
Gets the type code of this SQL expression.
virtual SqlExpression VisitVariableReference(SqlVariableReferenceExpression reference)
virtual SqlExpression VisitAssign(SqlAssignExpression assign)
static SqlUnaryExpression Unary(SqlExpressionType expressionType, SqlExpression operand)
virtual SqlExpression Visit(SqlExpression expression)
Visits a given SQL expression.