NihalJain commented on code in PR #2024:
URL: https://github.com/apache/phoenix/pull/2024#discussion_r2047051616


##########
phoenix-core-client/src/main/java/org/apache/phoenix/compile/CreateTableCompiler.java:
##########
@@ -84,712 +87,689 @@
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
-import static 
org.apache.phoenix.jdbc.PhoenixDatabaseMetaData.SYSTEM_CHILD_LINK_NAMESPACE_BYTES;
-import static 
org.apache.phoenix.jdbc.PhoenixDatabaseMetaData.SYSTEM_CHILD_LINK_NAME_BYTES;
-import static 
org.apache.phoenix.query.QueryServices.DEFAULT_PHOENIX_UPDATABLE_VIEW_RESTRICTION_ENABLED;
-import static 
org.apache.phoenix.query.QueryServices.PHOENIX_UPDATABLE_VIEW_RESTRICTION_ENABLED;
-
+import org.apache.phoenix.thirdparty.com.google.common.collect.Iterators;
 
 public class CreateTableCompiler {
-    private static final Logger LOGGER = 
LoggerFactory.getLogger(CreateTableCompiler.class);
-    private static final PDatum VARBINARY_DATUM = new VarbinaryDatum();
-    private final PhoenixStatement statement;
-    private final Operation operation;
-    
-    public CreateTableCompiler(PhoenixStatement statement, Operation 
operation) {
-        this.statement = statement;
-        this.operation = operation;
-    }
-
-    public MutationPlan compile(CreateTableStatement create) throws 
SQLException {
-        final PhoenixConnection connection = statement.getConnection();
-        ColumnResolver resolver = FromCompiler.getResolverForCreation(create, 
connection);
-        PTableType type = create.getTableType();
-        PTable parentToBe = null;
-        ViewType viewTypeToBe = null;
-        Scan scan = new Scan();
-        final StatementContext context = new StatementContext(statement, 
resolver, scan, new SequenceManager(statement));
-        // TODO: support any statement for a VIEW instead of just a WHERE 
clause
-        ParseNode whereNode = create.getWhereClause();
-        String viewStatementToBe = null;
-        byte[][] viewColumnConstantsToBe = null;
-        BitSet isViewColumnReferencedToBe = null;
-        Set<PColumn> pkColumnsInWhere = new HashSet<>();
-        Set<PColumn> nonPkColumnsInWhere = new HashSet<>();
-        byte[] rowKeyMatcher = ByteUtil.EMPTY_BYTE_ARRAY;
-
-        // Check whether column families having local index column family 
suffix or not if present
-        // don't allow creating table.
-        // Also validate the default values expressions.
-        List<ColumnDef> columnDefs = create.getColumnDefs();
-        List<ColumnDef> overideColumnDefs = null;
-        PrimaryKeyConstraint pkConstraint = create.getPrimaryKeyConstraint();
-        for (int i = 0; i < columnDefs.size(); i++) {
-            ColumnDef columnDef = columnDefs.get(i);
-            if (columnDef.getColumnDefName().getFamilyName()!=null && 
columnDef.getColumnDefName().getFamilyName().contains(QueryConstants.LOCAL_INDEX_COLUMN_FAMILY_PREFIX))
 {
-                throw new 
SQLExceptionInfo.Builder(SQLExceptionCode.UNALLOWED_COLUMN_FAMILY)
-                        .build().buildException();
-            }
-            // False means we do not need the default (because it evaluated to 
null)
-            if (!columnDef.validateDefault(context, pkConstraint)) {
-                if (overideColumnDefs == null) {
-                    overideColumnDefs = new ArrayList<>(columnDefs);
-                }
-                overideColumnDefs.set(i, new ColumnDef(columnDef, null));
-            }
-        }
-        if (overideColumnDefs != null) {
-            create = new CreateTableStatement(create,overideColumnDefs);
-        }
-        final CreateTableStatement finalCreate = create;
-        
-        if (type == PTableType.VIEW) {
-            TableRef tableRef = resolver.getTables().get(0);
-            int nColumns = tableRef.getTable().getColumns().size();
-            isViewColumnReferencedToBe = new BitSet(nColumns);
-            // Used to track column references in a view
-            ExpressionCompiler expressionCompiler = new 
ColumnTrackingExpressionCompiler(context, isViewColumnReferencedToBe);
-            parentToBe = tableRef.getTable();
-
-            // Disallow creating views on top of SYSTEM tables. See 
PHOENIX-5386
-            if (parentToBe.getType() == PTableType.SYSTEM) {
-                throw new SQLExceptionInfo
-                        
.Builder(SQLExceptionCode.CANNOT_CREATE_VIEWS_ON_SYSTEM_TABLES)
-                        .build().buildException();
-            }
-            viewTypeToBe = parentToBe.getViewType() == ViewType.MAPPED ? 
ViewType.MAPPED : ViewType.UPDATABLE;
-            Expression where = null;
-            if (whereNode == null) {
-                if (parentToBe.getViewType() == ViewType.READ_ONLY) {
-                    viewTypeToBe = ViewType.READ_ONLY;
-                }
-                viewStatementToBe = parentToBe.getViewStatement();
-                if (viewStatementToBe != null) {
-                    SelectStatement select = new 
SQLParser(viewStatementToBe).parseQuery();
-                    whereNode = select.getWhere();
-                    where = whereNode.accept(expressionCompiler);
-                }
-            } else {
-                whereNode = StatementNormalizer.normalize(whereNode, resolver);
-                if (whereNode.isStateless()) {
-                    throw new 
SQLExceptionInfo.Builder(SQLExceptionCode.VIEW_WHERE_IS_CONSTANT)
-                        .build().buildException();
-                }
-                // If our parent has a VIEW statement, combine it with this one
-                if (parentToBe.getViewStatement() != null) {
-                    SelectStatement select = new 
SQLParser(parentToBe.getViewStatement()).parseQuery().combine(whereNode);
-                    whereNode = select.getWhere();
-                }
-                where = whereNode.accept(expressionCompiler);
-                if (where != null && !LiteralExpression.isTrue(where)) {
-                    TableName baseTableName = create.getBaseTableName();
-                    StringBuilder buf = new StringBuilder();
-                    whereNode.toSQL(resolver, buf);
-                    viewStatementToBe = 
QueryUtil.getViewStatement(baseTableName.getSchemaName(), 
baseTableName.getTableName(), buf.toString());
-                }
-                if (viewTypeToBe != ViewType.MAPPED) {
-                    viewColumnConstantsToBe = new byte[nColumns][];
-                    ViewWhereExpressionVisitor visitor = new 
ViewWhereExpressionVisitor(parentToBe, viewColumnConstantsToBe);
-                    where.accept(visitor);
-
-                    viewTypeToBe = visitor.isUpdatable() ? ViewType.UPDATABLE 
: ViewType.READ_ONLY;
-                    boolean updatableViewRestrictionEnabled = 
connection.getQueryServices()
-                            
.getProps().getBoolean(PHOENIX_UPDATABLE_VIEW_RESTRICTION_ENABLED,
-                                    
DEFAULT_PHOENIX_UPDATABLE_VIEW_RESTRICTION_ENABLED);
-                    if (viewTypeToBe == ViewType.UPDATABLE && 
updatableViewRestrictionEnabled) {
-                        ViewWhereExpressionValidatorVisitor validatorVisitor =
-                                new 
ViewWhereExpressionValidatorVisitor(parentToBe,
-                                        pkColumnsInWhere, nonPkColumnsInWhere);
-                        where.accept(validatorVisitor);
-                        if (!(connection.getQueryServices()
-                                instanceof ConnectionlessQueryServicesImpl)) {
-                            try {
-                                viewTypeToBe = setViewTypeToBe(connection, 
parentToBe,
-                                        pkColumnsInWhere, nonPkColumnsInWhere);
-                                LOGGER.info("VIEW type is set to {}. View 
Statement: {}, " +
-                                                "View Name: {}, " +
-                                                "Parent Table/View Name: {}",
-                                        viewTypeToBe, viewStatementToBe,
-                                        create.getTableName(), 
parentToBe.getName());
-                            } catch (IOException e) {
-                                throw new SQLException(e);
-                            }
-                        }
-                    }
-
-                    // If view is not updatable, viewColumnConstants should be 
empty. We will still
-                    // inherit our parent viewConstants, but we have no 
additional ones.
-                    if (viewTypeToBe != ViewType.UPDATABLE) {
-                        viewColumnConstantsToBe = null;
-                    }
-                }
-            }
-            if (viewTypeToBe == ViewType.MAPPED
-                    && parentToBe.getPKColumns().isEmpty()) {
-                validateCreateViewCompilation(connection, parentToBe,
-                    columnDefs, pkConstraint);
-            } else if (where != null && viewTypeToBe == ViewType.UPDATABLE) {
-                rowKeyMatcher = WhereOptimizer.getRowKeyMatcher(context, 
create.getTableName(),
-                        parentToBe, where);
-            }
-            verifyIfAnyParentHasIndexesAndViewExtendsPk(parentToBe, 
columnDefs, pkConstraint);
-        }
-        final ViewType viewType = viewTypeToBe;
-        final String viewStatement = viewStatementToBe;
-        final byte[][] viewColumnConstants = viewColumnConstantsToBe;
-        final BitSet isViewColumnReferenced = isViewColumnReferencedToBe;
-        List<ParseNode> splitNodes = create.getSplitNodes();
-        final byte[][] splits = new byte[splitNodes.size()][];
-        ImmutableBytesWritable ptr = context.getTempPtr();
-        ExpressionCompiler expressionCompiler = new 
ExpressionCompiler(context);
-        for (int i = 0; i < splits.length; i++) {
-            ParseNode node = splitNodes.get(i);
-            if (node instanceof BindParseNode) {
-                context.getBindManager().addParamMetaData((BindParseNode) 
node, VARBINARY_DATUM);
-            }
-            if (node.isStateless()) {
-                Expression expression = node.accept(expressionCompiler);
-                if (expression.evaluate(null, ptr)) {;
-                    splits[i] = ByteUtil.copyKeyBytesIfNecessary(ptr);
-                    continue;
-                }
+  private static final Logger LOGGER = 
LoggerFactory.getLogger(CreateTableCompiler.class);
+  private static final PDatum VARBINARY_DATUM = new VarbinaryDatum();
+  private final PhoenixStatement statement;
+  private final Operation operation;
+
+  public CreateTableCompiler(PhoenixStatement statement, Operation operation) {
+    this.statement = statement;
+    this.operation = operation;
+  }
+
+  public MutationPlan compile(CreateTableStatement create) throws SQLException 
{
+    final PhoenixConnection connection = statement.getConnection();
+    ColumnResolver resolver = FromCompiler.getResolverForCreation(create, 
connection);
+    PTableType type = create.getTableType();
+    PTable parentToBe = null;
+    ViewType viewTypeToBe = null;
+    Scan scan = new Scan();
+    final StatementContext context =
+      new StatementContext(statement, resolver, scan, new 
SequenceManager(statement));
+    // TODO: support any statement for a VIEW instead of just a WHERE clause
+    ParseNode whereNode = create.getWhereClause();
+    String viewStatementToBe = null;
+    byte[][] viewColumnConstantsToBe = null;
+    BitSet isViewColumnReferencedToBe = null;
+    Set<PColumn> pkColumnsInWhere = new HashSet<>();
+    Set<PColumn> nonPkColumnsInWhere = new HashSet<>();
+    byte[] rowKeyMatcher = ByteUtil.EMPTY_BYTE_ARRAY;
+
+    // Check whether column families having local index column family suffix 
or not if present
+    // don't allow creating table.
+    // Also validate the default values expressions.
+    List<ColumnDef> columnDefs = create.getColumnDefs();
+    List<ColumnDef> overideColumnDefs = null;
+    PrimaryKeyConstraint pkConstraint = create.getPrimaryKeyConstraint();
+    for (int i = 0; i < columnDefs.size(); i++) {
+      ColumnDef columnDef = columnDefs.get(i);
+      if (
+        columnDef.getColumnDefName().getFamilyName() != null && 
columnDef.getColumnDefName()
+          
.getFamilyName().contains(QueryConstants.LOCAL_INDEX_COLUMN_FAMILY_PREFIX)
+      ) {
+        throw new 
SQLExceptionInfo.Builder(SQLExceptionCode.UNALLOWED_COLUMN_FAMILY).build()
+          .buildException();
+      }
+      // False means we do not need the default (because it evaluated to null)
+      if (!columnDef.validateDefault(context, pkConstraint)) {
+        if (overideColumnDefs == null) {
+          overideColumnDefs = new ArrayList<>(columnDefs);
+        }
+        overideColumnDefs.set(i, new ColumnDef(columnDef, null));
+      }
+    }
+    if (overideColumnDefs != null) {
+      create = new CreateTableStatement(create, overideColumnDefs);
+    }
+    final CreateTableStatement finalCreate = create;
+
+    if (type == PTableType.VIEW) {
+      TableRef tableRef = resolver.getTables().get(0);
+      int nColumns = tableRef.getTable().getColumns().size();
+      isViewColumnReferencedToBe = new BitSet(nColumns);
+      // Used to track column references in a view
+      ExpressionCompiler expressionCompiler =
+        new ColumnTrackingExpressionCompiler(context, 
isViewColumnReferencedToBe);
+      parentToBe = tableRef.getTable();
+
+      // Disallow creating views on top of SYSTEM tables. See PHOENIX-5386
+      if (parentToBe.getType() == PTableType.SYSTEM) {
+        throw new 
SQLExceptionInfo.Builder(SQLExceptionCode.CANNOT_CREATE_VIEWS_ON_SYSTEM_TABLES)
+          .build().buildException();
+      }
+      viewTypeToBe =
+        parentToBe.getViewType() == ViewType.MAPPED ? ViewType.MAPPED : 
ViewType.UPDATABLE;
+      Expression where = null;
+      if (whereNode == null) {
+        if (parentToBe.getViewType() == ViewType.READ_ONLY) {
+          viewTypeToBe = ViewType.READ_ONLY;
+        }
+        viewStatementToBe = parentToBe.getViewStatement();
+        if (viewStatementToBe != null) {
+          SelectStatement select = new 
SQLParser(viewStatementToBe).parseQuery();
+          whereNode = select.getWhere();
+          where = whereNode.accept(expressionCompiler);
+        }
+      } else {
+        whereNode = StatementNormalizer.normalize(whereNode, resolver);
+        if (whereNode.isStateless()) {
+          throw new 
SQLExceptionInfo.Builder(SQLExceptionCode.VIEW_WHERE_IS_CONSTANT).build()
+            .buildException();
+        }
+        // If our parent has a VIEW statement, combine it with this one
+        if (parentToBe.getViewStatement() != null) {
+          SelectStatement select =
+            new 
SQLParser(parentToBe.getViewStatement()).parseQuery().combine(whereNode);
+          whereNode = select.getWhere();
+        }
+        where = whereNode.accept(expressionCompiler);
+        if (where != null && !LiteralExpression.isTrue(where)) {
+          TableName baseTableName = create.getBaseTableName();
+          StringBuilder buf = new StringBuilder();
+          whereNode.toSQL(resolver, buf);
+          viewStatementToBe = 
QueryUtil.getViewStatement(baseTableName.getSchemaName(),
+            baseTableName.getTableName(), buf.toString());
+        }
+        if (viewTypeToBe != ViewType.MAPPED) {
+          viewColumnConstantsToBe = new byte[nColumns][];
+          ViewWhereExpressionVisitor visitor =
+            new ViewWhereExpressionVisitor(parentToBe, 
viewColumnConstantsToBe);
+          where.accept(visitor);
+
+          viewTypeToBe = visitor.isUpdatable() ? ViewType.UPDATABLE : 
ViewType.READ_ONLY;
+          boolean updatableViewRestrictionEnabled = 
connection.getQueryServices().getProps()
+            .getBoolean(PHOENIX_UPDATABLE_VIEW_RESTRICTION_ENABLED,
+              DEFAULT_PHOENIX_UPDATABLE_VIEW_RESTRICTION_ENABLED);
+          if (viewTypeToBe == ViewType.UPDATABLE && 
updatableViewRestrictionEnabled) {
+            ViewWhereExpressionValidatorVisitor validatorVisitor =
+              new ViewWhereExpressionValidatorVisitor(parentToBe, 
pkColumnsInWhere,
+                nonPkColumnsInWhere);
+            where.accept(validatorVisitor);
+            if (!(connection.getQueryServices() instanceof 
ConnectionlessQueryServicesImpl)) {
+              try {
+                viewTypeToBe =
+                  setViewTypeToBe(connection, parentToBe, pkColumnsInWhere, 
nonPkColumnsInWhere);
+                LOGGER.info(
+                  "VIEW type is set to {}. View Statement: {}, " + "View Name: 
{}, "
+                    + "Parent Table/View Name: {}",
+                  viewTypeToBe, viewStatementToBe, create.getTableName(), 
parentToBe.getName());
+              } catch (IOException e) {
+                throw new SQLException(e);
+              }
             }
-            throw new 
SQLExceptionInfo.Builder(SQLExceptionCode.SPLIT_POINT_NOT_CONSTANT)
-                .setMessage("Node: " + node).build().buildException();
-        }
-        final MetaDataClient client = new MetaDataClient(connection);
-        final PTable parent = parentToBe;
-
-        return new CreateTableMutationPlan(context, client, finalCreate, 
splits, parent,
-                viewStatement, viewType, rowKeyMatcher,
-                viewColumnConstants, isViewColumnReferenced, connection);
-    }
-
-    /**
-     * Restrict view to be UPDATABLE if the view specification:
-     * 1. uses only the PK columns;
-     * 2. starts from the first PK column (ignore the prefix PK columns, 
TENANT_ID and/or
-     * _SALTED, if the parent table is multi-tenant and/or salted);
-     * 3. PK columns should be in the order they are defined;
-     * 4. uses the same set of PK columns as its sibling views' specification;
-     * Otherwise, mark the view as READ_ONLY.
-     *
-     * @param connection The client connection
-     * @param parentToBe To be parent for given view
-     * @param pkColumnsInWhere Set of primary key in where clause
-     * @param nonPkColumnsInWhere Set of non-primary key columns in where 
clause
-     * @throws IOException thrown if there is an error finding sibling views
-     * @throws SQLException
-     */
-    private ViewType setViewTypeToBe(final PhoenixConnection connection, final 
PTable parentToBe,
-                                     final Set<PColumn> pkColumnsInWhere,
-                                     final Set<PColumn> nonPkColumnsInWhere)
-            throws IOException, SQLException {
-        // 1. Check the view specification WHERE clause uses only the PK 
columns
-        if (!nonPkColumnsInWhere.isEmpty()) {
-            LOGGER.info("Setting the view type as READ_ONLY because the view 
statement contains " +
-                    "non-PK columns: {}", nonPkColumnsInWhere);
-            return ViewType.READ_ONLY;
-        }
-        if (pkColumnsInWhere.isEmpty()) {
-            return ViewType.UPDATABLE;
-        }
+          }
+
+          // If view is not updatable, viewColumnConstants should be empty. We 
will still
+          // inherit our parent viewConstants, but we have no additional ones.
+          if (viewTypeToBe != ViewType.UPDATABLE) {
+            viewColumnConstantsToBe = null;
+          }
+        }
+      }
+      if (viewTypeToBe == ViewType.MAPPED && 
parentToBe.getPKColumns().isEmpty()) {
+        validateCreateViewCompilation(connection, parentToBe, columnDefs, 
pkConstraint);
+      } else if (where != null && viewTypeToBe == ViewType.UPDATABLE) {
+        rowKeyMatcher =
+          WhereOptimizer.getRowKeyMatcher(context, create.getTableName(), 
parentToBe, where);
+      }
+      verifyIfAnyParentHasIndexesAndViewExtendsPk(parentToBe, columnDefs, 
pkConstraint);
+    }
+    final ViewType viewType = viewTypeToBe;
+    final String viewStatement = viewStatementToBe;
+    final byte[][] viewColumnConstants = viewColumnConstantsToBe;
+    final BitSet isViewColumnReferenced = isViewColumnReferencedToBe;
+    List<ParseNode> splitNodes = create.getSplitNodes();
+    final byte[][] splits = new byte[splitNodes.size()][];
+    ImmutableBytesWritable ptr = context.getTempPtr();
+    ExpressionCompiler expressionCompiler = new ExpressionCompiler(context);
+    for (int i = 0; i < splits.length; i++) {
+      ParseNode node = splitNodes.get(i);
+      if (node instanceof BindParseNode) {
+        context.getBindManager().addParamMetaData((BindParseNode) node, 
VARBINARY_DATUM);
+      }
+      if (node.isStateless()) {
+        Expression expression = node.accept(expressionCompiler);
+        if (expression.evaluate(null, ptr)) {
+          ;
+          splits[i] = ByteUtil.copyKeyBytesIfNecessary(ptr);
+          continue;
+        }
+      }
+      throw new 
SQLExceptionInfo.Builder(SQLExceptionCode.SPLIT_POINT_NOT_CONSTANT)
+        .setMessage("Node: " + node).build().buildException();
+    }
+    final MetaDataClient client = new MetaDataClient(connection);
+    final PTable parent = parentToBe;
+
+    return new CreateTableMutationPlan(context, client, finalCreate, splits, 
parent, viewStatement,
+      viewType, rowKeyMatcher, viewColumnConstants, isViewColumnReferenced, 
connection);
+  }
+
+  /**
+   * Restrict view to be UPDATABLE if the view specification: 1. uses only the 
PK columns; 2. starts

Review Comment:
   fix



-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: issues-unsubscr...@phoenix.apache.org

For queries about this service, please contact Infrastructure at:
us...@infra.apache.org

Reply via email to