Skip to content

Allow Table and Column name expressions to return SqlIdentifier #2077

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 1 commit into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@
* @author Bastian Wilhelm
* @author Mikhail Polivakha
* @author Kurt Niemi
* @author Sergey Korotaev
*/
class BasicRelationalPersistentEntity<T> extends BasicPersistentEntity<T, RelationalPersistentProperty>
implements RelationalPersistentEntity<T> {
Expand All @@ -47,7 +48,7 @@ class BasicRelationalPersistentEntity<T> extends BasicPersistentEntity<T, Relati
private final @Nullable Expression tableNameExpression;
private final Lazy<Optional<SqlIdentifier>> schemaName;
private final @Nullable Expression schemaNameExpression;
private final ExpressionEvaluator expressionEvaluator;
private final SqlIdentifierExpressionEvaluator sqlIdentifierExpressionEvaluator;
private boolean forceQuote = true;

/**
Expand All @@ -56,11 +57,11 @@ class BasicRelationalPersistentEntity<T> extends BasicPersistentEntity<T, Relati
* @param information must not be {@literal null}.
*/
BasicRelationalPersistentEntity(TypeInformation<T> information, NamingStrategy namingStrategy,
ExpressionEvaluator expressionEvaluator) {
SqlIdentifierExpressionEvaluator sqlIdentifierExpressionEvaluator) {

super(information);

this.expressionEvaluator = expressionEvaluator;
this.sqlIdentifierExpressionEvaluator = sqlIdentifierExpressionEvaluator;

Lazy<Optional<SqlIdentifier>> defaultSchema = Lazy.of(() -> StringUtils.hasText(namingStrategy.getSchema())
? Optional.of(createDerivedSqlIdentifier(namingStrategy.getSchema()))
Expand Down Expand Up @@ -129,15 +130,15 @@ public SqlIdentifier getTableName() {
return tableName.get();
}

return createSqlIdentifier(expressionEvaluator.evaluate(tableNameExpression));
return sqlIdentifierExpressionEvaluator.evaluate(tableNameExpression, isForceQuote());
}

@Override
public SqlIdentifier getQualifiedTableName() {

SqlIdentifier schema;
if (schemaNameExpression != null) {
schema = createSqlIdentifier(expressionEvaluator.evaluate(schemaNameExpression));
schema = sqlIdentifierExpressionEvaluator.evaluate(schemaNameExpression, isForceQuote());
} else {
schema = schemaName.get().orElse(null);
}
Expand All @@ -147,7 +148,7 @@ public SqlIdentifier getQualifiedTableName() {
}

if (schemaNameExpression != null) {
schema = createSqlIdentifier(expressionEvaluator.evaluate(schemaNameExpression));
schema = sqlIdentifierExpressionEvaluator.evaluate(schemaNameExpression, isForceQuote());
}

return SqlIdentifier.from(schema, getTableName());
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,7 @@
* @author Florian Lüdiger
* @author Bastian Wilhelm
* @author Kurt Niemi
* @author Sergey Korotaev
*/
public class BasicRelationalPersistentProperty extends AnnotationBasedPersistentProperty<RelationalPersistentProperty>
implements RelationalPersistentProperty {
Expand All @@ -61,7 +62,9 @@ public class BasicRelationalPersistentProperty extends AnnotationBasedPersistent

private final NamingStrategy namingStrategy;
private boolean forceQuote = true;
private ExpressionEvaluator expressionEvaluator = new ExpressionEvaluator(EvaluationContextProvider.DEFAULT);

private SqlIdentifierExpressionEvaluator sqlIdentifierExpressionEvaluator =
new SqlIdentifierExpressionEvaluator(EvaluationContextProvider.DEFAULT);

/**
* Creates a new {@link BasicRelationalPersistentProperty}.
Expand All @@ -73,7 +76,7 @@ public class BasicRelationalPersistentProperty extends AnnotationBasedPersistent
* @since 2.0
*/
public BasicRelationalPersistentProperty(Property property, PersistentEntity<?, RelationalPersistentProperty> owner,
SimpleTypeHolder simpleTypeHolder, NamingStrategy namingStrategy) {
SimpleTypeHolder simpleTypeHolder, NamingStrategy namingStrategy) {

super(property, owner, simpleTypeHolder);
this.namingStrategy = namingStrategy;
Expand Down Expand Up @@ -136,8 +139,8 @@ public BasicRelationalPersistentProperty(Property property, PersistentEntity<?,
this.collectionKeyColumnName = collectionKeyColumnName;
}

void setExpressionEvaluator(ExpressionEvaluator expressionEvaluator) {
this.expressionEvaluator = expressionEvaluator;
void setSqlIdentifierExpressionEvaluator(SqlIdentifierExpressionEvaluator sqlIdentifierExpressionEvaluator) {
this.sqlIdentifierExpressionEvaluator = sqlIdentifierExpressionEvaluator;
}

/**
Expand Down Expand Up @@ -191,7 +194,7 @@ public SqlIdentifier getColumnName() {
return columnName.get();
}

return createSqlIdentifier(expressionEvaluator.evaluate(columnNameExpression));
return sqlIdentifierExpressionEvaluator.evaluate(columnNameExpression, isForceQuote());
}

@Override
Expand Down Expand Up @@ -222,7 +225,7 @@ public SqlIdentifier getKeyColumn() {
return collectionKeyColumnName.get();
}

return createSqlIdentifier(expressionEvaluator.evaluate(collectionKeyColumnNameExpression));
return sqlIdentifierExpressionEvaluator.evaluate(collectionKeyColumnNameExpression, isForceQuote());
}

@Override
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -48,7 +48,8 @@ public class RelationalMappingContext

private boolean forceQuote = true;

private final ExpressionEvaluator expressionEvaluator = new ExpressionEvaluator(EvaluationContextProvider.DEFAULT);
private final SqlIdentifierExpressionEvaluator sqlIdentifierExpressionEvaluator =
new SqlIdentifierExpressionEvaluator(EvaluationContextProvider.DEFAULT);
private boolean singleQueryLoadingEnabled = false;

/**
Expand Down Expand Up @@ -99,7 +100,7 @@ public void setForceQuote(boolean forceQuote) {
* @since 3.2
*/
public void setSqlIdentifierSanitizer(SqlIdentifierSanitizer sanitizer) {
this.expressionEvaluator.setSanitizer(sanitizer);
this.sqlIdentifierExpressionEvaluator.setSanitizer(sanitizer);
}

public NamingStrategy getNamingStrategy() {
Expand All @@ -108,7 +109,7 @@ public NamingStrategy getNamingStrategy() {

@Override
public void setApplicationContext(ApplicationContext applicationContext) throws BeansException {
this.expressionEvaluator.setProvider(new ExtensionAwareEvaluationContextProvider(applicationContext));
this.sqlIdentifierExpressionEvaluator.setProvider(new ExtensionAwareEvaluationContextProvider(applicationContext));
}

@Nullable
Expand All @@ -130,7 +131,7 @@ public RelationalPersistentEntity<?> getPersistentEntity(RelationalPersistentPro
protected <T> RelationalPersistentEntity<T> createPersistentEntity(TypeInformation<T> typeInformation) {

BasicRelationalPersistentEntity<T> entity = new BasicRelationalPersistentEntity<>(typeInformation,
this.namingStrategy, this.expressionEvaluator);
this.namingStrategy, this.sqlIdentifierExpressionEvaluator);
entity.setForceQuote(isForceQuote());

return entity;
Expand Down Expand Up @@ -171,7 +172,7 @@ public void setSingleQueryLoadingEnabled(boolean singleQueryLoadingEnabled) {
protected void applyDefaults(BasicRelationalPersistentProperty persistentProperty) {

persistentProperty.setForceQuote(isForceQuote());
persistentProperty.setExpressionEvaluator(this.expressionEvaluator);
persistentProperty.setSqlIdentifierExpressionEvaluator(this.sqlIdentifierExpressionEvaluator);
}

/**
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package org.springframework.data.relational.core.mapping;

import org.springframework.data.relational.core.sql.SqlIdentifier;
import org.springframework.data.spel.EvaluationContextProvider;
import org.springframework.expression.EvaluationException;
import org.springframework.expression.Expression;
Expand All @@ -13,25 +14,31 @@
* {@link #setSanitizer(SqlIdentifierSanitizer)} method.
*
* @author Kurt Niemi
* @author Sergey Korotaev
* @see SqlIdentifierSanitizer
* @since 3.2
*/
class ExpressionEvaluator {
class SqlIdentifierExpressionEvaluator {

private EvaluationContextProvider provider;

private SqlIdentifierSanitizer sanitizer = SqlIdentifierSanitizer.words();

public ExpressionEvaluator(EvaluationContextProvider provider) {
public SqlIdentifierExpressionEvaluator(EvaluationContextProvider provider) {
this.provider = provider;
}

public String evaluate(Expression expression) throws EvaluationException {
public SqlIdentifier evaluate(Expression expression, boolean isForceQuote) throws EvaluationException {

Assert.notNull(expression, "Expression must not be null.");

String result = expression.getValue(provider.getEvaluationContext(null), String.class);
return sanitizer.sanitize(result);
Object value = expression.getValue(provider.getEvaluationContext(null), Object.class);
if (value instanceof SqlIdentifier sqlIdentifier) {
return sqlIdentifier;
}

String sanitizedResult = sanitizer.sanitize((String) value);
return isForceQuote ? SqlIdentifier.quoted(sanitizedResult) : SqlIdentifier.unquoted(sanitizedResult);
}

public void setSanitizer(SqlIdentifierSanitizer sanitizer) {
Expand Down