asterixdb-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From ima...@apache.org
Subject [10/50] [abbrv] incubator-asterixdb git commit: Merge branch 'master' into hyracks-merge2
Date Thu, 07 Apr 2016 14:59:45 GMT
http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/8516517e/asterixdb/asterix-installer/src/test/resources/transactionts/queries/query_after_restart/external_index/external_index.2.ddl.aql
----------------------------------------------------------------------
diff --cc asterixdb/asterix-installer/src/test/resources/transactionts/queries/query_after_restart/external_index/external_index.2.ddl.aql
index 7aa1129,0000000..e6b7e21
mode 100644,000000..100644
--- a/asterixdb/asterix-installer/src/test/resources/transactionts/queries/query_after_restart/external_index/external_index.2.ddl.aql
+++ b/asterixdb/asterix-installer/src/test/resources/transactionts/queries/query_after_restart/external_index/external_index.2.ddl.aql
@@@ -1,42 -1,0 +1,46 @@@
 +/*
 + * Licensed to the Apache Software Foundation (ASF) under one
 + * or more contributor license agreements.  See the NOTICE file
 + * distributed with this work for additional information
 + * regarding copyright ownership.  The ASF licenses this file
 + * to you under the Apache License, Version 2.0 (the
 + * "License"); you may not use this file except in compliance
 + * with the License.  You may obtain a copy of the License at
 + *
 + *   http://www.apache.org/licenses/LICENSE-2.0
 + *
 + * Unless required by applicable law or agreed to in writing,
 + * software distributed under the License is distributed on an
 + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 + * KIND, either express or implied.  See the License for the
 + * specific language governing permissions and limitations
 + * under the License.
 + */
 +/*
 +* Description  : Create an external dataset that contains records stored with text hdfs file format.
 +                 Build an index over the external dataset age attribute
 +                 Perform a query over the dataset using the index.
 +* Expected Res : Success
 +* Date         : 3rd Jan 2014
 +*/
 +drop dataverse test if exists;
 +create dataverse test;
 +
 +use dataverse test;
 +
 +create type EmployeeType as closed {
 + id: int64,
 + name: string,
 + age: int64
 +};
 +
 +create external dataset EmployeeDataset(EmployeeType)
 +using hdfs
- (("hdfs"="hdfs://127.0.0.1:31888"),("path"="/asterix/external-indexing-test.txt"),("input-format"="text-input-format"),("format"="delimited-text"),("delimiter"="|"));
++(("hdfs"="hdfs://127.0.0.1:31888"),
++("path"="/asterix/external-indexing-test.txt"),
++("input-format"="text-input-format"),
++("format"="delimited-text"),
++("delimiter"="|"));
 +
 +create index EmployeeAgeIdx on EmployeeDataset(age);
 +

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/8516517e/asterixdb/asterix-installer/src/test/resources/transactionts/testsuite.xml
----------------------------------------------------------------------
diff --cc asterixdb/asterix-installer/src/test/resources/transactionts/testsuite.xml
index 0635e7c,0000000..0c12426
mode 100644,000000..100644
--- a/asterixdb/asterix-installer/src/test/resources/transactionts/testsuite.xml
+++ b/asterixdb/asterix-installer/src/test/resources/transactionts/testsuite.xml
@@@ -1,199 -1,0 +1,203 @@@
 +<!--
 + ! Licensed to the Apache Software Foundation (ASF) under one
 + ! or more contributor license agreements.  See the NOTICE file
 + ! distributed with this work for additional information
 + ! regarding copyright ownership.  The ASF licenses this file
 + ! to you under the Apache License, Version 2.0 (the
 + ! "License"); you may not use this file except in compliance
 + ! with the License.  You may obtain a copy of the License at
 + !
 + !   http://www.apache.org/licenses/LICENSE-2.0
 + !
 + ! Unless required by applicable law or agreed to in writing,
 + ! software distributed under the License is distributed on an
 + ! "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 + ! KIND, either express or implied.  See the License for the
 + ! specific language governing permissions and limitations
 + ! under the License.
 + !-->
 +<test-suite xmlns="urn:xml.testframework.asterix.apache.org" ResultOffsetPath="results" QueryOffsetPath="queries" QueryFileExtension=".aql">
- 
 +  <test-group name="query_after_restart">
 +      <test-case FilePath="query_after_restart">
++          <compilation-unit name="dataset-with-meta-record">
++              <output-dir compare="Text">dataset-with-meta-record</output-dir>
++          </compilation-unit>
++      </test-case>
++      <test-case FilePath="query_after_restart">
 +          <compilation-unit name="external_index">
 +              <output-dir compare="Text">external_index</output-dir>
 +          </compilation-unit>
 +      </test-case>
 +  </test-group>
 +  <test-group name="recover_after_abort">
 +
 +    <test-case FilePath="recover_after_abort">
 +      <compilation-unit name="primary_index_only">
 +        <output-dir compare="Text">primary_index_only</output-dir>
 +      </compilation-unit>
 +    </test-case>
 +
 +    <test-case FilePath="recover_after_abort">
 +      <compilation-unit name="primary_plus_default_secondary_index">
 +        <output-dir compare="Text">primary_plus_default_secondary_index</output-dir>
 +      </compilation-unit>
 +    </test-case>
 +
 +    <test-case FilePath="recover_after_abort">
 +      <compilation-unit name="primary_plus_rtree_index">
 +        <output-dir compare="Text">primary_plus_rtree_index</output-dir>
 +      </compilation-unit>
 +    </test-case>
 +
 +    <test-case FilePath="recover_after_abort">
 +      <compilation-unit name="primary_plus_keyword_secondary_index">
 +        <output-dir compare="Text">primary_plus_keyword_secondary_index</output-dir>
 +      </compilation-unit>
 +    </test-case>
 +
 +    <test-case FilePath="recover_after_abort">
 +      <compilation-unit name="primary_plus_ngram_index">
 +        <output-dir compare="Text">primary_plus_ngram_index</output-dir>
 +      </compilation-unit>
 +    </test-case>
 + 
 +	<test-case FilePath="recover_after_abort">
 +      <compilation-unit name="primary_plus_multiple_secondary_indices">
 +        <output-dir compare="Text">primary_plus_multiple_secondary_indices</output-dir>
 +      </compilation-unit>
 +    </test-case>
 +  
 +    <test-case FilePath="recover_after_abort">
 +      <compilation-unit name="temp_primary_index_only">
 +        <output-dir compare="Text">primary_index_only</output-dir>
 +        <expected-error>org.apache.hyracks.algebricks.common.exceptions.AlgebricksException</expected-error>
 +      </compilation-unit>
 +    </test-case>
 +
 +    <test-case FilePath="recover_after_abort">
 +      <compilation-unit name="temp_primary_plus_default_secondary_index">
 +        <output-dir compare="Text">primary_plus_default_secondary_index</output-dir>
 +        <expected-error>org.apache.hyracks.algebricks.common.exceptions.AlgebricksException</expected-error>
 +      </compilation-unit>
 +    </test-case>
 +
 +    <test-case FilePath="recover_after_abort">
 +      <compilation-unit name="temp_primary_plus_rtree_index">
 +        <output-dir compare="Text">primary_plus_rtree_index</output-dir>
 +        <expected-error>org.apache.hyracks.algebricks.common.exceptions.AlgebricksException</expected-error>
 +      </compilation-unit>
 +    </test-case>
 +
 +    <test-case FilePath="recover_after_abort">
 +      <compilation-unit name="temp_primary_plus_keyword_secondary_index">
 +        <output-dir compare="Text">primary_plus_keyword_secondary_index</output-dir>
 +        <expected-error>org.apache.hyracks.algebricks.common.exceptions.AlgebricksException: Could not find dataset Fragile in dataverse recovery</expected-error>
 +      </compilation-unit>
 +    </test-case>
 +
 +    <test-case FilePath="recover_after_abort">
 +      <compilation-unit name="temp_primary_plus_ngram_index">
 +        <output-dir compare="Text">primary_plus_ngram_index</output-dir>
 +        <expected-error>org.apache.hyracks.algebricks.common.exceptions.AlgebricksException</expected-error>
 +      </compilation-unit>
 +    </test-case>
 +
 +    <test-case FilePath="recover_after_abort">
 +      <compilation-unit name="primary_plus_multiple_secondary_indices"><!-- The only exception here is during the kill command which is in a different JVM, hence not caught -->
 +        <output-dir compare="Text">primary_plus_multiple_secondary_indices</output-dir>
 +        <!-- <expected-error>org.apache.hyracks.algebricks.common.exceptions.AlgebricksException</expected-error> -->
 +      </compilation-unit>
 +    </test-case>
 + </test-group>
 +
 + <test-group name="recovery_ddl">
 +
 +    <test-case FilePath="recovery_ddl">
 +      <compilation-unit name="dataverse_recovery">
 +        <output-dir compare="Text">dataverse_recovery</output-dir>
 +      </compilation-unit>
 +    </test-case>
 +
 +    <test-case FilePath="recovery_ddl">
 +      <compilation-unit name="datatype_recovery">
 +        <output-dir compare="Text">datatype_recovery</output-dir>
 +      </compilation-unit>
 +    </test-case>
 +
 +    <test-case FilePath="recovery_ddl">
 +      <compilation-unit name="dataset_recovery">
 +        <output-dir compare="Text">dataset_recovery</output-dir>
 +      </compilation-unit>
 +    </test-case>
 +
 +    <test-case FilePath="recovery_ddl">
 +      <compilation-unit name="secondary_index_recovery">
 +        <output-dir compare="Text">secondary_index_recovery</output-dir>
 +      </compilation-unit>
 +    </test-case>
 +
 +    <test-case FilePath="recovery_ddl">
 +      <compilation-unit name="load_after_recovery">
 +        <output-dir compare="Text">load_after_recovery</output-dir>
 +      </compilation-unit>
 +    </test-case>
 +
 +    <test-case FilePath="recovery_ddl">
 +      <compilation-unit name="insert_after_recovery">
 +        <output-dir compare="Text">insert_after_recovery</output-dir>
 +      </compilation-unit>
 +    </test-case>
 +
 +    <test-case FilePath="recovery_ddl">
 +      <compilation-unit name="delete_after_recovery">
 +        <output-dir compare="Text">delete_after_recovery</output-dir>
 +      </compilation-unit>
 +    </test-case>
 +
 +    <test-case FilePath="recovery_ddl">
 +      <compilation-unit name="function_recovery">
 +        <output-dir compare="Text">function_recovery</output-dir>
 +      </compilation-unit>
 +    </test-case>
 +
 +    <test-case FilePath="recovery_ddl">
 +      <compilation-unit name="temp_dataset_recovery">
 +        <output-dir compare="Text">dataset_recovery</output-dir>
 +        <!-- <expected-error>org.apache.hyracks.algebricks.common.exceptions.AlgebricksException</expected-error> -->
 +      </compilation-unit>
 +    </test-case>
 +
 +    <test-case FilePath="recovery_ddl">
 +      <compilation-unit name="temp_delete_after_recovery">
 +        <output-dir compare="Text">delete_after_recovery</output-dir>
 +        <expected-error>org.apache.hyracks.algebricks.common.exceptions.AlgebricksException: Cannot find dataset Fragile_raw in dataverse recovery</expected-error>
 +        <expected-error>org.apache.hyracks.algebricks.common.exceptions.AlgebricksException: Could not find dataset Fragile_raw in dataverse recovery</expected-error>
 +      </compilation-unit>
 +    </test-case>
 +
 +    <test-case FilePath="recovery_ddl">
 +      <compilation-unit name="temp_insert_after_recovery">
 +        <output-dir compare="Text">insert_after_recovery</output-dir>
 +        <expected-error>org.apache.hyracks.algebricks.common.exceptions.AlgebricksException</expected-error>
 +        <expected-error>org.apache.hyracks.algebricks.common.exceptions.AlgebricksException: Could not find dataset Fragile in dataverse recovery</expected-error>
 +      </compilation-unit>
 +    </test-case>
 +
 +    <test-case FilePath="recovery_ddl">
 +      <compilation-unit name="temp_load_after_recovery">
 +        <output-dir compare="Text">load_after_recovery</output-dir>
 +        <expected-error>org.apache.hyracks.algebricks.common.exceptions.AlgebricksException</expected-error>
 +        <expected-error>org.apache.hyracks.algebricks.common.exceptions.AlgebricksException: Could not find dataset Fragile_raw in dataverse recovery</expected-error>
 +      </compilation-unit>
 +    </test-case>
 +
 +    <test-case FilePath="recovery_ddl">
 +      <compilation-unit name="temp_secondary_index_recovery">
 +        <output-dir compare="Text">secondary_index_recovery</output-dir>
 +        <!-- <expected-error>org.apache.hyracks.algebricks.common.exceptions.AlgebricksException</expected-error> -->
 +      </compilation-unit>
 +    </test-case>
 + 
 +  </test-group>
 +
 +</test-suite>

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/8516517e/asterixdb/asterix-lang-common/pom.xml
----------------------------------------------------------------------
diff --cc asterixdb/asterix-lang-common/pom.xml
index d1a5f80,0000000..dd5035f
mode 100644,000000..100644
--- a/asterixdb/asterix-lang-common/pom.xml
+++ b/asterixdb/asterix-lang-common/pom.xml
@@@ -1,84 -1,0 +1,84 @@@
 +<!--
 + ! Licensed to the Apache Software Foundation (ASF) under one
 + ! or more contributor license agreements.  See the NOTICE file
 + ! distributed with this work for additional information
 + ! regarding copyright ownership.  The ASF licenses this file
 + ! to you under the Apache License, Version 2.0 (the
 + ! "License"); you may not use this file except in compliance
 + ! with the License.  You may obtain a copy of the License at
 + !
 + !   http://www.apache.org/licenses/LICENSE-2.0
 + !
 + ! Unless required by applicable law or agreed to in writing,
 + ! software distributed under the License is distributed on an
 + ! "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 + ! KIND, either express or implied.  See the License for the
 + ! specific language governing permissions and limitations
 + ! under the License.
 + !-->
 +<project
 +    xmlns="http://maven.apache.org/POM/4.0.0"
 +    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
 +    xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
 +    <modelVersion>4.0.0</modelVersion>
 +    <parent>
 +        <artifactId>apache-asterixdb</artifactId>
 +        <groupId>org.apache.asterix</groupId>
 +        <version>0.8.9-SNAPSHOT</version>
 +    </parent>
 +
 +    <licenses>
 +        <license>
 +            <name>Apache License, Version 2.0</name>
 +            <url>http://www.apache.org/licenses/LICENSE-2.0.txt</url>
 +            <distribution>repo</distribution>
 +            <comments>A business-friendly OSS license</comments>
 +        </license>
 +    </licenses>
 +
 +    <artifactId>asterix-lang-common</artifactId>
 +    <build>
 +        <plugins>
 +            <plugin>
 +                <groupId>org.codehaus.mojo</groupId>
 +                <artifactId>build-helper-maven-plugin</artifactId>
 +                <version>1.9</version>
 +                <executions>
 +                    <execution>
 +                        <id>add-source</id>
 +                        <phase>generate-sources</phase>
 +                        <goals>
 +                            <goal>add-source</goal>
 +                        </goals>
 +                        <configuration>
 +                            <sources>
 +                                <source>${project.build.directory}/generated-sources/javacc/</source>
 +                            </sources>
 +                        </configuration>
 +                    </execution>
 +                </executions>
 +            </plugin>
 +        </plugins>
 +    </build>
 +
 +    <dependencies>
 +        <dependency>
 +            <groupId>org.apache.asterix</groupId>
 +            <artifactId>asterix-common</artifactId>
 +            <version>0.8.9-SNAPSHOT</version>
 +            <scope>compile</scope>
 +        </dependency>
 +        <dependency>
 +            <groupId>org.apache.asterix</groupId>
 +            <artifactId>asterix-metadata</artifactId>
 +            <version>0.8.9-SNAPSHOT</version>
 +            <scope>compile</scope>
 +        </dependency>
 +        <dependency>
 +            <groupId>xerces</groupId>
