KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > oracle > toplink > essentials > internal > parsing > VariableNode


1 /*
2  * The contents of this file are subject to the terms
3  * of the Common Development and Distribution License
4  * (the "License"). You may not use this file except
5  * in compliance with the License.
6  *
7  * You can obtain a copy of the license at
8  * glassfish/bootstrap/legal/CDDLv1.0.txt or
9  * https://glassfish.dev.java.net/public/CDDLv1.0.html.
10  * See the License for the specific language governing
11  * permissions and limitations under the License.
12  *
13  * When distributing Covered Code, include this CDDL
14  * HEADER in each file and include the License file at
15  * glassfish/bootstrap/legal/CDDLv1.0.txt. If applicable,
16  * add the following below this CDDL HEADER, with the
17  * fields enclosed by brackets "[]" replaced with your
18  * own identifying information: Portions Copyright [yyyy]
19  * [name of copyright owner]
20  */

21 // Copyright (c) 1998, 2006, Oracle. All rights reserved.
22
package oracle.toplink.essentials.internal.parsing;
23
24 import java.util.*;
25
26 // TopLink imports
27
import oracle.toplink.essentials.exceptions.*;
28 import oracle.toplink.essentials.expressions.*;
29 import oracle.toplink.essentials.mappings.DatabaseMapping;
30 import oracle.toplink.essentials.queryframework.ObjectLevelReadQuery;
31 import oracle.toplink.essentials.queryframework.ReportQuery;
32
33 /**
34  * INTERNAL
35  * <p><b>Purpose</b>: The Superclass for for typed variables, local variables and remote variables
36  * <p><b>Responsibilities</b>:<ul>
37  * <li> Generate the correct expression for an AND in EJBQL
38  * </ul>
39  * @author Jon Driscoll and Joel Lucuik
40  * @since TopLink 4.0
41  */

