1 21 package oracle.toplink.essentials.internal.parsing; 23 24 25 import java.util.*; 27 28 import oracle.toplink.essentials.exceptions.EJBQLException; 30 import oracle.toplink.essentials.expressions.*; 31 import oracle.toplink.essentials.queryframework.*; 32 import oracle.toplink.essentials.internal.localization.*; 33 import oracle.toplink.essentials.internal.sessions.AbstractSession; 34 35 51 public class ParseTree { 52 private ParseTreeContext context; 53 private QueryNode queryNode; 54 private FromNode fromNode; 55 private SetNode setNode; 56 private WhereNode whereNode; 57 private OrderByNode orderByNode = null; 58 private GroupByNode groupByNode = null; 59 private HavingNode havingNode = null; 60 private ClassLoader classLoader = null; 61 private short distinctState = ObjectLevelReadQuery.UNCOMPUTED_DISTINCT; 62 private boolean validated = false; 63 private Set unusedVariables = null; 64 65 68 public ParseTree() { 69 super(); 70 } 71 72 78 public void adjustReferenceClassForQuery(DatabaseQuery theQuery, GenerationContext generationContext) { 79 Class referenceClass = getReferenceClass(theQuery, generationContext); 80 if ((referenceClass != null) && (referenceClass != theQuery.getReferenceClass())) { 81 if (theQuery.isObjectLevelReadQuery()) { 82 ((ObjectLevelReadQuery)theQuery).setReferenceClass(referenceClass); 85 generationContext.setBaseQueryClass(referenceClass); 86 ((ObjectLevelReadQuery)theQuery).changeDescriptor(generationContext.getSession()); 87 } else if (theQuery.isUpdateAllQuery()) { 88 ((UpdateAllQuery)theQuery).setReferenceClass(referenceClass); 89 } else if (theQuery.isDeleteAllQuery()) { 90 ((DeleteAllQuery)theQuery).setReferenceClass(referenceClass); 91 } 92 } 93 } 94 95 99 public void initBaseExpression(ObjectLevelReadQuery theQuery, GenerationContext generationContext) { 100 String variable = getFromNode().getFirstVariable(); 101 ParseTreeContext context = generationContext.getParseTreeContext(); 102 if (context.isRangeVariable(variable)) { 103 Class referenceClass = theQuery.getReferenceClass(); 104 ExpressionBuilder builder = new ExpressionBuilder(referenceClass); 106 theQuery.setExpressionBuilder(builder); 108 generationContext.setBaseExpression(variable, builder); 110 } else { 111 Node path = context.pathForVariable(variable); 113 Class baseClass = getBaseExpressionClass(path, generationContext); 115 theQuery.setExpressionBuilder(new ExpressionBuilder(baseClass)); 117 theQuery.setReferenceClass(baseClass); 119 theQuery.changeDescriptor(generationContext.getSession()); 120 generationContext.setBaseQueryClass(baseClass); 121 generationContext.setBaseExpression( 123 variable, path.generateExpression(generationContext)); 124 } 125 } 126 127 131 public void initBaseExpression(ModifyAllQuery theQuery, GenerationContext generationContext) { 132 ModifyNode queryNode = (ModifyNode)getQueryNode(); 133 String variable = queryNode.getAbstractSchemaIdentifier(); 134 if (variable == null) { 135 variable = queryNode.getAbstractSchemaName(); 138 } 139 Class referenceClass = theQuery.getReferenceClass(); 140 ExpressionBuilder builder = new ExpressionBuilder(referenceClass); 142 theQuery.setExpressionBuilder(builder); 144 generationContext.setBaseExpression(variable, builder); 146 } 147 148 149 private Class getBaseExpressionClass(Node node, GenerationContext generationContext) { 150 ParseTreeContext context = generationContext.getParseTreeContext(); 151 Class clazz = null; 152 if (node == null) { 153 clazz = null; 154 } else if (node.isDotNode()) { 155 clazz = getBaseExpressionClass(node.getLeft(), generationContext); 157 } else if (node.isVariableNode()) { 158 String variable = ((VariableNode)node).getVariableName(); 160 if (!context.isRangeVariable(variable)) { 161 Node path = context.pathForVariable(variable); 162 clazz = getBaseExpressionClass(path, generationContext); 165 } else { 166 String schema = context.schemaForVariable(variable); 169 if (schema != null) { 170 clazz = context.classForSchemaName(schema, generationContext); 171 } 172 } 173 } 174 return clazz; 175 } 176 177 181 protected void validate(AbstractSession session, ClassLoader classLoader) { 182 validate(new TypeHelperImpl(session, classLoader)); 183 } 184 185 189 public void validate(TypeHelper typeHelper) { 190 ParseTreeContext context = getContext(); 191 context.setTypeHelper(typeHelper); 192 validate(context); 193 } 194 195 199 public void validate(ParseTreeContext context) { 200 if (validated) { 201 return; 203 } 204 205 validated = true; 206 context.enterScope(); 207 if (fromNode != null) { 208 fromNode.validate(context); 209 } 210 queryNode.validate(context); 211 if (setNode != null) { 212 setNode.validate(context); 213 } 214 if (whereNode != null) { 215 whereNode.validate(context); 216 } 217 if (hasOrderBy()) { 218 orderByNode.validate(context, (SelectNode)queryNode); 219 } 220 if (hasGroupBy()) { 221 groupByNode.validate(context, (SelectNode)queryNode); 222 } 223 if (hasHaving()) { 224 havingNode.validate(context, groupByNode); 225 } 226 unusedVariables = context.getUnusedVariables(); 228 context.leaveScope(); 229 } 230 231 235 public void addOrderingToQuery(ObjectLevelReadQuery theQuery, GenerationContext generationContext) { 236 if (hasOrderBy()) { 237 ((OrderByNode)getOrderByNode()).addOrderingToQuery(theQuery, generationContext); 238 } 239 } 240 241 245 public void addGroupingToQuery(ObjectLevelReadQuery theQuery, GenerationContext generationContext) { 246 if (hasGroupBy()) { 247 ((GroupByNode)getGroupByNode()).addGroupingToQuery(theQuery, generationContext); 248 } 249 } 250 251 255 public void addHavingToQuery(ObjectLevelReadQuery theQuery, GenerationContext generationContext) { 256 if (hasHaving()) { 257 ((HavingNode)getHavingNode()).addHavingToQuery(theQuery, generationContext); 258 } 259 } 260 261 264 public void addNonFetchJoinAttributes(ObjectLevelReadQuery theQuery, GenerationContext generationContext) { 265 ParseTreeContext context = generationContext.getParseTreeContext(); 266 for (Iterator i = unusedVariables.iterator(); i.hasNext();) { 267 String variable = (String )i.next(); 268 Expression expr = null; 269 if (!context.isRangeVariable(variable)) { 270 Node path = context.pathForVariable(variable); 271 expr = path.generateExpression(generationContext); 272 theQuery.addNonFetchJoinedAttribute(expr); 273 } else { 274 throw EJBQLException.notYetImplemented( 276 "Variable [" + variable + "] is defined in a range variable declaration, but not used in the rest of the query."); 277 } 278 } 279 } 280 281 285 public void addUpdatesToQuery(UpdateAllQuery theQuery, GenerationContext generationContext) { 286 if (getSetNode() != null) { 287 ((SetNode)getSetNode()).addUpdatesToQuery(theQuery, generationContext); 288 } 289 } 290 291 295 public void addParametersToQuery(DatabaseQuery query) { 296 if (context.hasParameters()) { 298 for (Iterator i = context.getParameterNames().iterator(); i.hasNext();) { 299 String param = (String )i.next(); 300 Class type = (Class )context.getParameterType(param); 301 if (type == null) { 302 type = Object .class; 303 } 304 query.addArgument(param, type); 305 } 306 } 307 } 308 309 315 public void applyQueryNodeToQuery(DatabaseQuery theQuery, GenerationContext generationContext) { 316 getQueryNode().applyToQuery(theQuery, generationContext); 317 } 318 319 323 public GenerationContext buildContext(DatabaseQuery query, AbstractSession sessionForContext) { 324 if (query.isObjectLevelReadQuery()) { 325 return buildContextForReadQuery(sessionForContext); 326 } else if (query.isUpdateAllQuery() || query.isDeleteAllQuery()) { 327 return new GenerationContext(getContext(), sessionForContext, this); 328 } 329 return null; 330 } 331 332 336 public GenerationContext buildContextForReadQuery(AbstractSession sessionForContext) { 337 return new SelectGenerationContext(getContext(), sessionForContext, this); 338 } 339 340 344 public Expression generateExpression(DatabaseQuery readQuery, GenerationContext generationContext) { 345 Expression selectExpression = getQueryNode().generateExpression(generationContext); 346 if (getWhereNode() == null) { 347 return selectExpression; 348 } 349 Expression whereExpression = getWhereNode().generateExpression(generationContext); 350 351 selectExpression = getQueryNode().generateExpression(generationContext); 352 if (selectExpression != null) { 353 whereExpression = selectExpression.and(whereExpression); 354 } 355 return whereExpression; 356 } 357 358 361 public ParseTreeContext getContext() { 362 return context; 363 } 364 365 369 public FromNode getFromNode() { 370 return fromNode; 371 } 372 373 378 public ClassLoader getClassLoader() { 379 if (classLoader == null) { 380 return oracle.toplink.essentials.internal.helper.ConversionManager.getDefaultManager().getLoader(); 381 } else { 382 return classLoader; 383 } 384 } 385 386 390 public OrderByNode getOrderByNode() { 391 return orderByNode; 392 } 393 394 398 public GroupByNode getGroupByNode() { 399 return groupByNode; 400 } 401 402 406 public HavingNode getHavingNode() { 407 return havingNode; 408 } 409 410 414 public Class getReferenceClass(DatabaseQuery query, GenerationContext generationContext) { 415 if (getQueryNode() == null) { 416 return null; 417 } 418 return getQueryNode().getReferenceClass(generationContext); 419 } 420 421 425 public QueryNode getQueryNode() { 426 return queryNode; 427 } 428 429 433 public SetNode getSetNode() { 434 return setNode; 435 } 436 437 441 public WhereNode getWhereNode() { 442 return whereNode; 443 } 444 445 449 public short getDistinctState() { 450 return distinctState; 451 } 452 453 457 public boolean hasOrderBy() { 458 return getOrderByNode() != null; 459 } 460 461 465 public boolean hasGroupBy() { 466 return getGroupByNode() != null; 467 } 468 469 473 public boolean hasHaving() { 474 return getHavingNode() != null; 475 } 476 477 482 public void setClassLoader(ClassLoader loader){ 483 this.classLoader = loader; 484 } 485 486 490 public void setContext(ParseTreeContext newContext) { 491 context = newContext; 492 } 493 494 498 public void setFromNode(FromNode fromNode) { 499 this.fromNode = fromNode; 500 } 501 502 506 public void setOrderByNode(OrderByNode newOrderByNode) { 507 orderByNode = newOrderByNode; 508 } 509 510 514 public void setGroupByNode(GroupByNode newGroupByNode) { 515 groupByNode = newGroupByNode; 516 } 517 518 522 public void setHavingNode(HavingNode newHavingNode) { 523 havingNode = newHavingNode; 524 } 525 526 public void setSelectionCriteriaForQuery(DatabaseQuery theQuery, GenerationContext generationContext) { 527 theQuery.setSelectionCriteria(generateExpression(theQuery, generationContext)); 528 } 529 530 534 public void setQueryNode(QueryNode newQueryNode) { 535 queryNode = newQueryNode; 536 } 537 538 542 public void setSetNode(SetNode newSetNode) { 543 setNode = newSetNode; 544 } 545 546 550 public void setWhereNode(WhereNode newWhereNode) { 551 whereNode = newWhereNode; 552 } 553 554 558 public void setDistinctState(short newDistinctState) { 559 distinctState = newDistinctState; 560 } 561 562 566 public String toString() { 567 StringBuffer buffer = new StringBuffer (); 568 buffer.append(getContext().toString()); 569 return ToStringLocalization.buildMessage("context", (Object [])null) + " " + buffer.toString(); 570 } 571 572 578 public void verifySelect(DatabaseQuery theQuery, GenerationContext generationContext) { 579 if (theQuery.isObjectLevelReadQuery()) { 580 ((SelectNode)getQueryNode()).verifySelectedAlias(generationContext); 583 } 584 } 585 586 590 public boolean usesDistinct() { 591 return distinctState == ObjectLevelReadQuery.USE_DISTINCT; 592 } 593 } 594 | Popular Tags |