-             <artifactId>xerces</artifactId>
-             <version>2.4.0</version>
++            <artifactId>xercesImpl</artifactId>
++            <version>2.9.1</version>
 +        </dependency>
 +    </dependencies>
 +
 +</project>

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/8516517e/asterixdb/asterix-lang-common/src/main/java/org/apache/asterix/lang/common/clause/GroupbyClause.java
----------------------------------------------------------------------
diff --cc asterixdb/asterix-lang-common/src/main/java/org/apache/asterix/lang/common/clause/GroupbyClause.java
index 50e0ae2,0000000..b5d78e2
mode 100644,000000..100644
--- a/asterixdb/asterix-lang-common/src/main/java/org/apache/asterix/lang/common/clause/GroupbyClause.java
+++ b/asterixdb/asterix-lang-common/src/main/java/org/apache/asterix/lang/common/clause/GroupbyClause.java
@@@ -1,131 -1,0 +1,143 @@@
 +/*
 + * Licensed to the Apache Software Foundation (ASF) under one
 + * or more contributor license agreements.  See the NOTICE file
 + * distributed with this work for additional information
 + * regarding copyright ownership.  The ASF licenses this file
 + * to you under the Apache License, Version 2.0 (the
 + * "License"); you may not use this file except in compliance
 + * with the License.  You may obtain a copy of the License at
 + *
 + *   http://www.apache.org/licenses/LICENSE-2.0
 + *
 + * Unless required by applicable law or agreed to in writing,
 + * software distributed under the License is distributed on an
 + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 + * KIND, either express or implied.  See the License for the
 + * specific language governing permissions and limitations
 + * under the License.
 + */
 +package org.apache.asterix.lang.common.clause;
 +
 +import java.util.ArrayList;
 +import java.util.List;
 +
 +import org.apache.asterix.common.exceptions.AsterixException;
 +import org.apache.asterix.lang.common.base.Clause;
 +import org.apache.asterix.lang.common.base.Expression;
 +import org.apache.asterix.lang.common.expression.GbyVariableExpressionPair;
 +import org.apache.asterix.lang.common.expression.VariableExpr;
 +import org.apache.asterix.lang.common.struct.Identifier;
 +import org.apache.asterix.lang.common.visitor.base.ILangVisitor;
 +import org.apache.hyracks.algebricks.common.utils.Pair;
 +
 +public class GroupbyClause implements Clause {
 +
 +    private List<GbyVariableExpressionPair> gbyPairList;
 +    private List<GbyVariableExpressionPair> decorPairList;
 +    private List<VariableExpr> withVarList;
 +    private VariableExpr groupVar;
 +    private List<Pair<Expression, Identifier>> groupFieldList = new ArrayList<Pair<Expression, Identifier>>();
 +    private boolean hashGroupByHint;
++    private boolean groupAll;
 +
 +    public GroupbyClause() {
 +    }
 +
 +    public GroupbyClause(List<GbyVariableExpressionPair> gbyPairList, List<GbyVariableExpressionPair> decorPairList,
 +            List<VariableExpr> withVarList, VariableExpr groupVarExpr,
 +            List<Pair<Expression, Identifier>> groupFieldList, boolean hashGroupByHint) {
++        this(gbyPairList, decorPairList, withVarList, groupVarExpr, groupFieldList, hashGroupByHint, false);
++    }
++
++    public GroupbyClause(List<GbyVariableExpressionPair> gbyPairList, List<GbyVariableExpressionPair> decorPairList,
++            List<VariableExpr> withVarList, VariableExpr groupVarExpr,
++            List<Pair<Expression, Identifier>> groupFieldList, boolean hashGroupByHint, boolean groupAll) {
 +        this.gbyPairList = gbyPairList;
 +        this.decorPairList = decorPairList;
 +        this.withVarList = withVarList;
 +        this.groupVar = groupVarExpr;
 +        if (groupFieldList != null) {
 +            this.groupFieldList = groupFieldList;
 +        }
 +        this.hashGroupByHint = hashGroupByHint;
++        this.groupAll = groupAll;
 +    }
 +
 +    public List<GbyVariableExpressionPair> getGbyPairList() {
 +        return gbyPairList;
 +    }
 +
 +    public void setGbyPairList(List<GbyVariableExpressionPair> vePairList) {
 +        this.gbyPairList = vePairList;
 +    }
 +
 +    public List<VariableExpr> getWithVarList() {
 +        return withVarList;
 +    }
 +
 +    public void setWithVarList(List<VariableExpr> withVarList) {
 +        this.withVarList = withVarList;
 +    }
 +
 +    public VariableExpr getGroupVar() {
 +        return groupVar;
 +    }
 +
 +    public void setGroupVar(VariableExpr groupVarExpr) {
 +        this.groupVar = groupVarExpr;
 +    }
 +
 +    public List<Pair<Expression, Identifier>> getGroupFieldList() {
 +        return groupFieldList;
 +    }
 +
 +    public void setGroupFieldList(List<Pair<Expression, Identifier>> groupFieldList) {
 +        this.groupFieldList = groupFieldList;
 +    }
 +
 +    @Override
 +    public ClauseType getClauseType() {
 +        return ClauseType.GROUP_BY_CLAUSE;
 +    }
 +
 +    @Override
 +    public <R, T> R accept(ILangVisitor<R, T> visitor, T arg) throws AsterixException {
 +        return visitor.visit(this, arg);
 +    }
 +
 +    public void setDecorPairList(List<GbyVariableExpressionPair> decorPairList) {
 +        this.decorPairList = decorPairList;
 +    }
 +
 +    public List<GbyVariableExpressionPair> getDecorPairList() {
 +        return decorPairList;
 +    }
 +
 +    public void setHashGroupByHint(boolean hashGroupByHint) {
 +        this.hashGroupByHint = hashGroupByHint;
 +    }
 +
 +    public boolean hasHashGroupByHint() {
 +        return hashGroupByHint;
 +    }
 +
 +    public boolean hasDecorList() {
 +        return decorPairList != null && decorPairList.size() > 0;
 +    }
 +
 +    public boolean hasWithList() {
 +        return withVarList != null && withVarList.size() > 0;
 +    }
 +
 +    public boolean hasGroupVar() {
 +        return groupVar != null;
 +    }
 +
 +    public boolean hasGroupFieldList() {
 +        return groupFieldList != null && groupFieldList.size() > 0;
 +    }
++
++    public boolean isGroupAll() {
++        return groupAll;
++    }
 +}

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/8516517e/asterixdb/asterix-lang-common/src/main/java/org/apache/asterix/lang/common/clause/LimitClause.java
----------------------------------------------------------------------
diff --cc asterixdb/asterix-lang-common/src/main/java/org/apache/asterix/lang/common/clause/LimitClause.java
index 451d7ef,0000000..7ebedc2
mode 100644,000000..100644
--- a/asterixdb/asterix-lang-common/src/main/java/org/apache/asterix/lang/common/clause/LimitClause.java
+++ b/asterixdb/asterix-lang-common/src/main/java/org/apache/asterix/lang/common/clause/LimitClause.java
@@@ -1,63 -1,0 +1,67 @@@
 +/*
 + * Licensed to the Apache Software Foundation (ASF) under one
 + * or more contributor license agreements.  See the NOTICE file
 + * distributed with this work for additional information
 + * regarding copyright ownership.  The ASF licenses this file
 + * to you under the Apache License, Version 2.0 (the
 + * "License"); you may not use this file except in compliance
 + * with the License.  You may obtain a copy of the License at
 + *
 + *   http://www.apache.org/licenses/LICENSE-2.0
 + *
 + * Unless required by applicable law or agreed to in writing,
 + * software distributed under the License is distributed on an
 + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 + * KIND, either express or implied.  See the License for the
 + * specific language governing permissions and limitations
 + * under the License.
 + */
 +package org.apache.asterix.lang.common.clause;
 +
 +import org.apache.asterix.common.exceptions.AsterixException;
 +import org.apache.asterix.lang.common.base.Clause;
 +import org.apache.asterix.lang.common.base.Expression;
 +import org.apache.asterix.lang.common.visitor.base.ILangVisitor;
 +
 +public class LimitClause implements Clause {
 +    private Expression limitexpr;
 +    private Expression offset;
 +
 +    public LimitClause() {
 +    }
 +
 +    public LimitClause(Expression limitexpr, Expression offset) {
 +        this.limitexpr = limitexpr;
 +        this.offset = offset;
 +    }
 +
 +    public Expression getLimitExpr() {
 +        return limitexpr;
 +    }
 +
 +    public void setLimitExpr(Expression limitexpr) {
 +        this.limitexpr = limitexpr;
 +    }
 +
 +    public Expression getOffset() {
 +        return offset;
 +    }
 +
 +    public void setOffset(Expression offset) {
 +        this.offset = offset;
 +    }
 +
++    public boolean hasOffset() {
++        return offset != null;
++    }
++
 +    @Override
 +    public ClauseType getClauseType() {
 +        return ClauseType.LIMIT_CLAUSE;
 +    }
 +
 +    @Override
 +    public <R, T> R accept(ILangVisitor<R, T> visitor, T arg) throws AsterixException {
 +        return visitor.visit(this, arg);
 +    }
 +}

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/8516517e/asterixdb/asterix-lang-common/src/main/java/org/apache/asterix/lang/common/expression/CallExpr.java
----------------------------------------------------------------------
diff --cc asterixdb/asterix-lang-common/src/main/java/org/apache/asterix/lang/common/expression/CallExpr.java
index 8cff0e8,0000000..c7d48b6
mode 100644,000000..100644
--- a/asterixdb/asterix-lang-common/src/main/java/org/apache/asterix/lang/common/expression/CallExpr.java
+++ b/asterixdb/asterix-lang-common/src/main/java/org/apache/asterix/lang/common/expression/CallExpr.java
@@@ -1,64 -1,0 +1,68 @@@
 +/*
 + * Licensed to the Apache Software Foundation (ASF) under one
 + * or more contributor license agreements.  See the NOTICE file
 + * distributed with this work for additional information
 + * regarding copyright ownership.  The ASF licenses this file
 + * to you under the Apache License, Version 2.0 (the
 + * "License"); you may not use this file except in compliance
 + * with the License.  You may obtain a copy of the License at
 + *
 + *   http://www.apache.org/licenses/LICENSE-2.0
 + *
 + * Unless required by applicable law or agreed to in writing,
 + * software distributed under the License is distributed on an
 + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 + * KIND, either express or implied.  See the License for the
 + * specific language governing permissions and limitations
 + * under the License.
 + */
 +package org.apache.asterix.lang.common.expression;
 +
 +import java.util.List;
 +
 +import org.apache.asterix.common.exceptions.AsterixException;
 +import org.apache.asterix.common.functions.FunctionSignature;
 +import org.apache.asterix.lang.common.base.AbstractExpression;
 +import org.apache.asterix.lang.common.base.Expression;
 +import org.apache.asterix.lang.common.visitor.base.ILangVisitor;
 +
 +public class CallExpr extends AbstractExpression {
-     private final FunctionSignature functionSignature;
++    private FunctionSignature functionSignature;
 +    private List<Expression> exprList;
 +    private boolean isBuiltin;
 +
 +    public CallExpr(FunctionSignature functionSignature, List<Expression> exprList) {
 +        this.functionSignature = functionSignature;
 +        this.exprList = exprList;
 +    }
 +
 +    public FunctionSignature getFunctionSignature() {
 +        return functionSignature;
 +    }
 +
 +    public List<Expression> getExprList() {
 +        return exprList;
 +    }
 +
 +    public boolean isBuiltin() {
 +        return isBuiltin;
 +    }
 +
 +    @Override
 +    public Kind getKind() {
 +        return Kind.CALL_EXPRESSION;
 +    }
 +
++    public void setFunctionSignature(FunctionSignature functionSignature) {
++        this.functionSignature = functionSignature;
++    }
++
 +    public void setExprList(List<Expression> exprList) {
 +        this.exprList = exprList;
 +    }
 +
 +    @Override
 +    public <R, T> R accept(ILangVisitor<R, T> visitor, T arg) throws AsterixException {
 +        return visitor.visit(this, arg);
 +    }
 +}

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/8516517e/asterixdb/asterix-lang-common/src/main/java/org/apache/asterix/lang/common/expression/OperatorExpr.java
----------------------------------------------------------------------
diff --cc asterixdb/asterix-lang-common/src/main/java/org/apache/asterix/lang/common/expression/OperatorExpr.java
index da7f59e,0000000..65422b2
mode 100644,000000..100644
--- a/asterixdb/asterix-lang-common/src/main/java/org/apache/asterix/lang/common/expression/OperatorExpr.java
+++ b/asterixdb/asterix-lang-common/src/main/java/org/apache/asterix/lang/common/expression/OperatorExpr.java
@@@ -1,144 -1,0 +1,147 @@@
 +/*
 + * Licensed to the Apache Software Foundation (ASF) under one
 + * or more contributor license agreements.  See the NOTICE file
 + * distributed with this work for additional information
 + * regarding copyright ownership.  The ASF licenses this file
 + * to you under the Apache License, Version 2.0 (the
 + * "License"); you may not use this file except in compliance
 + * with the License.  You may obtain a copy of the License at
 + *
 + *   http://www.apache.org/licenses/LICENSE-2.0
 + *
 + * Unless required by applicable law or agreed to in writing,
 + * software distributed under the License is distributed on an
 + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 + * KIND, either express or implied.  See the License for the
 + * specific language governing permissions and limitations
 + * under the License.
 + */
 +package org.apache.asterix.lang.common.expression;
 +
 +import java.util.ArrayList;
 +import java.util.List;
 +
 +import org.apache.asterix.common.exceptions.AsterixException;
 +import org.apache.asterix.lang.common.base.AbstractExpression;
 +import org.apache.asterix.lang.common.base.Expression;
 +import org.apache.asterix.lang.common.struct.OperatorType;
 +import org.apache.asterix.lang.common.visitor.base.ILangVisitor;
 +
 +public class OperatorExpr extends AbstractExpression {
 +    private List<Expression> exprList;
 +    private List<OperatorType> opList;
 +    private List<Integer> exprBroadcastIdx;
 +    private boolean currentop = false;
 +
 +    public OperatorExpr() {
 +        super();
 +        exprList = new ArrayList<Expression>();
 +        exprBroadcastIdx = new ArrayList<Integer>();
 +        opList = new ArrayList<OperatorType>();
 +    }
 +
-     public OperatorExpr(List<Expression> exprList, List<Integer> exprBroadcastIdx, List<OperatorType> opList) {
++    public OperatorExpr(List<Expression> exprList, List<Integer> exprBroadcastIdx, List<OperatorType> opList,
++            boolean currentop) {
 +        this.exprList = exprList;
 +        this.exprBroadcastIdx = exprBroadcastIdx;
 +        this.opList = opList;
++        this.currentop = currentop;
 +    }
 +
 +    public boolean isCurrentop() {
 +        return currentop;
 +    }
 +
 +    public void setCurrentop(boolean currentop) {
 +        this.currentop = currentop;
 +    }
 +
 +    public List<Expression> getExprList() {
 +        return exprList;
 +    }
 +
 +    public List<Integer> getExprBroadcastIdx() {
 +        return exprBroadcastIdx;
 +    }
 +
 +    public List<OperatorType> getOpList() {
 +        return opList;
 +    }
 +
 +    public void setExprList(List<Expression> exprList) {
 +        this.exprList = exprList;
 +    }
 +
 +    public void addOperand(Expression operand) {
 +        addOperand(operand, false);
 +    }
 +
 +    public void addOperand(Expression operand, boolean broadcast) {
 +        if (broadcast) {
 +            exprBroadcastIdx.add(exprList.size());
 +        }
 +        exprList.add(operand);
 +    }
 +
 +    public final static boolean opIsComparison(OperatorType t) {
 +        return t == OperatorType.EQ || t == OperatorType.NEQ || t == OperatorType.GT || t == OperatorType.GE
 +                || t == OperatorType.LT || t == OperatorType.LE;
 +    }
 +
 +    public void addOperator(String strOp) {
-         if ("or".equals(strOp))
++        if ("or".equals(strOp)) {
 +            opList.add(OperatorType.OR);
-         else if ("and".equals(strOp))
++        } else if ("and".equals(strOp)) {
 +            opList.add(OperatorType.AND);
-         else if ("<".equals(strOp))
++        } else if ("<".equals(strOp)) {
 +            opList.add(OperatorType.LT);
-         else if (">".equals(strOp))
++        } else if (">".equals(strOp)) {
 +            opList.add(OperatorType.GT);
-         else if ("<=".equals(strOp))
++        } else if ("<=".equals(strOp)) {
 +            opList.add(OperatorType.LE);
-         else if ("<=".equals(strOp))
++        } else if ("<=".equals(strOp)) {
 +            opList.add(OperatorType.LE);
-         else if (">=".equals(strOp))
++        } else if (">=".equals(strOp)) {
 +            opList.add(OperatorType.GE);
-         else if ("=".equals(strOp))
++        } else if ("=".equals(strOp)) {
 +            opList.add(OperatorType.EQ);
-         else if ("!=".equals(strOp))
++        } else if ("!=".equals(strOp)) {
 +            opList.add(OperatorType.NEQ);
-         else if ("+".equals(strOp))
++        } else if ("+".equals(strOp)) {
 +            opList.add(OperatorType.PLUS);
-         else if ("-".equals(strOp))
++        } else if ("-".equals(strOp)) {
 +            opList.add(OperatorType.MINUS);
-         else if ("*".equals(strOp))
++        } else if ("*".equals(strOp)) {
 +            opList.add(OperatorType.MUL);
-         else if ("/".equals(strOp))
++        } else if ("/".equals(strOp)) {
 +            opList.add(OperatorType.DIV);
-         else if ("%".equals(strOp))
++        } else if ("%".equals(strOp)) {
 +            opList.add(OperatorType.MOD);
-         else if ("^".equals(strOp))
++        } else if ("^".equals(strOp)) {
 +            opList.add(OperatorType.CARET);
-         else if ("idiv".equals(strOp))
++        } else if ("idiv".equals(strOp)) {
 +            opList.add(OperatorType.IDIV);
-         else if ("~=".equals(strOp))
++        } else if ("~=".equals(strOp)) {
 +            opList.add(OperatorType.FUZZY_EQ);
++        }
 +    }
 +
 +    @Override
 +    public Kind getKind() {
 +        return Kind.OP_EXPRESSION;
 +    }
 +
 +    @Override
 +    public <R, T> R accept(ILangVisitor<R, T> visitor, T arg) throws AsterixException {
 +        return visitor.visit(this, arg);
 +    }
 +
 +    public boolean isBroadcastOperand(int idx) {
 +        for (Integer i : exprBroadcastIdx) {
 +            if (i == idx) {
 +                return true;
 +            }
 +        }
 +        return false;
 +    }
 +}

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/8516517e/asterixdb/asterix-lang-common/src/main/java/org/apache/asterix/lang/common/statement/Query.java
----------------------------------------------------------------------
diff --cc asterixdb/asterix-lang-common/src/main/java/org/apache/asterix/lang/common/statement/Query.java
index ac7698d,0000000..64ca0c1
mode 100644,000000..100644
--- a/asterixdb/asterix-lang-common/src/main/java/org/apache/asterix/lang/common/statement/Query.java
+++ b/asterixdb/asterix-lang-common/src/main/java/org/apache/asterix/lang/common/statement/Query.java
@@@ -1,85 -1,0 +1,97 @@@
 +/*
 + * Licensed to the Apache Software Foundation (ASF) under one
 + * or more contributor license agreements.  See the NOTICE file
 + * distributed with this work for additional information
 + * regarding copyright ownership.  The ASF licenses this file
 + * to you under the Apache License, Version 2.0 (the
 + * "License"); you may not use this file except in compliance
 + * with the License.  You may obtain a copy of the License at
 + *
 + *   http://www.apache.org/licenses/LICENSE-2.0
 + *
 + * Unless required by applicable law or agreed to in writing,
 + * software distributed under the License is distributed on an
 + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 + * KIND, either express or implied.  See the License for the
 + * specific language governing permissions and limitations
 + * under the License.
 + */
 +package org.apache.asterix.lang.common.statement;
 +
 +import java.util.ArrayList;
 +import java.util.List;
 +
 +import org.apache.asterix.common.exceptions.AsterixException;
 +import org.apache.asterix.lang.common.base.Expression;
 +import org.apache.asterix.lang.common.base.Statement;
 +import org.apache.asterix.lang.common.visitor.base.ILangVisitor;
 +
 +public class Query implements Statement {
 +    private boolean topLevel = true;
 +    private Expression body;
 +    private int varCounter;
 +    private List<String> dataverses = new ArrayList<String>();
 +    private List<String> datasets = new ArrayList<String>();
 +
++    public Query() {
++
++    }
++
++    public Query(boolean topLevel, Expression body, int varCounter, List<String> dataverses, List<String> datasets) {
++        this.topLevel = topLevel;
++        this.body = body;
++        this.varCounter = varCounter;
++        this.dataverses.addAll(dataverses);
++        this.datasets.addAll(datasets);
++    }
++
 +    public Expression getBody() {
 +        return body;
 +    }
 +
 +    public void setBody(Expression body) {
 +        this.body = body;
 +    }
 +
 +    public int getVarCounter() {
 +        return varCounter;
 +    }
 +
 +    public void setVarCounter(int varCounter) {
 +        this.varCounter = varCounter;
 +    }
 +
 +    public void setTopLevel(boolean topLevel) {
 +        this.topLevel = topLevel;
 +    }
 +
 +    public boolean isTopLevel() {
 +        return topLevel;
 +    }
 +
 +    @Override
 +    public Kind getKind() {
 +        return Kind.QUERY;
 +    }
 +
 +    @Override
 +    public <R, T> R accept(ILangVisitor<R, T> visitor, T arg) throws AsterixException {
 +        return visitor.visit(this, arg);
 +    }
 +
 +    public void setDataverses(List<String> dataverses) {
 +        this.dataverses = dataverses;
 +    }
 +
 +    public void setDatasets(List<String> datasets) {
 +        this.datasets = datasets;
 +    }
 +
 +    public List<String> getDataverses() {
 +        return dataverses;
 +    }
 +
 +    public List<String> getDatasets() {
 +        return datasets;
 +    }
 +}

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/8516517e/asterixdb/asterix-lang-common/src/main/java/org/apache/asterix/lang/common/visitor/CloneAndSubstituteVariablesVisitor.java
----------------------------------------------------------------------
diff --cc asterixdb/asterix-lang-common/src/main/java/org/apache/asterix/lang/common/visitor/CloneAndSubstituteVariablesVisitor.java
index ebe266e,0000000..db55c0e
mode 100644,000000..100644
--- a/asterixdb/asterix-lang-common/src/main/java/org/apache/asterix/lang/common/visitor/CloneAndSubstituteVariablesVisitor.java
+++ b/asterixdb/asterix-lang-common/src/main/java/org/apache/asterix/lang/common/visitor/CloneAndSubstituteVariablesVisitor.java
@@@ -1,342 -1,0 +1,342 @@@
 +/*
 + * Licensed to the Apache Software Foundation (ASF) under one
 + * or more contributor license agreements.  See the NOTICE file
 + * distributed with this work for additional information
 + * regarding copyright ownership.  The ASF licenses this file
 + * to you under the Apache License, Version 2.0 (the
 + * "License"); you may not use this file except in compliance
 + * with the License.  You may obtain a copy of the License at
 + *
 + *   http://www.apache.org/licenses/LICENSE-2.0
 + *
 + * Unless required by applicable law or agreed to in writing,
 + * software distributed under the License is distributed on an
 + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 + * KIND, either express or implied.  See the License for the
 + * specific language governing permissions and limitations
 + * under the License.
 + */
 +package org.apache.asterix.lang.common.visitor;
 +
 +import java.util.ArrayList;
 +import java.util.LinkedList;
 +import java.util.List;
 +
 +import org.apache.asterix.common.exceptions.AsterixException;
 +import org.apache.asterix.lang.common.base.Expression;
 +import org.apache.asterix.lang.common.base.Expression.Kind;
 +import org.apache.asterix.lang.common.base.ILangExpression;
 +import org.apache.asterix.lang.common.clause.GroupbyClause;
 +import org.apache.asterix.lang.common.clause.LetClause;
 +import org.apache.asterix.lang.common.clause.LimitClause;
 +import org.apache.asterix.lang.common.clause.OrderbyClause;
 +import org.apache.asterix.lang.common.clause.WhereClause;
 +import org.apache.asterix.lang.common.expression.CallExpr;
 +import org.apache.asterix.lang.common.expression.FieldAccessor;
 +import org.apache.asterix.lang.common.expression.FieldBinding;
 +import org.apache.asterix.lang.common.expression.GbyVariableExpressionPair;
 +import org.apache.asterix.lang.common.expression.IfExpr;
 +import org.apache.asterix.lang.common.expression.IndexAccessor;
 +import org.apache.asterix.lang.common.expression.ListConstructor;
 +import org.apache.asterix.lang.common.expression.LiteralExpr;
 +import org.apache.asterix.lang.common.expression.OperatorExpr;
 +import org.apache.asterix.lang.common.expression.QuantifiedExpression;
 +import org.apache.asterix.lang.common.expression.RecordConstructor;
 +import org.apache.asterix.lang.common.expression.UnaryExpr;
 +import org.apache.asterix.lang.common.expression.VariableExpr;
 +import org.apache.asterix.lang.common.rewrites.LangRewritingContext;
 +import org.apache.asterix.lang.common.rewrites.VariableSubstitutionEnvironment;
 +import org.apache.asterix.lang.common.statement.FunctionDecl;
 +import org.apache.asterix.lang.common.statement.Query;
 +import org.apache.asterix.lang.common.struct.Identifier;
 +import org.apache.asterix.lang.common.struct.QuantifiedPair;
 +import org.apache.asterix.lang.common.struct.VarIdentifier;
 +import org.apache.asterix.lang.common.util.VariableCloneAndSubstitutionUtil;
 +import org.apache.asterix.lang.common.visitor.base.AbstractQueryExpressionVisitor;
 +import org.apache.hyracks.algebricks.common.utils.Pair;
 +
 +public class CloneAndSubstituteVariablesVisitor extends
 +        AbstractQueryExpressionVisitor<Pair<ILangExpression, VariableSubstitutionEnvironment>, VariableSubstitutionEnvironment> {
 +
 +    private LangRewritingContext context;
 +
 +    public CloneAndSubstituteVariablesVisitor(LangRewritingContext context) {
 +        this.context = context;
 +    }
 +
 +    @Override
 +    public Pair<ILangExpression, VariableSubstitutionEnvironment> visit(LetClause lc,
 +            VariableSubstitutionEnvironment env) throws AsterixException {
 +        Pair<ILangExpression, VariableSubstitutionEnvironment> p1 = lc.getBindingExpr().accept(this, env);
 +        VariableExpr varExpr = lc.getVarExpr();
 +        VariableExpr newVe = generateNewVariable(context, varExpr);
 +        LetClause newLet = new LetClause(newVe, (Expression) p1.first);
 +        return new Pair<ILangExpression, VariableSubstitutionEnvironment>(newLet,
 +                VariableCloneAndSubstitutionUtil.eliminateSubstFromList(lc.getVarExpr(), env));
 +    }
 +
 +    @Override
 +    public Pair<ILangExpression, VariableSubstitutionEnvironment> visit(GroupbyClause gc,
 +            VariableSubstitutionEnvironment env) throws AsterixException {
 +        VariableSubstitutionEnvironment newSubs = env;
 +        List<GbyVariableExpressionPair> newGbyList = VariableCloneAndSubstitutionUtil.substInVarExprPair(context,
 +                gc.getGbyPairList(), env, newSubs, this);
 +        List<GbyVariableExpressionPair> newDecorList = gc.hasDecorList() ? VariableCloneAndSubstitutionUtil
 +                .substInVarExprPair(context, gc.getDecorPairList(), env, newSubs, this)
 +                : new ArrayList<GbyVariableExpressionPair>();
 +
 +        VariableExpr newGroupVar = null;
 +        if (gc.hasGroupVar()) {
 +            newGroupVar = generateNewVariable(context, gc.getGroupVar());
 +        }
 +        List<VariableExpr> wList = new LinkedList<VariableExpr>();
 +        if (gc.hasWithList()) {
 +            for (VariableExpr w : gc.getWithVarList()) {
 +                VarIdentifier newVar = context.getRewrittenVar(w.getVar().getId());
 +                if (newVar == null) {
 +                    throw new AsterixException("Could not find a rewritten variable identifier for " + w);
 +                }
 +                VariableExpr newWithVar = new VariableExpr(newVar);
 +                wList.add(newWithVar);
 +            }
 +        }
 +        List<Pair<Expression, Identifier>> newGroupFieldList = new ArrayList<>();
 +        if (gc.hasGroupFieldList()) {
 +            for (Pair<Expression, Identifier> varId : gc.getGroupFieldList()) {
 +                Expression newExpr = (Expression) varId.first.accept(this, env).first;
 +                newGroupFieldList.add(new Pair<Expression, Identifier>(newExpr, varId.second));
 +            }
 +        }
 +        GroupbyClause newGroup = new GroupbyClause(newGbyList, newDecorList, wList, newGroupVar, newGroupFieldList,
-                 gc.hasHashGroupByHint());
++                gc.hasHashGroupByHint(), gc.isGroupAll());
 +        return new Pair<ILangExpression, VariableSubstitutionEnvironment>(newGroup, newSubs);
 +    }
 +
 +    @Override
 +    public Pair<ILangExpression, VariableSubstitutionEnvironment> visit(QuantifiedExpression qe,
 +            VariableSubstitutionEnvironment env) throws AsterixException {
 +        List<QuantifiedPair> oldPairs = qe.getQuantifiedList();
 +        List<QuantifiedPair> newPairs = new ArrayList<QuantifiedPair>(oldPairs.size());
 +        VariableSubstitutionEnvironment newSubs = env;
 +        for (QuantifiedPair t : oldPairs) {
 +            VariableExpr newVar = generateNewVariable(context, t.getVarExpr());
 +            newSubs = VariableCloneAndSubstitutionUtil.eliminateSubstFromList(newVar, newSubs);
 +            Pair<ILangExpression, VariableSubstitutionEnvironment> p1 = visitUnnesBindingExpression(t.getExpr(),
 +                    newSubs);
 +            QuantifiedPair t2 = new QuantifiedPair(newVar, (Expression) p1.first);
 +            newPairs.add(t2);
 +        }
 +        Pair<ILangExpression, VariableSubstitutionEnvironment> p2 = qe.getSatisfiesExpr().accept(this, newSubs);
 +        QuantifiedExpression qe2 = new QuantifiedExpression(qe.getQuantifier(), newPairs, (Expression) p2.first);
 +        return new Pair<ILangExpression, VariableSubstitutionEnvironment>(qe2, newSubs);
 +    }
 +
 +    @Override
 +    public Pair<ILangExpression, VariableSubstitutionEnvironment> visit(WhereClause wc,
 +            VariableSubstitutionEnvironment env) throws AsterixException {
 +        Pair<ILangExpression, VariableSubstitutionEnvironment> p1 = wc.getWhereExpr().accept(this, env);
 +        WhereClause newW = new WhereClause((Expression) p1.first);
 +        return new Pair<ILangExpression, VariableSubstitutionEnvironment>(newW, p1.second);
 +    }
 +
 +    @Override
 +    public Pair<ILangExpression, VariableSubstitutionEnvironment> visit(CallExpr pf,
 +            VariableSubstitutionEnvironment env) throws AsterixException {
 +        List<Expression> exprList = VariableCloneAndSubstitutionUtil.visitAndCloneExprList(pf.getExprList(), env, this);
 +        CallExpr f = new CallExpr(pf.getFunctionSignature(), exprList);
 +        return new Pair<ILangExpression, VariableSubstitutionEnvironment>(f, env);
 +    }
 +
 +    @Override
 +    public Pair<ILangExpression, VariableSubstitutionEnvironment> visit(FunctionDecl fd,
 +            VariableSubstitutionEnvironment env) throws AsterixException {
 +        List<VarIdentifier> newList = new ArrayList<VarIdentifier>(fd.getParamList().size());
 +        for (VarIdentifier vi : fd.getParamList()) {
 +            VariableExpr varExpr = new VariableExpr(vi);
 +            if (!env.constainsOldVar(varExpr)) {
 +                throw new AsterixException("Parameter " + vi + " does not appear in the substitution list.");
 +            }
 +            Expression newExpr = env.findSubstituion(varExpr);
 +            if (newExpr.getKind() != Kind.VARIABLE_EXPRESSION) {
 +                throw new AsterixException("Parameter " + vi + " cannot be substituted by a non-variable expression.");
 +            }
 +            newList.add(((VariableExpr) newExpr).getVar());
 +        }
 +
 +        Pair<ILangExpression, VariableSubstitutionEnvironment> p1 = fd.getFuncBody().accept(this, env);
 +        FunctionDecl newF = new FunctionDecl(fd.getSignature(), newList, (Expression) p1.first);
 +        return new Pair<ILangExpression, VariableSubstitutionEnvironment>(newF, env);
 +    }
 +
 +    @Override
 +    public Pair<ILangExpression, VariableSubstitutionEnvironment> visit(IfExpr ifexpr,
 +            VariableSubstitutionEnvironment env) throws AsterixException {
 +        Pair<ILangExpression, VariableSubstitutionEnvironment> p1 = ifexpr.getCondExpr().accept(this, env);
 +        Pair<ILangExpression, VariableSubstitutionEnvironment> p2 = ifexpr.getThenExpr().accept(this, env);
 +        Pair<ILangExpression, VariableSubstitutionEnvironment> p3 = ifexpr.getElseExpr().accept(this, env);
 +        IfExpr i = new IfExpr((Expression) p1.first, (Expression) p2.first, (Expression) p3.first);
 +        return new Pair<ILangExpression, VariableSubstitutionEnvironment>(i, env);
 +    }
 +
 +    @Override
 +    public Pair<ILangExpression, VariableSubstitutionEnvironment> visit(LimitClause lc,
 +            VariableSubstitutionEnvironment env) throws AsterixException {
 +        Pair<ILangExpression, VariableSubstitutionEnvironment> p1 = lc.getLimitExpr().accept(this, env);
 +        Pair<ILangExpression, VariableSubstitutionEnvironment> p2 = null;
 +        Expression lcOffsetExpr = lc.getOffset();
 +        if (lcOffsetExpr != null) {
 +            p2 = lcOffsetExpr.accept(this, env);
 +        } else {
 +            p2 = new Pair<ILangExpression, VariableSubstitutionEnvironment>(null, null);
 +        }
 +        LimitClause c = new LimitClause((Expression) p1.first, (Expression) p2.first);
 +        return new Pair<ILangExpression, VariableSubstitutionEnvironment>(c, env);
 +    }
 +
 +    @Override
 +    public Pair<ILangExpression, VariableSubstitutionEnvironment> visit(ListConstructor lc,
 +            VariableSubstitutionEnvironment env) throws AsterixException {
 +        List<Expression> oldExprList = lc.getExprList();
 +        List<Expression> exprs = VariableCloneAndSubstitutionUtil.visitAndCloneExprList(oldExprList, env, this);
 +        ListConstructor c = new ListConstructor(lc.getType(), exprs);
 +        return new Pair<ILangExpression, VariableSubstitutionEnvironment>(c, env);
 +    }
 +
 +    @Override
 +    public Pair<ILangExpression, VariableSubstitutionEnvironment> visit(LiteralExpr l,
 +            VariableSubstitutionEnvironment env) throws AsterixException {
 +        return new Pair<ILangExpression, VariableSubstitutionEnvironment>(l, env);
 +    }
 +
 +    @Override
 +    public Pair<ILangExpression, VariableSubstitutionEnvironment> visit(OperatorExpr op,
 +            VariableSubstitutionEnvironment env) throws AsterixException {
 +        List<Expression> oldExprList = op.getExprList();
 +        List<Expression> exprs = new ArrayList<Expression>(oldExprList.size());
 +        for (Expression e : oldExprList) {
 +            Pair<ILangExpression, VariableSubstitutionEnvironment> p1 = e.accept(this, env);
 +            exprs.add((Expression) p1.first);
 +        }
-         OperatorExpr oe = new OperatorExpr(exprs, op.getExprBroadcastIdx(), op.getOpList());
-         oe.setCurrentop(op.isCurrentop());
++        OperatorExpr oe = new OperatorExpr(exprs, op.getExprBroadcastIdx(), op.getOpList(), op.isCurrentop());
 +        return new Pair<ILangExpression, VariableSubstitutionEnvironment>(oe, env);
 +    }
 +
 +    @Override
 +    public Pair<ILangExpression, VariableSubstitutionEnvironment> visit(OrderbyClause oc,
 +            VariableSubstitutionEnvironment env) throws AsterixException {
 +        List<Expression> exprList = VariableCloneAndSubstitutionUtil.visitAndCloneExprList(oc.getOrderbyList(), env,
 +                this);
 +        OrderbyClause oc2 = new OrderbyClause(exprList, oc.getModifierList());
 +        oc2.setNumFrames(oc.getNumFrames());
 +        oc2.setNumTuples(oc.getNumTuples());
 +        oc2.setRangeMap(oc.getRangeMap());
 +        return new Pair<ILangExpression, VariableSubstitutionEnvironment>(oc2, env);
 +    }
 +
 +    @Override
 +    public Pair<ILangExpression, VariableSubstitutionEnvironment> visit(Query q, VariableSubstitutionEnvironment env)
 +            throws AsterixException {
 +        Query newQ = new Query();
 +        Pair<ILangExpression, VariableSubstitutionEnvironment> p1 = q.getBody().accept(this, env);
 +        newQ.setBody((Expression) p1.first);
 +        return new Pair<ILangExpression, VariableSubstitutionEnvironment>(newQ, p1.second);
 +    }
 +
 +    @Override
 +    public Pair<ILangExpression, VariableSubstitutionEnvironment> visit(RecordConstructor rc,
 +            VariableSubstitutionEnvironment env) throws AsterixException {
 +        List<FieldBinding> oldFbs = rc.getFbList();
 +        ArrayList<FieldBinding> newFbs = new ArrayList<FieldBinding>(oldFbs.size());
 +        for (FieldBinding fb : oldFbs) {
 +            Pair<ILangExpression, VariableSubstitutionEnvironment> p1 = fb.getLeftExpr().accept(this, env);
 +            Pair<ILangExpression, VariableSubstitutionEnvironment> p2 = fb.getRightExpr().accept(this, env);
 +            FieldBinding fb2 = new FieldBinding((Expression) p1.first, (Expression) p2.first);
 +            newFbs.add(fb2);
 +        }
 +        RecordConstructor newRc = new RecordConstructor(newFbs);
 +        return new Pair<ILangExpression, VariableSubstitutionEnvironment>(newRc, env);
 +    }
 +
 +    @Override
 +    public Pair<ILangExpression, VariableSubstitutionEnvironment> visit(UnaryExpr u,
 +            VariableSubstitutionEnvironment env) throws AsterixException {
 +        Pair<ILangExpression, VariableSubstitutionEnvironment> p1 = u.getExpr().accept(this, env);
 +        UnaryExpr newU = new UnaryExpr(u.getSign(), (Expression) p1.first);
 +        return new Pair<ILangExpression, VariableSubstitutionEnvironment>(newU, env);
 +    }
 +
 +    @Override
 +    public Pair<ILangExpression, VariableSubstitutionEnvironment> visit(IndexAccessor ia,
 +            VariableSubstitutionEnvironment env) throws AsterixException {
 +        Pair<ILangExpression, VariableSubstitutionEnvironment> p1 = ia.getExpr().accept(this, env);
 +        Expression indexExpr = null;
 +        if (!ia.isAny()) {
 +            Pair<ILangExpression, VariableSubstitutionEnvironment> p2 = ia.getIndexExpr().accept(this, env);
 +            indexExpr = (Expression) p2.first;
 +        }
 +        IndexAccessor i = new IndexAccessor((Expression) p1.first, indexExpr);
 +        i.setAny(ia.isAny());
 +        return new Pair<ILangExpression, VariableSubstitutionEnvironment>(i, env);
 +    }
 +
 +    @Override
 +    public Pair<ILangExpression, VariableSubstitutionEnvironment> visit(FieldAccessor fa,
 +            VariableSubstitutionEnvironment env) throws AsterixException {
 +        Pair<ILangExpression, VariableSubstitutionEnvironment> p = fa.getExpr().accept(this, env);
 +        FieldAccessor newF = new FieldAccessor((Expression) p.first, fa.getIdent());
 +        return new Pair<ILangExpression, VariableSubstitutionEnvironment>(newF, p.second);
 +    }
 +
 +    @Override
 +    public Pair<ILangExpression, VariableSubstitutionEnvironment> visit(VariableExpr v,
 +            VariableSubstitutionEnvironment env) throws AsterixException {
 +        return new Pair<ILangExpression, VariableSubstitutionEnvironment>(rewriteVariableExpr(v, env), env);
 +    }
 +
 +    // Replace a variable expression if the variable is to-be substituted.
-     protected Expression rewriteVariableExpr(VariableExpr expr, VariableSubstitutionEnvironment env) {
++    protected Expression rewriteVariableExpr(VariableExpr expr, VariableSubstitutionEnvironment env)
++            throws AsterixException {
 +        if (env.constainsOldVar(expr)) {
 +            return env.findSubstituion(expr);
 +        } else {
 +            // it is a variable from the context
 +            VarIdentifier var = context.getRewrittenVar(expr.getVar().getId());
 +            if (var != null) {
 +                return new VariableExpr(var);
 +            }
 +        }
 +        return expr;
 +    }
 +
 +    /**
 +     * Generates a new variable for an existing variable.
 +     *
 +     * @param context
 +     *            , the language rewriting context which keeps all the rewriting variable-int-id to variable-string-identifier mappings.
 +     * @param varExpr
 +     *            , the existing variable expression.
 +     * @return the new variable expression.
 +     */
 +    public VariableExpr generateNewVariable(LangRewritingContext context, VariableExpr varExpr) {
 +        VarIdentifier vi = varExpr.getVar();
 +        VarIdentifier newVar = context.mapOldId(vi.getId(), vi.getValue());
 +        VariableExpr newVarExpr = new VariableExpr(newVar);
 +        return newVarExpr;
 +    }
 +
 +    /**
 +     * Visits an expression that is used for unnest binding.
 +     *
 +     * @param expr,
 +     *            the expression to consider.
 +     * @param env,
 +     *            the variable substitution environment.
 +     * @return a pair of an ILangExpression and a variable substitution environment.
 +     * @throws AsterixException
 +     */
 +    protected Pair<ILangExpression, VariableSubstitutionEnvironment> visitUnnesBindingExpression(Expression expr,
 +            VariableSubstitutionEnvironment env) throws AsterixException {
 +        return expr.accept(this, env);
 +    }
 +
 +}

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/8516517e/asterixdb/asterix-lang-sqlpp/src/main/java/org/apache/asterix/lang/sqlpp/clause/SelectBlock.java
----------------------------------------------------------------------
diff --cc asterixdb/asterix-lang-sqlpp/src/main/java/org/apache/asterix/lang/sqlpp/clause/SelectBlock.java
index 646e150,0000000..f63eced
mode 100644,000000..100644
--- a/asterixdb/asterix-lang-sqlpp/src/main/java/org/apache/asterix/lang/sqlpp/clause/SelectBlock.java
+++ b/asterixdb/asterix-lang-sqlpp/src/main/java/org/apache/asterix/lang/sqlpp/clause/SelectBlock.java
@@@ -1,115 -1,0 +1,119 @@@
 +/*
 + * Licensed to the Apache Software Foundation (ASF) under one
 + * or more contributor license agreements.  See the NOTICE file
 + * distributed with this work for additional information
 + * regarding copyright ownership.  The ASF licenses this file
 + * to you under the Apache License, Version 2.0 (the
 + * "License"); you may not use this file except in compliance
 + * with the License.  You may obtain a copy of the License at
 + *
 + *   http://www.apache.org/licenses/LICENSE-2.0
 + *
 + * Unless required by applicable law or agreed to in writing,
 + * software distributed under the License is distributed on an
 + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 + * KIND, either express or implied.  See the License for the
 + * specific language governing permissions and limitations
 + * under the License.
 + */
 +
 +package org.apache.asterix.lang.sqlpp.clause;
 +
 +import java.util.List;
 +
 +import org.apache.asterix.common.exceptions.AsterixException;
 +import org.apache.asterix.lang.common.base.Clause;
 +import org.apache.asterix.lang.common.clause.GroupbyClause;
 +import org.apache.asterix.lang.common.clause.LetClause;
 +import org.apache.asterix.lang.common.clause.WhereClause;
 +import org.apache.asterix.lang.common.visitor.base.ILangVisitor;
 +import org.apache.asterix.lang.sqlpp.visitor.base.ISqlppVisitor;
 +
 +public class SelectBlock implements Clause {
 +
 +    private SelectClause selectClause;
 +    private FromClause fromClause;
 +    private List<LetClause> letClauses;
 +    private WhereClause whereClause;
 +    private GroupbyClause groupbyClause;
 +    private List<LetClause> letClausesAfterGby;
 +    private HavingClause havingClause;
 +
 +    public SelectBlock(SelectClause selectClause, FromClause fromClause, List<LetClause> letClauses,
 +            WhereClause whereClause, GroupbyClause groupbyClause, List<LetClause> letClausesAfterGby,
 +            HavingClause havingClause) {
 +        this.selectClause = selectClause;
 +        this.fromClause = fromClause;
 +        this.letClauses = letClauses;
 +        this.whereClause = whereClause;
 +        this.groupbyClause = groupbyClause;
 +        this.havingClause = havingClause;
 +        this.letClausesAfterGby = letClausesAfterGby;
 +    }
 +
 +    @Override
 +    public <R, T> R accept(ILangVisitor<R, T> visitor, T arg) throws AsterixException {
 +        return ((ISqlppVisitor<R, T>) visitor).visit(this, arg);
 +    }
 +
 +    @Override
 +    public ClauseType getClauseType() {
 +        return ClauseType.SELECT_BLOCK;
 +    }
 +
 +    public SelectClause getSelectClause() {
 +        return selectClause;
 +    }
 +
 +    public FromClause getFromClause() {
 +        return fromClause;
 +    }
 +
 +    public List<LetClause> getLetList() {
 +        return letClauses;
 +    }
 +
 +    public WhereClause getWhereClause() {
 +        return whereClause;
 +    }
 +
 +    public GroupbyClause getGroupbyClause() {
 +        return groupbyClause;
 +    }
 +
 +    public HavingClause getHavingClause() {
 +        return havingClause;
 +    }
 +
 +    public boolean hasFromClause() {
 +        return fromClause != null;
 +    }
 +
 +    public boolean hasLetClauses() {
 +        return letClauses != null && letClauses.size() > 0;
 +    }
 +
 +    public boolean hasWhereClause() {
 +        return whereClause != null;
 +    }
 +
 +    public boolean hasGroupbyClause() {
 +        return groupbyClause != null;
 +    }
 +
 +    public boolean hasLetClausesAfterGroupby() {
 +        return letClausesAfterGby != null && letClausesAfterGby.size() > 0;
 +    }
 +
 +    public List<LetClause> getLetListAfterGroupby() {
 +        return letClausesAfterGby;
 +    }
 +
 +    public boolean hasHavingClause() {
 +        return havingClause != null;
 +    }
++
++    public void setGroupbyClause(GroupbyClause groupbyClause) {
++        this.groupbyClause = groupbyClause;
++    }
 +}

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/8516517e/asterixdb/asterix-lang-sqlpp/src/main/java/org/apache/asterix/lang/sqlpp/rewrites/SqlppFunctionBodyRewriter.java
----------------------------------------------------------------------
diff --cc asterixdb/asterix-lang-sqlpp/src/main/java/org/apache/asterix/lang/sqlpp/rewrites/SqlppFunctionBodyRewriter.java
index 1f119ae,0000000..01b9b54
mode 100644,000000..100644
--- a/asterixdb/asterix-lang-sqlpp/src/main/java/org/apache/asterix/lang/sqlpp/rewrites/SqlppFunctionBodyRewriter.java
+++ b/asterixdb/asterix-lang-sqlpp/src/main/java/org/apache/asterix/lang/sqlpp/rewrites/SqlppFunctionBodyRewriter.java
@@@ -1,50 -1,0 +1,53 @@@
 +/*
 + * Licensed to the Apache Software Foundation (ASF) under one
 + * or more contributor license agreements.  See the NOTICE file
 + * distributed with this work for additional information
 + * regarding copyright ownership.  The ASF licenses this file
 + * to you under the Apache License, Version 2.0 (the
 + * "License"); you may not use this file except in compliance
 + * with the License.  You may obtain a copy of the License at
 + *
 + *   http://www.apache.org/licenses/LICENSE-2.0
 + *
 + * Unless required by applicable law or agreed to in writing,
 + * software distributed under the License is distributed on an
 + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 + * KIND, either express or implied.  See the License for the
 + * specific language governing permissions and limitations
 + * under the License.
 + */
 +package org.apache.asterix.lang.sqlpp.rewrites;
 +
 +import java.util.List;
 +
 +import org.apache.asterix.common.exceptions.AsterixException;
 +import org.apache.asterix.lang.common.rewrites.LangRewritingContext;
 +import org.apache.asterix.lang.common.statement.FunctionDecl;
 +import org.apache.asterix.lang.common.statement.Query;
 +import org.apache.asterix.metadata.declared.AqlMetadataProvider;
 +
 +class SqlppFunctionBodyRewriter extends SqlppQueryRewriter {
 +
 +    @Override
 +    public void rewrite(List<FunctionDecl> declaredFunctions, Query topExpr, AqlMetadataProvider metadataProvider,
 +            LangRewritingContext context) throws AsterixException {
 +        // Sets up parameters.
 +        setup(declaredFunctions, topExpr, metadataProvider, context);
 +
 +        // Inlines column aliases.
 +        inlineColumnAlias();
 +
++        // Rewrites SQL-92 global aggregations.
++        rewriteGlobalAggregations();
++
 +        // Group-by core/sugar rewrites.
 +        rewriteGroupBys();
 +
 +        // Generates ids for variables (considering scopes) but DOES NOT replace unbounded variable access with the dataset function.
 +        // An unbounded variable within a function could be a bounded variable in the top-level query.
 +        variableCheckAndRewrite(false);
 +
 +        // Inlines functions recursively.
 +        inlineDeclaredUdfs();
 +    }
 +}

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/8516517e/asterixdb/asterix-lang-sqlpp/src/main/java/org/apache/asterix/lang/sqlpp/rewrites/SqlppQueryRewriter.java
----------------------------------------------------------------------
diff --cc asterixdb/asterix-lang-sqlpp/src/main/java/org/apache/asterix/lang/sqlpp/rewrites/SqlppQueryRewriter.java
index a2c84ba,0000000..f9a7183
mode 100644,000000..100644
--- a/asterixdb/asterix-lang-sqlpp/src/main/java/org/apache/asterix/lang/sqlpp/rewrites/SqlppQueryRewriter.java
+++ b/asterixdb/asterix-lang-sqlpp/src/main/java/org/apache/asterix/lang/sqlpp/rewrites/SqlppQueryRewriter.java
@@@ -1,340 -1,0 +1,369 @@@
 +/*
 + * Licensed to the Apache Software Foundation (ASF) under one
 + * or more contributor license agreements.  See the NOTICE file
 + * distributed with this work for additional information
 + * regarding copyright ownership.  The ASF licenses this file
 + * to you under the Apache License, Version 2.0 (the
 + * "License"); you may not use this file except in compliance
 + * with the License.  You may obtain a copy of the License at
 + *
 + *   http://www.apache.org/licenses/LICENSE-2.0
 + *
 + * Unless required by applicable law or agreed to in writing,
 + * software distributed under the License is distributed on an
 + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 + * KIND, either express or implied.  See the License for the
 + * specific language governing permissions and limitations
 + * under the License.
 + */
 +package org.apache.asterix.lang.sqlpp.rewrites;
 +
 +import java.util.ArrayList;
 +import java.util.List;
 +import java.util.Set;
 +
 +import org.apache.asterix.common.exceptions.AsterixException;
 +import org.apache.asterix.common.functions.FunctionSignature;
 +import org.apache.asterix.lang.common.base.Expression;
 +import org.apache.asterix.lang.common.base.IQueryRewriter;
 +import org.apache.asterix.lang.common.clause.LetClause;
 +import org.apache.asterix.lang.common.rewrites.LangRewritingContext;
 +import org.apache.asterix.lang.common.statement.FunctionDecl;
 +import org.apache.asterix.lang.common.statement.Query;
 +import org.apache.asterix.lang.common.util.FunctionUtil;
 +import org.apache.asterix.lang.common.visitor.GatherFunctionCallsVisitor;
 +import org.apache.asterix.lang.sqlpp.clause.AbstractBinaryCorrelateClause;
 +import org.apache.asterix.lang.sqlpp.clause.FromClause;
 +import org.apache.asterix.lang.sqlpp.clause.FromTerm;
 +import org.apache.asterix.lang.sqlpp.clause.HavingClause;
 +import org.apache.asterix.lang.sqlpp.clause.JoinClause;
 +import org.apache.asterix.lang.sqlpp.clause.NestClause;
 +import org.apache.asterix.lang.sqlpp.clause.Projection;
 +import org.apache.asterix.lang.sqlpp.clause.SelectBlock;
 +import org.apache.asterix.lang.sqlpp.clause.SelectClause;
 +import org.apache.asterix.lang.sqlpp.clause.SelectElement;
 +import org.apache.asterix.lang.sqlpp.clause.SelectRegular;
 +import org.apache.asterix.lang.sqlpp.clause.SelectSetOperation;
 +import org.apache.asterix.lang.sqlpp.clause.UnnestClause;
 +import org.apache.asterix.lang.sqlpp.expression.SelectExpression;
 +import org.apache.asterix.lang.sqlpp.parser.FunctionParser;
 +import org.apache.asterix.lang.sqlpp.parser.SqlppParserFactory;
++import org.apache.asterix.lang.sqlpp.rewrites.visitor.InlineColumnAliasVisitor;
++import org.apache.asterix.lang.sqlpp.rewrites.visitor.SqlppBuiltinFunctionRewriteVisitor;
++import org.apache.asterix.lang.sqlpp.rewrites.visitor.SqlppGlobalAggregationSugarVisitor;
++import org.apache.asterix.lang.sqlpp.rewrites.visitor.SqlppGroupByVisitor;
++import org.apache.asterix.lang.sqlpp.rewrites.visitor.SqlppInlineUdfsVisitor;
++import org.apache.asterix.lang.sqlpp.rewrites.visitor.VariableCheckAndRewriteVisitor;
 +import org.apache.asterix.lang.sqlpp.struct.SetOperationRight;
- import org.apache.asterix.lang.sqlpp.visitor.InlineColumnAliasVisitor;
- import org.apache.asterix.lang.sqlpp.visitor.SqlppGroupByVisitor;
- import org.apache.asterix.lang.sqlpp.visitor.SqlppInlineUdfsVisitor;
- import org.apache.asterix.lang.sqlpp.visitor.VariableCheckAndRewriteVisitor;
++import org.apache.asterix.lang.sqlpp.util.FunctionMapUtil;
 +import org.apache.asterix.lang.sqlpp.visitor.base.ISqlppVisitor;
 +import org.apache.asterix.metadata.MetadataManager;
 +import org.apache.asterix.metadata.MetadataTransactionContext;
 +import org.apache.asterix.metadata.declared.AqlMetadataProvider;
 +import org.apache.asterix.metadata.entities.Function;
 +import org.apache.asterix.om.functions.AsterixBuiltinFunctions;
 +
 +class SqlppQueryRewriter implements IQueryRewriter {
 +    private final FunctionParser functionRepository = new FunctionParser(new SqlppParserFactory());
 +    private Query topExpr;
 +    private List<FunctionDecl> declaredFunctions;
 +    private LangRewritingContext context;
 +    private MetadataTransactionContext mdTxnCtx;
 +    private AqlMetadataProvider metadataProvider;
 +
 +    protected void setup(List<FunctionDecl> declaredFunctions, Query topExpr, AqlMetadataProvider metadataProvider,
 +            LangRewritingContext context) {
 +        this.topExpr = topExpr;
 +        this.context = context;
 +        this.declaredFunctions = declaredFunctions;
 +        this.mdTxnCtx = metadataProvider.getMetadataTxnContext();
 +        this.metadataProvider = metadataProvider;
 +    }
 +
 +    @Override
 +    public void rewrite(List<FunctionDecl> declaredFunctions, Query topExpr, AqlMetadataProvider metadataProvider,
 +            LangRewritingContext context) throws AsterixException {
 +        // Sets up parameters.
 +        setup(declaredFunctions, topExpr, metadataProvider, context);
 +
 +        // Inlines column aliases.
 +        inlineColumnAlias();
 +
++        // Rewrites SQL-92 global aggregations.
++        rewriteGlobalAggregations();
++
 +        // Group-by core/sugar rewrites.
 +        rewriteGroupBys();
 +
 +        // Generate ids for variables (considering scopes) and replace global variable access with the dataset function.
 +        variableCheckAndRewrite(true);
 +
 +        // Inlines functions.
 +        inlineDeclaredUdfs();
 +
++        // Rewrites function names.
++        // This should be done after inlineDeclaredUdfs() because user-defined function
++        // names could be case sensitive.
++        rewriteFunctionNames();
++
 +        // Replace global variable access with the dataset function for inlined expressions.
 +        variableCheckAndRewrite(true);
 +
 +        // Sets the var counter of the query.
 +        topExpr.setVarCounter(context.getVarCounter());
 +    }
 +
++    protected void rewriteGlobalAggregations() throws AsterixException {
++        if (topExpr == null) {
++            return;
++        }
++        SqlppGlobalAggregationSugarVisitor globalAggregationVisitor = new SqlppGlobalAggregationSugarVisitor();
++        globalAggregationVisitor.visit(topExpr, null);
++    }
++
++    protected void rewriteFunctionNames() throws AsterixException {
++        if (topExpr == null) {
++            return;
++        }
++        SqlppBuiltinFunctionRewriteVisitor functionNameMapVisitor = new SqlppBuiltinFunctionRewriteVisitor();
++        functionNameMapVisitor.visit(topExpr, null);
++    }
++
 +    protected void inlineColumnAlias() throws AsterixException {
 +        if (topExpr == null) {
 +            return;
 +        }
 +        // Inline column aliases.
 +        InlineColumnAliasVisitor inlineColumnAliasVisitor = new InlineColumnAliasVisitor(context);
 +        inlineColumnAliasVisitor.visit(topExpr, false);
 +    }
 +
 +    protected void variableCheckAndRewrite(boolean overwrite) throws AsterixException {
 +        if (topExpr == null) {
 +            return;
 +        }
 +        VariableCheckAndRewriteVisitor variableCheckAndRewriteVisitor = new VariableCheckAndRewriteVisitor(context,
 +                overwrite, metadataProvider);
 +        variableCheckAndRewriteVisitor.visit(topExpr, null);
 +    }
 +
 +    protected void rewriteGroupBys() throws AsterixException {
 +        if (topExpr == null) {
 +            return;
 +        }
-         SqlppGroupByVisitor groupByVisitor = new SqlppGroupByVisitor(context, metadataProvider);
++        SqlppGroupByVisitor groupByVisitor = new SqlppGroupByVisitor(context);
 +        groupByVisitor.visit(topExpr, null);
 +    }
 +
 +    protected void inlineDeclaredUdfs() throws AsterixException {
 +        if (topExpr == null) {
 +            return;
 +        }
 +        List<FunctionSignature> funIds = new ArrayList<FunctionSignature>();
 +        for (FunctionDecl fdecl : declaredFunctions) {
 +            funIds.add(fdecl.getSignature());
 +        }
 +
 +        List<FunctionDecl> otherFDecls = new ArrayList<FunctionDecl>();
 +        buildOtherUdfs(topExpr.getBody(), otherFDecls, funIds);
 +        declaredFunctions.addAll(otherFDecls);
 +        if (!declaredFunctions.isEmpty()) {
 +            SqlppInlineUdfsVisitor visitor = new SqlppInlineUdfsVisitor(context,
 +                    new SqlppFunctionBodyRewriterFactory() /* the rewriter for function bodies expressions*/,
 +                    declaredFunctions, metadataProvider);
 +            while (topExpr.accept(visitor, declaredFunctions)) {
 +                // loop until no more changes
 +            }
 +        }
 +        declaredFunctions.removeAll(otherFDecls);
 +    }
 +
 +    protected void buildOtherUdfs(Expression expression, List<FunctionDecl> functionDecls,
 +            List<FunctionSignature> declaredFunctions) throws AsterixException {
 +        if (expression == null) {
 +            return;
 +        }
 +        String value = metadataProvider.getConfig().get(FunctionUtil.IMPORT_PRIVATE_FUNCTIONS);
 +        boolean includePrivateFunctions = (value != null) ? Boolean.valueOf(value.toLowerCase()) : false;
 +        Set<FunctionSignature> functionCalls = getFunctionCalls(expression);
 +        for (FunctionSignature signature : functionCalls) {
 +
 +            if (declaredFunctions != null && declaredFunctions.contains(signature)) {
 +                continue;
 +            }
 +
 +            Function function = lookupUserDefinedFunctionDecl(signature);
 +            if (function == null) {
-                 if (AsterixBuiltinFunctions.isBuiltinCompilerFunction(signature, includePrivateFunctions)) {
++                FunctionSignature normalizedSignature = FunctionMapUtil.normalizeBuiltinFunctionSignature(signature,
++                        false);
++                if (AsterixBuiltinFunctions.isBuiltinCompilerFunction(normalizedSignature, includePrivateFunctions)) {
 +                    continue;
 +                }
 +                StringBuilder messageBuilder = new StringBuilder();
 +                if (functionDecls.size() > 0) {
 +                    messageBuilder.append(" function " + functionDecls.get(functionDecls.size() - 1).getSignature()
 +                            + " depends upon function " + signature + " which is undefined");
 +                } else {
 +                    messageBuilder.append(" function " + signature + " is undefined ");
 +                }
 +                throw new AsterixException(messageBuilder.toString());
 +            }
 +
 +            if (function.getLanguage().equalsIgnoreCase(Function.LANGUAGE_AQL)) {
 +                FunctionDecl functionDecl = functionRepository.getFunctionDecl(function);
 +                if (functionDecl != null) {
 +                    if (functionDecls.contains(functionDecl)) {
 +                        throw new AsterixException("ERROR:Recursive invocation "
 +                                + functionDecls.get(functionDecls.size() - 1).getSignature() + " <==> "
 +                                + functionDecl.getSignature());
 +                    }
 +                    functionDecls.add(functionDecl);
 +                    buildOtherUdfs(functionDecl.getFuncBody(), functionDecls, declaredFunctions);
 +                }
 +            }
 +        }
 +
 +    }
 +
 +    private Function lookupUserDefinedFunctionDecl(FunctionSignature signature) throws AsterixException {
 +        if (signature.getNamespace() == null) {
 +            return null;
 +        }
 +        return MetadataManager.INSTANCE.getFunction(mdTxnCtx, signature);
 +    }
 +
 +    private Set<FunctionSignature> getFunctionCalls(Expression expression) throws AsterixException {
 +        GatherFunctionCalls gfc = new GatherFunctionCalls();
 +        expression.accept(gfc, null);
 +        return gfc.getCalls();
 +    }
 +
 +    private static class GatherFunctionCalls extends GatherFunctionCallsVisitor implements ISqlppVisitor<Void, Void> {
 +
 +        public GatherFunctionCalls() {
 +        }
 +
 +        @Override
 +        public Void visit(FromClause fromClause, Void arg) throws AsterixException {
 +            for (FromTerm fromTerm : fromClause.getFromTerms()) {
 +                fromTerm.accept(this, arg);
 +            }
 +            return null;
 +        }
 +
 +        @Override
 +        public Void visit(FromTerm fromTerm, Void arg) throws AsterixException {
 +            fromTerm.getLeftExpression().accept(this, arg);
 +            for (AbstractBinaryCorrelateClause correlateClause : fromTerm.getCorrelateClauses()) {
 +                correlateClause.accept(this, arg);
 +            }
 +            return null;
 +        }
 +
 +        @Override
 +        public Void visit(JoinClause joinClause, Void arg) throws AsterixException {
 +            joinClause.getRightExpression().accept(this, arg);
 +            joinClause.getConditionExpression().accept(this, arg);
 +            return null;
 +        }
 +
 +        @Override
 +        public Void visit(NestClause nestClause, Void arg) throws AsterixException {
 +            nestClause.getRightExpression().accept(this, arg);
 +            nestClause.getConditionExpression().accept(this, arg);
 +            return null;
 +        }
 +
 +        @Override
 +        public Void visit(Projection projection, Void arg) throws AsterixException {
 +            projection.getExpression().accept(this, arg);
 +            return null;
 +        }
 +
 +        @Override
 +        public Void visit(SelectBlock selectBlock, Void arg) throws AsterixException {
 +            if (selectBlock.hasFromClause()) {
 +                selectBlock.getFromClause().accept(this, arg);
 +            }
 +            if (selectBlock.hasLetClauses()) {
 +                for (LetClause letClause : selectBlock.getLetList()) {
 +                    letClause.accept(this, arg);
 +                }
 +            }
 +            if (selectBlock.hasWhereClause()) {
 +                selectBlock.getWhereClause().accept(this, arg);
 +            }
 +            if (selectBlock.hasGroupbyClause()) {
 +                selectBlock.getGroupbyClause().accept(this, arg);
 +            }
 +            if (selectBlock.hasLetClausesAfterGroupby()) {
 +                for (LetClause letClause : selectBlock.getLetListAfterGroupby()) {
 +                    letClause.accept(this, arg);
 +                }
 +            }
 +            if (selectBlock.hasHavingClause()) {
 +                selectBlock.getHavingClause().accept(this, arg);
 +            }
 +            selectBlock.getSelectClause().accept(this, arg);
 +            return null;
 +        }
 +
 +        @Override
 +        public Void visit(SelectClause selectClause, Void arg) throws AsterixException {
 +            if (selectClause.selectElement()) {
 +                selectClause.getSelectElement().accept(this, arg);
 +            } else {
 +                selectClause.getSelectRegular().accept(this, arg);
 +            }
 +            return null;
 +        }
 +
 +        @Override
 +        public Void visit(SelectElement selectElement, Void arg) throws AsterixException {
 +            selectElement.getExpression().accept(this, arg);
 +            return null;
 +        }
 +
 +        @Override
 +        public Void visit(SelectRegular selectRegular, Void arg) throws AsterixException {
 +            for (Projection projection : selectRegular.getProjections()) {
 +                projection.accept(this, arg);
 +            }
 +            return null;
 +        }
 +
 +        @Override
 +        public Void visit(SelectSetOperation selectSetOperation, Void arg) throws AsterixException {
 +            selectSetOperation.getLeftInput().accept(this, arg);
 +            for (SetOperationRight setOperationRight : selectSetOperation.getRightInputs()) {
 +                setOperationRight.getSetOperationRightInput().accept(this, arg);
 +            }
 +            return null;
 +        }
 +
 +        @Override
 +        public Void visit(SelectExpression selectStatement, Void arg) throws AsterixException {
 +            selectStatement.getSelectSetOperation().accept(this, arg);
 +            if (selectStatement.hasOrderby()) {
 +                selectStatement.getOrderbyClause().accept(this, arg);
 +            }
 +            if (selectStatement.hasLimit()) {
 +                selectStatement.getLimitClause().accept(this, arg);
 +            }
 +            return null;
 +        }
 +
 +        @Override
 +        public Void visit(UnnestClause unnestClause, Void arg) throws AsterixException {
 +            unnestClause.getRightExpression().accept(this, arg);
 +            return null;
 +        }
 +
 +        @Override
 +        public Void visit(HavingClause havingClause, Void arg) throws AsterixException {
 +            havingClause.getFilterExpression().accept(this, arg);
 +            return null;
 +        }
 +
 +    }
 +}

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/8516517e/asterixdb/asterix-lang-sqlpp/src/main/java/org/apache/asterix/lang/sqlpp/util/SqlppRewriteUtil.java
----------------------------------------------------------------------
diff --cc asterixdb/asterix-lang-sqlpp/src/main/java/org/apache/asterix/lang/sqlpp/util/SqlppRewriteUtil.java
index 0f8488a,0000000..6c737d6
mode 100644,000000..100644
--- a/asterixdb/asterix-lang-sqlpp/src/main/java/org/apache/asterix/lang/sqlpp/util/SqlppRewriteUtil.java
+++ b/asterixdb/asterix-lang-sqlpp/src/main/java/org/apache/asterix/lang/sqlpp/util/SqlppRewriteUtil.java
@@@ -1,50 -1,0 +1,59 @@@
 +/*
 + * Licensed to the Apache Software Foundation (ASF) under one
 + * or more contributor license agreements.  See the NOTICE file
 + * distributed with this work for additional information
 + * regarding copyright ownership.  The ASF licenses this file
 + * to you under the Apache License, Version 2.0 (the
 + * "License"); you may not use this file except in compliance
 + * with the License.  You may obtain a copy of the License at
 + *
 + *   http://www.apache.org/licenses/LICENSE-2.0
 + *
 + * Unless required by applicable law or agreed to in writing,
 + * software distributed under the License is distributed on an
 + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 + * KIND, either express or implied.  See the License for the
 + * specific language governing permissions and limitations
 + * under the License.
 + */
 +package org.apache.asterix.lang.sqlpp.util;
 +
 +import java.util.Collection;
 +import java.util.HashSet;
 +import java.util.Set;
 +
 +import org.apache.asterix.common.exceptions.AsterixException;
 +import org.apache.asterix.lang.common.base.Expression;
 +import org.apache.asterix.lang.common.base.ILangExpression;
 +import org.apache.asterix.lang.common.expression.VariableExpr;
 +import org.apache.asterix.lang.common.rewrites.LangRewritingContext;
- import org.apache.asterix.lang.sqlpp.visitor.SqlppGroupBySugarVisitor;
- import org.apache.asterix.lang.sqlpp.visitor.UsedVariableVisitor;
++import org.apache.asterix.lang.sqlpp.rewrites.visitor.SqlppGroupBySugarVisitor;
++import org.apache.asterix.lang.sqlpp.visitor.DeepCopyVisitor;
++import org.apache.asterix.lang.sqlpp.visitor.FreeVariableVisitor;
 +
 +public class SqlppRewriteUtil {
 +
 +    // Applying sugar rewriting for group-by.
 +    public static Expression rewriteExpressionUsingGroupVariable(VariableExpr groupVar,
 +            Collection<VariableExpr> targetVarList, ILangExpression expr, LangRewritingContext context)
 +                    throws AsterixException {
-         SqlppGroupBySugarVisitor visitor = new SqlppGroupBySugarVisitor(context, null, groupVar, targetVarList);
++        SqlppGroupBySugarVisitor visitor = new SqlppGroupBySugarVisitor(context, groupVar, targetVarList);
 +        return expr.accept(visitor, null);
 +    }
 +
-     public static Set<VariableExpr> getUsedVariable(Expression expr) throws AsterixException {
++    public static Set<VariableExpr> getFreeVariable(Expression expr) throws AsterixException {
 +        Set<VariableExpr> vars = new HashSet<>();
-         UsedVariableVisitor visitor = new UsedVariableVisitor();
++        FreeVariableVisitor visitor = new FreeVariableVisitor();
 +        expr.accept(visitor, vars);
 +        return vars;
 +    }
 +
++    public static ILangExpression deepCopy(ILangExpression expr) throws AsterixException {
++        if (expr == null) {
++            return expr;
++        }
++        DeepCopyVisitor visitor = new DeepCopyVisitor();
++        return expr.accept(visitor, null);
++    }
++
 +}


Mime
View raw message