You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@phoenix.apache.org by ri...@apache.org on 2022/01/11 15:31:14 UTC
[phoenix] branch master updated: PHOENIX-6596 Schema extraction double quotes expressions, resulting in un-executabe create statements
This is an automated email from the ASF dual-hosted git repository.
richardantal pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/phoenix.git
The following commit(s) were added to refs/heads/master by this push:
new faa5da8 PHOENIX-6596 Schema extraction double quotes expressions, resulting in un-executabe create statements
faa5da8 is described below
commit faa5da80a663fa916a4906142eb0eaf68da0cc53
Author: Richard Antal <an...@gmail.com>
AuthorDate: Thu Dec 9 14:00:08 2021 +0100
PHOENIX-6596 Schema extraction double quotes expressions, resulting in un-executabe create statements
Co-authored-by: Istvan Toth <st...@apache.org>
---
.../schema/tool/SchemaToolExtractionIT.java | 63 ++++++++++++++++++++--
.../schema/tool/SchemaExtractionProcessor.java | 28 ++++++++--
.../org/apache/phoenix/schema/tool/SchemaTool.java | 1 -
.../java/org/apache/phoenix/util/SchemaUtil.java | 23 ++++++++
4 files changed, 106 insertions(+), 9 deletions(-)
diff --git a/phoenix-core/src/it/java/org/apache/phoenix/schema/tool/SchemaToolExtractionIT.java b/phoenix-core/src/it/java/org/apache/phoenix/schema/tool/SchemaToolExtractionIT.java
index 6ba411c..0a733ae 100644
--- a/phoenix-core/src/it/java/org/apache/phoenix/schema/tool/SchemaToolExtractionIT.java
+++ b/phoenix-core/src/it/java/org/apache/phoenix/schema/tool/SchemaToolExtractionIT.java
@@ -93,13 +93,18 @@ public class SchemaToolExtractionIT extends ParallelStatsEnabledIT {
String indexName = generateUniqueName();
String indexName1 = generateUniqueName();
String indexName2 = generateUniqueName();
+ String indexName3 = generateUniqueName();
String properties = "TTL=2592000,IMMUTABLE_ROWS=true,DISABLE_WAL=true";
String pTableFullName = SchemaUtil.getQualifiedTableName(schemaName, tableName);
- String createTableStatement = "CREATE TABLE "+pTableFullName + "(k VARCHAR NOT NULL PRIMARY KEY, v1 VARCHAR, v2 VARCHAR)"
+ String createTableStatement = "CREATE TABLE "+pTableFullName + "(k VARCHAR NOT NULL PRIMARY KEY, \"v1\" VARCHAR, v2 VARCHAR)"
+ properties;
- String createIndexStatement = "CREATE INDEX "+indexName + " ON "+pTableFullName+"(v1 DESC) INCLUDE (v2)";
- String createIndexStatement1 = "CREATE INDEX "+indexName1 + " ON "+pTableFullName+"(v2 DESC) INCLUDE (v1)";
+ //FIXME never verified
+ String createIndexStatement = "CREATE INDEX "+indexName + " ON "+pTableFullName+"(\"v1\" DESC) INCLUDE (v2)";
+ //FIXME never verified
+ String createIndexStatement1 = "CREATE INDEX "+indexName1 + " ON "+pTableFullName+"(v2 DESC) INCLUDE (\"v1\")";
String createIndexStatement2 = "CREATE INDEX "+indexName2 + " ON "+pTableFullName+"(k)";
+ String createIndexStatement3 ="CREATE INDEX " + indexName3 + " ON " + pTableFullName +
+ "('QUOTED' || \"v1\" || V2 DESC, \"v1\" DESC, K) INCLUDE (V2)";
List<String> queries = new ArrayList<String>(){};
queries.add(createTableStatement);
queries.add(createIndexStatement);
@@ -108,6 +113,12 @@ public class SchemaToolExtractionIT extends ParallelStatsEnabledIT {
String result = runSchemaExtractionTool(schemaName, indexName2, null, queries);
Assert.assertEquals(createIndexStatement2.toUpperCase(), result.toUpperCase());
+
+ List<String> queries3 = new ArrayList<String>(){};
+ queries3.add(createIndexStatement3);
+
+ String result3 = runSchemaExtractionTool(schemaName, indexName3, null, queries3);
+ Assert.assertEquals(createIndexStatement3, result3);
}
@Test
@@ -144,17 +155,45 @@ public class SchemaToolExtractionIT extends ParallelStatsEnabledIT {
String tableName = generateUniqueName();
String schemaName = generateUniqueName();
String indexName = generateUniqueName();
+ String indexName2 = generateUniqueName();
String properties = "TTL=2592000,IMMUTABLE_ROWS=true,DISABLE_WAL=true";
String pTableFullName = SchemaUtil.getQualifiedTableName(schemaName, tableName);
String createTableStatement = "CREATE TABLE "+pTableFullName + "(k VARCHAR NOT NULL PRIMARY KEY, v1 VARCHAR, v2 VARCHAR)"
+ properties;
String createIndexStatement = "CREATE LOCAL INDEX "+indexName + " ON "+pTableFullName+"(v1 DESC, k) INCLUDE (v2)";
+ String createIndexStatement2 = "CREATE LOCAL INDEX "+indexName2 + " ON "+pTableFullName+"( LPAD(v1,10) DESC, k) INCLUDE (v2)";
+
List<String> queries = new ArrayList<String>(){};
queries.add(createTableStatement);
queries.add(createIndexStatement);
String result = runSchemaExtractionTool(schemaName, indexName, null, queries);
Assert.assertEquals(createIndexStatement.toUpperCase(), result.toUpperCase());
+
+ List<String> queries2 = new ArrayList<String>(){};
+ queries2.add(createIndexStatement2);
+
+ String result2 = runSchemaExtractionTool(schemaName, indexName2, null, queries2);
+ Assert.assertEquals(createIndexStatement2.toUpperCase(), result2.toUpperCase());
+ }
+
+ @Test
+ public void testCreateLocalIndexStatementLowerCase() throws Exception {
+ String tableName = generateUniqueName();
+ String schemaName = generateUniqueName();
+ String indexName = generateUniqueName();
+ String properties = "TTL=2592000,IMMUTABLE_ROWS=true,DISABLE_WAL=true";
+ String pTableFullName = SchemaUtil.getQualifiedTableName(schemaName, tableName);
+ String createTableStatement = "CREATE TABLE "+pTableFullName + "(K VARCHAR NOT NULL PRIMARY KEY, \"v1\" VARCHAR, V2 VARCHAR)"
+ + properties;
+ String createIndexStatement = "CREATE LOCAL INDEX "+indexName + " ON "+pTableFullName+"( LPAD(\"v1\",10) DESC, K) INCLUDE (V2)";
+
+ List<String> queries = new ArrayList<String>(){};
+ queries.add(createTableStatement);
+ queries.add(createIndexStatement);
+
+ String result = runSchemaExtractionTool(schemaName, indexName, null, queries);
+ Assert.assertEquals(createIndexStatement, result);
}
@Test
@@ -176,6 +215,24 @@ public class SchemaToolExtractionIT extends ParallelStatsEnabledIT {
}
@Test
+ public void testCreateIndexStatementLowerCaseCombined() throws Exception {
+ String tableName = "lowercase" + generateUniqueName();
+ String schemaName = "lowercase" + generateUniqueName();
+ String indexName = "\"lowercaseIND" + generateUniqueName() + "\"";
+ String properties = "TTL=2592000,IMMUTABLE_ROWS=true,DISABLE_WAL=true";
+ String pTableFullName = SchemaUtil.getEscapedTableName(schemaName, tableName);
+ String createTableStatement = "CREATE TABLE " + pTableFullName + "(ID varchar primary key, \"number\" integer, \"currency\" decimal(6,2), lista varchar[])"
+ + properties;
+ String createIndexStatement = "CREATE INDEX " + indexName + " ON "+ pTableFullName + "(\"number\" * \"currency\", ID) INCLUDE (LISTA)";
+ List<String> queries = new ArrayList<String>(){};
+ queries.add(createTableStatement);
+ queries.add(createIndexStatement);
+
+ String result = runSchemaExtractionTool("\"" + schemaName + "\"", indexName, null, queries);
+ Assert.assertEquals(createIndexStatement, result);
+ }
+
+ @Test
public void testCreateViewStatement() throws Exception {
String tableName = generateUniqueName();
String schemaName = generateUniqueName();
diff --git a/phoenix-core/src/main/java/org/apache/phoenix/schema/tool/SchemaExtractionProcessor.java b/phoenix-core/src/main/java/org/apache/phoenix/schema/tool/SchemaExtractionProcessor.java
index 6943b88..3ed37e6 100644
--- a/phoenix-core/src/main/java/org/apache/phoenix/schema/tool/SchemaExtractionProcessor.java
+++ b/phoenix-core/src/main/java/org/apache/phoenix/schema/tool/SchemaExtractionProcessor.java
@@ -138,8 +138,8 @@ public class SchemaExtractionProcessor implements SchemaProcessor {
StringBuilder indexedColumnsBuilder = new StringBuilder();
for (PColumn indexedColumn : indexPK) {
- String indexColumn = extractIndexColumn(indexedColumn.getName().getString(), defaultCF);
- if(indexColumn.equalsIgnoreCase(MetaDataUtil.VIEW_INDEX_ID_COLUMN_NAME)) {
+ String indexColumn = extractIndexColumn(indexedColumn.getExpressionStr(), defaultCF);
+ if (indexColumn == null) {
continue;
}
indexPKName.add(indexColumn);
@@ -187,21 +187,37 @@ public class SchemaExtractionProcessor implements SchemaProcessor {
}
private String extractIndexColumn(String columnName, String defaultCF) {
+ if (columnName == null) {
+ return null;
+ }
String [] columnNameSplit = columnName.split(":");
if(columnNameSplit[0].equals("") || columnNameSplit[0].equalsIgnoreCase(defaultCF) ||
(defaultCF.startsWith("L#") && columnNameSplit[0].equalsIgnoreCase(defaultCF.substring(2)))) {
- return SchemaUtil.formatColumnName(columnNameSplit[1]);
+ return formatColumnOrExpression(columnNameSplit[1]);
} else {
if (columnNameSplit.length > 1) {
String schema = SchemaUtil.formatSchemaName(columnNameSplit[0]);
String name = SchemaUtil.formatColumnName(columnNameSplit[1]);
return String.format("%s.%s", schema, name);
} else {
- return SchemaUtil.formatColumnName(columnNameSplit[0]);
+ return formatColumnOrExpression(columnNameSplit[0]);
}
}
}
+ private String formatColumnOrExpression(String columnOrExpression) {
+ if (columnOrExpression.startsWith("(")) {
+ //Expressions like (a*b) are always parenthesised
+ return columnOrExpression.substring(1, columnOrExpression.length()-1);
+ } else if (columnOrExpression.contains("(")) {
+ //Expressions like like func(a) are always have a parenthesis
+ return columnOrExpression;
+ } else {
+ //If there are no parentheses, this is a column name
+ return SchemaUtil.formatIndexColumnName(columnOrExpression);
+ }
+ }
+
private String getCoveredColumnsString(PTable indexPTable, String defaultCF) {
StringBuilder coveredColumnsBuilder = new StringBuilder();
List<PColumn> pkColumns = indexPTable.getColumns();
@@ -211,7 +227,9 @@ public class SchemaExtractionProcessor implements SchemaProcessor {
}
if(cc.getFamilyName()!=null) {
String indexColumn = extractIndexColumn(cc.getName().getString(), defaultCF);
- coveredColumnsBuilder.append(indexColumn);
+ if (indexColumn != null) {
+ coveredColumnsBuilder.append(indexColumn);
+ }
}
}
return coveredColumnsBuilder.toString();
diff --git a/phoenix-core/src/main/java/org/apache/phoenix/schema/tool/SchemaTool.java b/phoenix-core/src/main/java/org/apache/phoenix/schema/tool/SchemaTool.java
index f9bbd36..bacbc7c 100644
--- a/phoenix-core/src/main/java/org/apache/phoenix/schema/tool/SchemaTool.java
+++ b/phoenix-core/src/main/java/org/apache/phoenix/schema/tool/SchemaTool.java
@@ -17,7 +17,6 @@
*/
package org.apache.phoenix.schema.tool;
-import org.apache.hadoop.yarn.webapp.hamlet.HamletSpec;
import org.apache.phoenix.thirdparty.org.apache.commons.cli.CommandLine;
import org.apache.phoenix.thirdparty.org.apache.commons.cli.CommandLineParser;
import org.apache.phoenix.thirdparty.org.apache.commons.cli.DefaultParser;
diff --git a/phoenix-core/src/main/java/org/apache/phoenix/util/SchemaUtil.java b/phoenix-core/src/main/java/org/apache/phoenix/util/SchemaUtil.java
index 4254b5f..961aec6 100644
--- a/phoenix-core/src/main/java/org/apache/phoenix/util/SchemaUtil.java
+++ b/phoenix-core/src/main/java/org/apache/phoenix/util/SchemaUtil.java
@@ -1301,6 +1301,29 @@ public class SchemaUtil {
return name;
}
+ public static String formatIndexColumnName(String name) {
+ String[] splitName = name.split("\\.");
+ if(splitName.length < 2) {
+ if (!name.contains("\"")) {
+ if (quotesNeededForColumn(name)) {
+ name = "\"" + name + "\"";
+ }
+ return name;
+ } else if (name.startsWith("\"") && name.endsWith("\"")) {
+ if (quotesNeededForColumn(name.substring(1, name.length() - 1))) {
+ return name;
+ } else {
+ return name.substring(1, name.length() - 1);
+ }
+ } else {
+ return name;
+ }
+ } else {
+ return String.format("%s.%s", formatIndexColumnName(splitName[0]),
+ formatIndexColumnName(splitName[1]));
+ }
+ }
+
public static boolean containsLowerCase(String name) {
if (Strings.isNullOrEmpty(name)) {
return false;