42 public class VariableNode extends Node {
43
44     /** */
45     private String JavaDoc variableName;
46     
47     /** */
48     private String JavaDoc canonicalName;
49
50     /**
51      * VariableNode constructor comment.
52      */

53     public VariableNode() {
54         super();
55     }
56
57     public VariableNode(String JavaDoc newVariableName) {
58         setVariableName(newVariableName);
59     }
60
61     public String JavaDoc getVariableName() {
62         return variableName;
63     }
64
65     public void setVariableName(String JavaDoc newVariableName) {
66         variableName = newVariableName;
67         canonicalName = IdentificationVariableDeclNode.calculateCanonicalName(newVariableName);
68     }
69
70     /** */
71     public String JavaDoc getCanonicalVariableName() {
72         return canonicalName;
73     }
74
75     /**
76      * INTERNAL
77      * Is this node a VariableNode
78      */

79     public boolean isVariableNode() {
80         return true;
81     }
82
83     /**
84      * INTERNAL
85      * Apply this node to the passed query
86      */

87     public void applyToQuery(ObjectLevelReadQuery theQuery, GenerationContext generationContext) {
88         String JavaDoc name = getCanonicalVariableName();
89         ParseTreeContext context = generationContext.getParseTreeContext();
90         if (theQuery instanceof ReportQuery) {
91             ReportQuery reportQuery = (ReportQuery)theQuery;
92             Expression expression = generationContext.expressionFor(name);
93             if (expression == null) {
94                 expression = generateExpression(generationContext);
95             }
96             addAttribute(reportQuery, expression, generationContext);
97         }
98     }
99
100     /** */
101     private void addAttribute(ReportQuery reportQuery, Expression expression,
102                               GenerationContext context) {
103         String JavaDoc name = getCanonicalVariableName();
104         List fetchJoinNodes = context.getParseTreeContext().getFetchJoins(name);
105         if (fetchJoinNodes == null) {
106             reportQuery.addAttribute(name, expression);
107         } else {
108             List fetchJoinExprs = new ArrayList(fetchJoinNodes.size());
109             for (Iterator i = fetchJoinNodes.iterator(); i.hasNext(); ) {
110                 Node node = (Node)i.next();
111                 fetchJoinExprs.add(node.generateExpression(context));
112             }
113             reportQuery.addItem(name, expression, fetchJoinExprs);
114         }
115     }
116
117     /**
118      * INTERNAL
119      * Validate node and calculate its type.
120      */

121     public void validate(ParseTreeContext context) {
122         TypeHelper typeHelper = context.getTypeHelper();
123         String JavaDoc name = getCanonicalVariableName();
124         if (context.isRangeVariable(name)) {
125             String JavaDoc schema = context.schemaForVariable(name);
126             setType(typeHelper.resolveSchema(schema));
127         } else {
128             Node path = context.pathForVariable(name);
129             if (path == null) {
130                 throw EJBQLException.aliasResolutionException(name);
131             } else {
132                 setType(path.getType());
133             }
134         }
135         context.usedVariable(name);
136         if (context.isDeclaredInOuterScope(name)) {
137             context.registerOuterScopeVariable(name);
138         }
139     }
140
141     public Expression generateBaseBuilderExpression(GenerationContext context) {
142         //create builder, and add it, and answer it
143
//BUG 3106877: Need to create builder using the actual class (if using parallel expressions)
144
if (context.useParallelExpressions()) {
145             return new ExpressionBuilder(this.resolveClass(context));
146         } else {
147             return new ExpressionBuilder();
148         }
149     }
150
151     public Expression generateExpression(GenerationContext generationContext) {
152         Expression myExpression = null;
153         String JavaDoc name = getCanonicalVariableName();
154         
155         //is there a cached Expression?
156
myExpression = generationContext.expressionFor(name);
157         if (myExpression != null) {
158             return myExpression;
159         }
160
161         //Either I have an alias type, or I'm an IN declaration
162
if (generationContext.getParseTreeContext().isRangeVariable(name)) {
163             myExpression = generateBaseBuilderExpression(generationContext);
164         } else {
165             myExpression = generateExpressionForAlias(generationContext);
166         }
167
168         generationContext.addExpression(myExpression, name);
169         return myExpression;
170     }
171
172     public Expression generateExpressionForAlias(GenerationContext context) {
173         // BUG 3105651: Verify if we need to resolve this alias, or just use
174
// an empty ExpressionBuilder. See OrderByItemNode.generateExpression()
175
// for more details
176
if (context.getParseTree().getQueryNode().isSelectNode() && context.shouldCheckSelectNodeBeforeResolving() && (((SelectNode)context.getParseTree().getQueryNode()).isSelected(this.getCanonicalVariableName()))) {
177             return new ExpressionBuilder();
178         }
179
180         Node nodeForAlias = getNodeForAlias(context);
181
182         //assume that if there is no node available for the given variable, then
183
//there must be an alias mismatch. Assume they know their attribute names better
184
//than their alias names. - JGL
185
if (nodeForAlias == null) {
186             throw EJBQLException.aliasResolutionException(getVariableName());
187         }
188
189         //create builder, and answer it
190
return nodeForAlias.generateExpression(context);
191     }
192
193     public Node getNodeForAlias(GenerationContext context) {
194         //Node node = context.getParseTreeContext().nodeForIdentifier(getCanonicalVariableName());
195
//return node != null ? ((IdentificationVariableDeclNode)node).getPath() : null;
196
return context.getParseTreeContext().pathForVariable(getCanonicalVariableName());
197     }
198
199     /**
200      * isAlias: Answer true if this variable represents an alias in the FROM clause.
201      * i.e. "FROM Employee emp" declares "emp" as an alias
202      */

203     public boolean isAlias(GenerationContext context) {
204         return isAlias(context.getParseTreeContext());
205     }
206
207     public boolean isAlias(ParseTreeContext context) {
208         String JavaDoc classNameForAlias = context.schemaForVariable(getCanonicalVariableName());
209         return classNameForAlias != null;
210     }
211
212     /**
213      * resolveClass: Answer the class which corresponds to my variableName. This is the class for
214      * an alias, where the variableName is registered to an alias.
215      */

216     public Class JavaDoc resolveClass(GenerationContext generationContext) {
217         Class JavaDoc clazz = null;
218         String JavaDoc name = getCanonicalVariableName();
219         ParseTreeContext context = generationContext.getParseTreeContext();
220         if (context.isRangeVariable(name)) {
221             String JavaDoc schema = context.schemaForVariable(name);
222             clazz = context.classForSchemaName(schema, generationContext);
223         } else {
224             DotNode path = (DotNode)context.pathForVariable(name);
225             if (path == null) {
226                 throw EJBQLException.aliasResolutionException(name);
227             } else {
228                 clazz = path.resolveClass(generationContext);
229             }
230         }
231         return clazz;
232     }
233
234     public String JavaDoc toString(int indent) {
235         StringBuffer JavaDoc buffer = new StringBuffer JavaDoc();
236         toStringIndent(indent, buffer);
237         buffer.append(toStringDisplayName() + "[" + getVariableName() + "]");
238         return buffer.toString();
239     }
240
241     /**
242      * INTERNAL
243      * Get the string representation of this node.
244      */

245     public String JavaDoc getAsString() {
246         return getVariableName();
247     }
248
249 }
250
Popular Tags