From 8064a6d1ddbd1785c45ef13fc37cc41f9850c5cc Mon Sep 17 00:00:00 2001 From: Mark Paluch Date: Tue, 18 Jun 2019 14:14:56 +0200 Subject: [PATCH] DATACASS-642 - Consider quoted identifiers in EntityQueryUtils and CqlIdentifier. EntityQueryUtils now considers quoted identifiers when extracting table names. --- .../data/cassandra/core/EntityQueryUtils.java | 10 +++++++--- .../data/cassandra/core/cql/CqlIdentifier.java | 13 +++++++++++-- .../cassandra/core/EntityQueryUtilsUnitTests.java | 10 ++++++++++ 3 files changed, 28 insertions(+), 5 deletions(-) diff --git a/spring-data-cassandra/src/main/java/org/springframework/data/cassandra/core/EntityQueryUtils.java b/spring-data-cassandra/src/main/java/org/springframework/data/cassandra/core/EntityQueryUtils.java index 42bc978a2..e668de1e9 100644 --- a/spring-data-cassandra/src/main/java/org/springframework/data/cassandra/core/EntityQueryUtils.java +++ b/spring-data-cassandra/src/main/java/org/springframework/data/cassandra/core/EntityQueryUtils.java @@ -230,7 +230,7 @@ class EntityQueryUtils { String table = (String) accessor.getPropertyValue("table"); if (table != null) { - return CqlIdentifier.of(table); + return CqlIdentifier.isQuotedIdentifier(table) ? CqlIdentifier.quoted(unquote(table)) : CqlIdentifier.of(table); } } @@ -240,8 +240,8 @@ class EntityQueryUtils { if (matcher.find()) { String cqlTableName = matcher.group(1); - if (cqlTableName.startsWith("\"")) { - return CqlIdentifier.quoted(cqlTableName.substring(1, cqlTableName.length() - 1)); + if (CqlIdentifier.isQuotedIdentifier(cqlTableName)) { + return CqlIdentifier.quoted(unquote(cqlTableName)); } int separator = cqlTableName.indexOf('.'); @@ -335,4 +335,8 @@ class EntityQueryUtils { return delete; } + + private static String unquote(String identifier) { + return identifier.substring(1, identifier.length() - 1); + } } diff --git a/spring-data-cassandra/src/main/java/org/springframework/data/cassandra/core/cql/CqlIdentifier.java b/spring-data-cassandra/src/main/java/org/springframework/data/cassandra/core/cql/CqlIdentifier.java index 38ee27e76..041ba22c4 100644 --- a/spring-data-cassandra/src/main/java/org/springframework/data/cassandra/core/cql/CqlIdentifier.java +++ b/spring-data-cassandra/src/main/java/org/springframework/data/cassandra/core/cql/CqlIdentifier.java @@ -85,7 +85,7 @@ public final class CqlIdentifier implements Comparable, Serializa Assert.hasText(string, "Identifier must not be empty"); - if (forceQuote || isQuotedIdentifier(string)) { + if (forceQuote || requiresQuoting(string)) { this.unquoted = string; this.identifier = "\"" + string + "\""; this.quoted = true; @@ -165,9 +165,18 @@ public final class CqlIdentifier implements Comparable, Serializa } /** - * Returns {@code true} if the given {@link CharSequence} is a legal unquoted identifier. + * Returns {@code true} if the given {@link CharSequence} is an identifier with quotes. */ public static boolean isQuotedIdentifier(CharSequence chars) { + return chars != null && chars.length() > 1 && chars.charAt(0) == '"' && chars.charAt(chars.length() - 1) == '"'; + } + + /** + * Returns {@code true} if the given {@link CharSequence} requires quoting. + * + * @since 2.2 + */ + public static boolean requiresQuoting(CharSequence chars) { return QUOTED.matcher(chars).matches() || ReservedKeyword.isReserved(chars); } diff --git a/spring-data-cassandra/src/test/java/org/springframework/data/cassandra/core/EntityQueryUtilsUnitTests.java b/spring-data-cassandra/src/test/java/org/springframework/data/cassandra/core/EntityQueryUtilsUnitTests.java index 140ec2476..12d72472f 100644 --- a/spring-data-cassandra/src/test/java/org/springframework/data/cassandra/core/EntityQueryUtilsUnitTests.java +++ b/spring-data-cassandra/src/test/java/org/springframework/data/cassandra/core/EntityQueryUtilsUnitTests.java @@ -47,6 +47,16 @@ public class EntityQueryUtilsUnitTests { assertThat(tableName).isEqualTo(CqlIdentifier.of("table")); } + @Test // DATACASS-642 + public void shouldRetrieveQuotedTableNameFromSelect() { + + Select select = QueryBuilder.select().from("keyspace", "\"table\""); + + CqlIdentifier tableName = EntityQueryUtils.getTableName(select); + + assertThat(tableName).isEqualTo(CqlIdentifier.quoted("table")); + } + @Test // DATACASS-106 public void shouldRetrieveTableNameFromSimpleStatement() {