1   package org.jdbc4olap.jdbc;
2   
3   import java.util.ArrayList;
4   import java.util.List;
5   
6   import org.jdbc4olap.parsing.ASTCompleteTableColumnName;
7   import org.jdbc4olap.parsing.ASTFromAliasItem;
8   import org.jdbc4olap.parsing.ASTFromItem;
9   import org.jdbc4olap.parsing.ASTSQLRelOpExpr;
10  import org.jdbc4olap.parsing.ASTSQLRelationalExpression;
11  import org.jdbc4olap.parsing.ASTSelectAliasItem;
12  import org.jdbc4olap.parsing.ASTSelectItem;
13  import org.jdbc4olap.parsing.ASTSelectList;
14  import org.jdbc4olap.parsing.ASTSelectStar;
15  import org.jdbc4olap.parsing.ASTTableColumnName;
16  import org.jdbc4olap.parsing.SimpleNode;
17  import org.jdbc4olap.xmla.QueryColumn;
18  import org.jdbc4olap.xmla.QueryFilter;
19  import org.jdbc4olap.xmla.QueryTable;
20  
21  public class QueryParsingHelper {
22  
23      private static final String QUOTE_NAME_CHAR = "\"";
24      private static final String QUOTE_EXPRESSION_CHAR = "'";
25  
26  
27      public List<QueryColumn> extractQueryFields(final SimpleNode node) {
28          final List<QueryColumn> list = new ArrayList<QueryColumn>();
29          if (node instanceof ASTSelectItem) {
30              QueryColumn field = new QueryColumn();
31              final SimpleNode child = (SimpleNode) node.jjtGetChild(0);
32              if (child instanceof ASTSelectStar) {
33                  //tableName.* or tableAlias.*
34                  final SimpleNode tableAlias = (SimpleNode) child.jjtGetChild(0);
35                  field.setField("*");
36                  field.setTableAlias(getUnquotedName(tableAlias.getText()));
37              } else {
38                  final SimpleNode columnName;
39                  if (child instanceof ASTSelectAliasItem) {
40                      //tableAlias.columnName
41                      columnName = (SimpleNode) child.jjtGetChild(0);
42                      field.setFieldAlias(((SimpleNode) child.jjtGetChild(1)).getText());
43                  } else {
44                      //columnName
45                      columnName = child;
46                  }
47                  field = readTableColumn(columnName, field);
48              }
49              list.add(field);
50          } else {
51              if (node instanceof ASTSelectList) {
52                  if ("*".equals(node.getText())) {
53                      final QueryColumn field = new QueryColumn();
54                      field.setField("*");
55                      list.add(field);
56                  } else {
57                      for (int j = 0; j < node.jjtGetNumChildren(); j++) {
58                          final SimpleNode item = (SimpleNode) node.jjtGetChild(j);
59                          list.addAll(extractQueryFields(item));
60                      }
61                  }
62              }
63          }
64          return list;
65      }
66  
67      public List<QueryTable> extractQueryTables(final SimpleNode node) {
68          List<QueryTable> list = new ArrayList<QueryTable>();
69          if (node instanceof ASTFromItem) {
70              SimpleNode child = (SimpleNode) node.jjtGetChild(0);
71              QueryTable qTable = new QueryTable();
72              SimpleNode tableReference;
73              if (child instanceof ASTFromAliasItem) {
74                  tableReference = (SimpleNode) child.jjtGetChild(0);
75                  qTable.setTableAlias(((SimpleNode) child.jjtGetChild(1)).getText());
76              } else {
77                  tableReference = child;
78              }
79              SimpleNode catalog = (SimpleNode) tableReference.jjtGetChild(0);
80              SimpleNode schema = (SimpleNode) tableReference.jjtGetChild(1);
81              SimpleNode table = (SimpleNode) tableReference.jjtGetChild(2);
82              qTable.setCatalog(getUnquotedName(((SimpleNode) catalog.jjtGetChild(0)).getText()));
83              qTable.setSchema(getUnquotedName(((SimpleNode) schema.jjtGetChild(0)).getText()));
84              qTable.setTable(getUnquotedName(((SimpleNode) table.jjtGetChild(0)).getText()));
85              list.add(qTable);
86          } else {
87              for (int j = 0; j < node.jjtGetNumChildren(); j++) {
88                  SimpleNode item = (SimpleNode) node.jjtGetChild(j);
89                  list.addAll(extractQueryTables(item));
90              }
91          }
92          return list;
93      }
94  
95      public List<QueryFilter> extractQueryFilters(final SimpleNode node) {
96          List<QueryFilter> list = new ArrayList<QueryFilter>();
97          if (node instanceof ASTSQLRelationalExpression) {
98              SimpleNode child = (SimpleNode) node.jjtGetChild(0);
99              QueryFilter qFilter = new QueryFilter();
100             SimpleNode simpleExpr = (SimpleNode) child.jjtGetChild(0);
101             if (simpleExpr.jjtGetNumChildren() > 0) {
102                 QueryColumn field = new QueryColumn();
103                 field = readTableColumn((SimpleNode) simpleExpr.jjtGetChild(0), field);
104                 qFilter.setLeftOp(field);
105             } else {
106                 List<String> valList = new ArrayList<String>();
107                 valList.add(getUnquotedExpression(simpleExpr.getText()));
108                 qFilter.setLeftOp(valList);
109             }
110             if (child instanceof ASTSQLRelOpExpr) {
111                 SimpleNode relExpr = (SimpleNode) child.jjtGetChild(1);
112                 SimpleNode op = (SimpleNode) relExpr.jjtGetChild(0);
113                 qFilter.setOperator(op.getText());
114                 simpleExpr = (SimpleNode) relExpr.jjtGetChild(1);
115                 if (simpleExpr.jjtGetNumChildren() > 0) {
116                     QueryColumn field = new QueryColumn();
117                     field = readTableColumn((SimpleNode) simpleExpr.jjtGetChild(0), field);
118                     qFilter.setRightOp(field);
119                 } else {
120                     List<String> l = new ArrayList<String>();
121                     l.add(getUnquotedExpression(simpleExpr.getText()));
122                     qFilter.setRightOp(l);
123                 }
124                 list.add(qFilter);
125             } else {
126                 SimpleNode inClause = (SimpleNode) child.jjtGetChild(1);
127                 SimpleNode exprList = (SimpleNode) inClause.jjtGetChild(0);
128                 List<String> l = new ArrayList<String>();
129                 QueryFilter filter = new QueryFilter();
130                 filter.setLeftOp(qFilter.getLeftOp());
131                 filter.setOperator("=");
132                 for (int i = 0; i < exprList.jjtGetNumChildren(); i++) {
133                     SimpleNode item = (SimpleNode) exprList.jjtGetChild(i);
134                     l.add(getUnquotedExpression(item.getText()));
135                 }
136                 filter.setRightOp(l);
137                 list.add(filter);
138 
139             }
140         } else {
141             for (int j = 0; j < node.jjtGetNumChildren(); j++) {
142                 SimpleNode item = (SimpleNode) node.jjtGetChild(j);
143                 list.addAll(extractQueryFilters(item));
144             }
145         }
146         return list;
147     }
148 
149     public QueryColumn readTableColumn(final SimpleNode node, final QueryColumn field) {
150         SimpleNode child = (SimpleNode) node.jjtGetChild(0);
151         if (child instanceof ASTTableColumnName) {
152             String fieldName = ((SimpleNode) child.jjtGetChild(1)).getText();
153             field.setField(getUnquotedName(fieldName));
154             String tableAliasName = ((SimpleNode) child.jjtGetChild(0)).getText();
155             field.setTableAlias(getUnquotedName(tableAliasName));
156         } else if (child instanceof ASTCompleteTableColumnName) {
157             String fieldName = ((SimpleNode) child.jjtGetChild(1)).getText();
158             field.setField(getUnquotedName(fieldName));
159             SimpleNode tableReference = (SimpleNode) child.jjtGetChild(0);
160             SimpleNode catalog = (SimpleNode) tableReference.jjtGetChild(0);
161             SimpleNode schema = (SimpleNode) tableReference.jjtGetChild(1);
162             SimpleNode table = (SimpleNode) tableReference.jjtGetChild(2);
163             field.setCatalog(getUnquotedName(((SimpleNode) catalog.jjtGetChild(0)).getText()));
164             field.setSchema(getUnquotedName(((SimpleNode) schema.jjtGetChild(0)).getText()));
165             field.setTable(getUnquotedName(((SimpleNode) table.jjtGetChild(0)).getText()));
166         } else {
167             field.setField(getUnquotedName(child.getText()));
168         }
169         return field;
170     }
171 
172     public String getUnquotedName(final String name) {
173         if (name.startsWith(QUOTE_NAME_CHAR) && name.endsWith(QUOTE_NAME_CHAR)) {
174             return name.substring(1, name.length() - 1);
175         }
176         return name;
177     }
178 
179     public String getUnquotedExpression(final String name) {
180         if (name.startsWith(QUOTE_EXPRESSION_CHAR) && name.endsWith(QUOTE_EXPRESSION_CHAR)) {
181             return name.substring(1, name.length() - 1);
182         }
183         return name;
184     }
185 
186 
187 }