public SelectStatement(
     List<FromTableReference> tables,
     List<ExpressionNode> projExprs,
     ExpressionNode where,
     List<SortingSpecification> order,
     LimitSpecification limit,
     SetQuantifier setQuant,
     List<MysqlSelectOption> options,
     List<SortingSpecification> grouping,
     ExpressionNode havingExpr,
     Boolean locking,
     AliasInformation ai,
     SourceLocation loc) {
   super(loc);
   setAliases(ai);
   setTables(tables);
   setProjection(projExprs);
   setWhereClause(where);
   setOrderBy(order);
   setLimit(limit);
   setGroupBy(grouping);
   setHavingExpression(havingExpr);
   this.setQuantifier = setQuant;
   setSelectOptions(options);
   this.locking = locking;
 }
  protected SelectStatement buildAggCommand(SelectStatement in) {
    SelectStatement out = CopyVisitor.copy(in);
    // we're going to build
    // select Name, max(Engine), max(Version), max(Row_format),
    // sum(Rows), avg(Avg_row_length), sum(Data_length),
    // max(Max_data_length), sum(Index_length),
    // sum(Data_free), max(Auto_increment), min(Create_time),
    // max(Update_time), max(Check_time),
    // max(Collation), null /*Checksum*/, max(Create_options), max(Comment) from temp1 group by Name

    // eventually we will build another temp table of rewrite info (visible name, auto_inc values)
    // and join
    // but for now this is good enough

    List<ExpressionNode> proj = new ArrayList<ExpressionNode>();
    ExpressionAlias nameColumn = null;
    for (ExpressionNode en : out.getProjection()) {
      ExpressionAlias ea = (ExpressionAlias) en;
      ColumnInstance ci = (ColumnInstance) ea.getTarget();
      String cn = ci.getColumn().getName().getUnquotedName().get();
      FunctionCall fc = null;
      if (maxedColumns.contains(cn)) {
        fc = new FunctionCall(FunctionName.makeMax(), ci);
      } else if (summedColumns.contains(cn)) {
        fc = new FunctionCall(FunctionName.makeSum(), ci);
      } else if ("Name".equals(cn)) {
        fc = null;
        nameColumn = ea;
      } else if ("Avg_row_length".equals(cn)) {
        fc =
            new FunctionCall(
                FunctionName.makeRound(), new FunctionCall(FunctionName.makeAvg(), ci));
      } else if ("Create_time".equals(cn)) {
        fc = new FunctionCall(FunctionName.makeMin(), ci);
      } else if ("Checksum".equals(cn)) {
        fc = null;
        ea =
            new ExpressionAlias(
                LiteralExpression.makeNullLiteral(),
                new NameAlias(ci.getColumn().getName().getUnqualified()),
                false);
      } else {
        throw new SchemaException(Pass.PLANNER, "Unknown show status column: " + cn);
      }
      if (fc != null) {
        ea =
            new ExpressionAlias(
                fc, new NameAlias(ci.getColumn().getName().getUnqualified()), false);
      }
      proj.add(ea);
    }
    out.setProjection(proj);
    SortingSpecification ngb = new SortingSpecification(nameColumn.buildAliasInstance(), true);
    ngb.setOrdering(Boolean.FALSE);
    out.getGroupBysEdge().add(ngb);

    return out;
  }
 @Override
 public ProjectionInfo getProjectionMetadata(SchemaContext sc) {
   // we can't actually normalize yet - produces the wrong results for prepare
   if (projectionMetadata == null) {
     List<ExpressionNode> proj = getProjection();
     proj = expandWildcards(sc, proj);
     projectionMetadata = buildProjectionMetadata(sc, proj);
     setProjection(proj);
   }
   return projectionMetadata;
 }
 @Override
 public void normalize(SchemaContext pc) {
   // we've already resolved everything.  now we:
   // [1] expand all wildcards and table wildcards (except for count(*))
   //     this is easy for the projection - walk down the list and look for naked wildcards or
   //     table wildcards
   List<ExpressionNode> proj = getProjection();
   proj = expandWildcards(pc, proj);
   if (projectionMetadata == null || projectionMetadata.getWidth() != proj.size())
     projectionMetadata = buildProjectionMetadata(pc, proj);
   // [2] assign aliases for everything that does not already use an alias
   //     for the projection, this is easy - just walk down the list and anything that is
   //     not a DerivedColumn must need an alias
   proj = assignProjectionAliases(pc, proj, getAliases());
   setProjection(proj);
   // for order by, group by, etc. now that the projection aliases are set, use them in any clauses
   normalizeSorts(pc);
 }