use of org.eclipse.persistence.jpa.jpql.parser.IdentificationVariable in project eclipselink by eclipse-ee4j.
the class GenericSemanticValidatorHelper method collectLocalDeclarationIdentificationVariables.
protected void collectLocalDeclarationIdentificationVariables(JPQLQueryContext queryContext, Map<String, List<IdentificationVariable>> identificationVariables) {
DeclarationResolver declarationResolver = queryContext.getDeclarationResolverImp();
for (Declaration declaration : declarationResolver.getDeclarations()) {
// Register the identification variable from the base expression
IdentificationVariable identificationVariable = declaration.getIdentificationVariable();
addIdentificationVariable(identificationVariable, identificationVariables);
// Register the identification variable from the JOIN expressions
for (Join join : declaration.getJoins()) {
IdentificationVariable joinIdentificationVariable = getIdentificationVariable(join.getIdentificationVariable());
addIdentificationVariable(joinIdentificationVariable, identificationVariables);
}
}
if (queryContext.getParent() == null) {
for (IdentificationVariable identificationVariable : declarationResolver.getResultVariablesMap().keySet()) {
addIdentificationVariable(identificationVariable, identificationVariables);
}
}
}
use of org.eclipse.persistence.jpa.jpql.parser.IdentificationVariable in project eclipselink by eclipse-ee4j.
the class DeclarationResolver method addRangeVariableDeclaration.
/**
* Registers a range variable declaration that will be used when a JPQL fragment is parsed.
*
* @param entityName The name of the entity to be accessible with the given variable name
* @param variableName The identification variable used to navigate to the entity
*/
public void addRangeVariableDeclaration(String entityName, String variableName) {
// Always make the identification variable be upper case since it's
// case insensitive, the get will also use upper case
String internalVariableName = variableName.toUpperCase(Locale.ROOT);
// this could cause issues when trying to resolve it
if (!resolvers.containsKey(internalVariableName)) {
// Resolve the expression and map it with the identification variable
Resolver resolver = new EntityResolver(this, entityName);
resolver = new IdentificationVariableResolver(resolver, variableName);
resolvers.put(internalVariableName, resolver);
RangeDeclaration declaration = new RangeDeclaration();
declaration.rootPath = entityName;
declaration.identificationVariable = new IdentificationVariable(null, variableName);
declarations.add(declaration);
}
}
use of org.eclipse.persistence.jpa.jpql.parser.IdentificationVariable in project eclipselink by eclipse-ee4j.
the class AbstractSemanticValidator method validateComparisonExpression.
/**
* Validates the left and right expressions of the given {@link ComparisonExpression}. The tests
* to perform are:
* <ul>
* <li>If the comparison operator is either '=' or {@literal '<>'}. The expressions can only be
* <ul>
* <li>Two identification variables;</li>
* <li>Two path expressions resolving to an association field;</li>
* <li>One can be a path expression resolving to a basic field and the other one has to
* resolve to a basic value.</li>
* </ul>
* </li>
* <li>If the comparison operator is either {@literal '<', '<=', '>=', '>'}. The expressions cannot be
* <ul>
* <li>Two identification variables;</li>
* <li>Two path expressions resolving to an association field;</li>
* </ul>
* </li>
* </ul>
*
* @param expression The {@link ConcatExpression} to validate by validating its
* left and right expressions
* @return The status of the comparison between the left and right expression: <code>true</code>
* if the two expressions pass the rules defined by this method; <code>false</code> otherwise
*/
protected boolean validateComparisonExpression(ComparisonExpression expression) {
Expression leftExpression = expression.getLeftExpression();
Expression rightExpression = expression.getRightExpression();
boolean valid = true;
// First determine what is being compared and validate them as well
ComparisonExpressionVisitor validator = getComparisonExpressionVisitor();
try {
// Visit the left expression and gather its information
validator.validatingLeftExpression = true;
leftExpression.accept(validator);
// Visit the right expression and gather its information
validator.validatingLeftExpression = false;
rightExpression.accept(validator);
// '<', '<=', '>=', '>'
if (isOrderComparison(expression)) {
// The left expression cannot be an identification variable
if (validator.leftIdentificationVariable && validator.leftIdentificationVariableValid) {
IdentificationVariable variable = (IdentificationVariable) leftExpression;
// maps to a direct collection mapping
if (!isIdentificationVariableValidInComparison(variable)) {
addProblem(leftExpression, ComparisonExpression_IdentificationVariable, leftExpression.toActualText(), expression.getComparisonOperator());
valid = false;
}
} else // The left expression is a path expression
if (validator.leftStateFieldPathExpression && validator.leftStateFieldPathExpressionValid) {
Object mapping = helper.resolveMapping(leftExpression);
// The path expression cannot be a non-basic mapping
if ((mapping != null) && !helper.isPropertyMapping(mapping)) {
addProblem(leftExpression, ComparisonExpression_AssociationField, leftExpression.toActualText(), expression.getComparisonOperator());
valid = false;
}
}
// The right expression cannot be an identification variable
if (validator.rightIdentificationVariable && validator.rightIdentificationVariableValid) {
IdentificationVariable variable = (IdentificationVariable) rightExpression;
// maps to a direct collection mapping
if (!isIdentificationVariableValidInComparison(variable)) {
addProblem(rightExpression, ComparisonExpression_IdentificationVariable, rightExpression.toActualText(), expression.getComparisonOperator());
valid = false;
}
} else // The right expression is a path expression
if (validator.rightStateFieldPathExpression && validator.rightStateFieldPathExpressionValid) {
Object mapping = helper.resolveMapping(rightExpression);
// The path expression cannot be a non-basic mapping
if ((mapping != null) && !helper.isPropertyMapping(mapping)) {
addProblem(rightExpression, ComparisonExpression_AssociationField, rightExpression.toActualText(), expression.getComparisonOperator());
valid = false;
}
}
} else // '=', '<>'
{
// The right expression is a path expression
if (validator.leftIdentificationVariable && validator.leftIdentificationVariableValid && validator.rightStateFieldPathExpression && validator.rightStateFieldPathExpressionValid) {
Object mapping = helper.resolveMapping(rightExpression);
IdentificationVariable variable = (IdentificationVariable) leftExpression;
// maps to a direct collection mapping
if ((mapping != null) && helper.isPropertyMapping(mapping) && !isIdentificationVariableValidInComparison(variable)) {
addProblem(rightExpression, ComparisonExpression_BasicField, rightExpression.toActualText(), expression.getComparisonOperator());
valid = false;
}
} else // The right expression is an identification variable
if (validator.rightIdentificationVariable && validator.rightIdentificationVariableValid && validator.leftStateFieldPathExpression && validator.leftStateFieldPathExpressionValid) {
Object mapping = helper.resolveMapping(leftExpression);
IdentificationVariable variable = (IdentificationVariable) rightExpression;
// maps to a direct collection mapping
if ((mapping != null) && helper.isPropertyMapping(mapping) && !isIdentificationVariableValidInComparison(variable)) {
addProblem(leftExpression, ComparisonExpression_BasicField, leftExpression.toActualText(), expression.getComparisonOperator());
valid = false;
}
}
}
return valid;
} finally {
validator.dispose();
}
}
use of org.eclipse.persistence.jpa.jpql.parser.IdentificationVariable in project eclipselink by eclipse-ee4j.
the class AbstractSemanticValidator method validateAbstractSchemaName.
/**
* Validates the given {@link AbstractSchemaName}. The tests to perform are:
* <ul>
* <li>Check to see the actual entity associated with the entity name does exist.</li>
* <li>If the abstract schema name is actually a path expression (which can be defined in a
* subquery but is always parsed as an abstract schema name), then make sure the path
* expression is resolving to a relationship mapping.</li>
* </ul>
*
* @param expression The {@link AbstractSchemaName} to validate
* @return <code>true</code> if the entity name was resolved; <code>false</code> otherwise
*/
protected boolean validateAbstractSchemaName(AbstractSchemaName expression) {
String abstractSchemaName = expression.getText();
Object managedType = helper.getEntityNamed(abstractSchemaName);
boolean valid = true;
if (managedType == null) {
// then check for a path expression
if (isWithinSubquery(expression)) {
// Find the identification variable from the UPDATE range declaration
IdentificationVariable identificationVariable = findVirtualIdentificationVariable(expression);
String variableName = (identificationVariable != null) ? identificationVariable.getText() : null;
if (ExpressionTools.stringIsNotEmpty(variableName)) {
Object mapping = helper.resolveMapping(variableName, abstractSchemaName);
Object type = helper.getMappingType(mapping);
// Does not resolve to a valid path
if (!helper.isTypeResolvable(type)) {
addProblem(expression, StateFieldPathExpression_NotResolvable, abstractSchemaName);
valid = false;
} else // Not a relationship mapping
if (!helper.isRelationshipMapping(mapping)) {
addProblem(expression, PathExpression_NotRelationshipMapping, abstractSchemaName);
valid = false;
}
} else {
addProblem(expression, AbstractSchemaName_Invalid, abstractSchemaName);
valid = false;
}
} else // The managed type does not exist
{
addProblem(expression, AbstractSchemaName_Invalid, abstractSchemaName);
valid = false;
}
}
return valid;
}
use of org.eclipse.persistence.jpa.jpql.parser.IdentificationVariable in project eclipselink by eclipse-ee4j.
the class JPQLExpressionTest1_0 method testGetExpression_2.
@Test
public void testGetExpression_2() {
String query = "SELECT OBJECT(e), COUNT(DISTINCT e) FROM Employee e";
JPQLExpression jpqlExpression = JPQLQueryBuilder.buildQuery(query, getGrammar(), true);
Expression expression = jpqlExpression.getExpression(query, 0);
assertNotNull(expression);
assertTrue("The expression was " + expression.getClass().getSimpleName(), expression instanceof JPQLExpression);
expression = jpqlExpression.getExpression(query, 14);
assertNotNull(expression);
assertTrue("The expression was " + expression.getClass().getSimpleName(), expression instanceof ObjectExpression);
// In 'SELECT'
for (int index = 1; index < 8; index++) {
expression = jpqlExpression.getExpression(query, index);
assertNotNull(expression);
assertTrue("The expression was " + expression.getClass().getSimpleName(), expression instanceof SelectClause);
}
// In 'OBJECT('
for (int index = 8; index < 15; index++) {
expression = jpqlExpression.getExpression(query, index);
assertNotNull(expression);
assertTrue("The expression was " + expression.getClass().getSimpleName(), expression instanceof ObjectExpression);
}
// In 'e' of 'OBJECT(e)'
expression = jpqlExpression.getExpression(query, 15);
assertNotNull(expression);
assertTrue("The expression was " + expression.getClass().getSimpleName(), expression instanceof IdentificationVariable);
expression = jpqlExpression.getExpression(query, 17);
assertNotNull(expression);
assertTrue("The expression was " + expression.getClass().getSimpleName(), expression instanceof CollectionExpression);
expression = jpqlExpression.getExpression(query, 18);
assertNotNull(expression);
assertTrue("The expression was " + expression.getClass().getSimpleName(), expression instanceof CollectionExpression);
expression = jpqlExpression.getExpression(query, 24);
assertNotNull(expression);
assertTrue("The expression was " + expression.getClass().getSimpleName(), expression instanceof CountFunction);
expression = jpqlExpression.getExpression(query, 35);
assertNotNull(expression);
assertTrue("The expression was " + expression.getClass().getSimpleName(), expression instanceof CountFunction);
expression = jpqlExpression.getExpression(query, 36);
assertNotNull(expression);
assertTrue("The expression was " + expression.getClass().getSimpleName(), expression instanceof SelectStatement);
}
Aggregations