You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@asterixdb.apache.org by ti...@apache.org on 2016/01/11 17:20:46 UTC

[1/6] incubator-asterixdb git commit: ASTERIXDB-1187, ASTERIXDB-1162 and ASTERIXDB-1252 fixes, plus new internal functions

Repository: incubator-asterixdb
Updated Branches:
  refs/heads/master 633acc400 -> 4053f390a


http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/functions/records/RecordMergeDescriptor.java
----------------------------------------------------------------------
diff --git a/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/functions/records/RecordMergeDescriptor.java b/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/functions/records/RecordMergeDescriptor.java
index 509f104..2c1a335 100644
--- a/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/functions/records/RecordMergeDescriptor.java
+++ b/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/functions/records/RecordMergeDescriptor.java
@@ -18,10 +18,9 @@
  */
 package org.apache.asterix.runtime.evaluators.functions.records;
 
-import java.io.ByteArrayInputStream;
-import java.io.DataInputStream;
 import java.io.IOException;
-import java.util.Stack;
+import java.util.ArrayList;
+import java.util.List;
 
 import org.apache.asterix.builders.RecordBuilder;
 import org.apache.asterix.common.exceptions.AsterixException;
@@ -32,13 +31,17 @@ import org.apache.asterix.om.functions.IFunctionDescriptor;
 import org.apache.asterix.om.functions.IFunctionDescriptorFactory;
 import org.apache.asterix.om.pointables.ARecordVisitablePointable;
 import org.apache.asterix.om.pointables.PointableAllocator;
+import org.apache.asterix.om.pointables.base.DefaultOpenFieldType;
 import org.apache.asterix.om.pointables.base.IVisitablePointable;
-import org.apache.asterix.om.typecomputer.impl.RecordMergeTypeComputer;
+import org.apache.asterix.om.typecomputer.impl.TypeComputerUtils;
 import org.apache.asterix.om.types.ARecordType;
 import org.apache.asterix.om.types.ATypeTag;
 import org.apache.asterix.om.types.BuiltinType;
 import org.apache.asterix.om.types.IAType;
+import org.apache.asterix.om.types.runtime.RuntimeRecordTypeInfo;
 import org.apache.asterix.runtime.evaluators.base.AbstractScalarFunctionDynamicDescriptor;
+import org.apache.asterix.runtime.evaluators.comparisons.DeepEqualAssessor;
+import org.apache.asterix.runtime.evaluators.functions.PointableHelper;
 import org.apache.hyracks.algebricks.common.exceptions.AlgebricksException;
 import org.apache.hyracks.algebricks.core.algebra.functions.FunctionIdentifier;
 import org.apache.hyracks.algebricks.runtime.base.ICopyEvaluator;
@@ -47,39 +50,34 @@ import org.apache.hyracks.api.dataflow.value.ISerializerDeserializer;
 import org.apache.hyracks.api.exceptions.HyracksDataException;
 import org.apache.hyracks.data.std.api.IDataOutputProvider;
 import org.apache.hyracks.data.std.util.ArrayBackedValueStorage;
-import org.apache.hyracks.data.std.util.ByteArrayAccessibleOutputStream;
 import org.apache.hyracks.dataflow.common.data.accessors.IFrameTupleReference;
-import org.apache.hyracks.util.string.UTF8StringReader;
-
-//The record merge evaluator is used to combine two records with no matching fieldnames
-//If both records have the same fieldname for a non-record field anywhere in the schema, the merge will fail
-//This function is performed on a recursive level, meaning that nested records can be combined
-//for instance if both records have a nested field called "metadata"
-//where metadata from A is {"comments":"this rocks"}
-//and metadata from B is {"index":7, "priority":5}
-//Records A and B can be combined yielding a nested record called "metadata"
-//That will have all three fields
-public class RecordMergeDescriptor extends AbstractScalarFunctionDynamicDescriptor {
-
-    private static final long serialVersionUID = 1L;
 
-    private static final byte SER_NULL_TYPE_TAG = ATypeTag.NULL.serialize();
+/**
+ * record merge evaluator is used to combine two records with no matching fieldnames
+ * If both records have the same fieldname for a non-record field anywhere in the schema, the merge will fail
+ * This function is performed on a recursive level, meaning that nested records can be combined
+ * for instance if both records have a nested field called "metadata"
+ * where metadata from A is {"comments":"this rocks"} and metadata from B is {"index":7, "priority":5}
+ * Records A and B can be combined yielding a nested record called "metadata"
+ * That will have all three fields
+ */
+public class RecordMergeDescriptor extends AbstractScalarFunctionDynamicDescriptor {
 
     public static final IFunctionDescriptorFactory FACTORY = new IFunctionDescriptorFactory() {
-        @Override
         public IFunctionDescriptor createFunctionDescriptor() {
             return new RecordMergeDescriptor();
         }
     };
-
+    private static final long serialVersionUID = 1L;
+    private static final byte SER_NULL_TYPE_TAG = ATypeTag.NULL.serialize();
     private ARecordType outRecType;
     private ARecordType inRecType0;
     private ARecordType inRecType1;
 
     public void reset(IAType outType, IAType inType0, IAType inType1) {
-        outRecType = RecordMergeTypeComputer.extractRecordType(outType);
-        inRecType0 = RecordMergeTypeComputer.extractRecordType(inType0);
-        inRecType1 = RecordMergeTypeComputer.extractRecordType(inType1);
+        outRecType = TypeComputerUtils.extractRecordType(outType);
+        inRecType0 = TypeComputerUtils.extractRecordType(inType0);
+        inRecType1 = TypeComputerUtils.extractRecordType(inType1);
     }
 
     @Override
@@ -88,11 +86,12 @@ public class RecordMergeDescriptor extends AbstractScalarFunctionDynamicDescript
 
             private static final long serialVersionUID = 1L;
 
+            @SuppressWarnings("unchecked")
+            private final ISerializerDeserializer<ANull> nullSerDe = AqlSerializerDeserializerProvider.INSTANCE
+                    .getSerializerDeserializer(BuiltinType.ANULL);
+
             @Override
             public ICopyEvaluator createEvaluator(final IDataOutputProvider output) throws AlgebricksException {
-                final ARecordType recType = new ARecordType(outRecType.getTypeName(), outRecType.getFieldNames(),
-                        outRecType.getFieldTypes(), outRecType.isOpen());
-
                 final PointableAllocator pa = new PointableAllocator();
                 final IVisitablePointable vp0 = pa.allocateRecordValue(inRecType0);
                 final IVisitablePointable vp1 = pa.allocateRecordValue(inRecType1);
@@ -103,18 +102,14 @@ public class RecordMergeDescriptor extends AbstractScalarFunctionDynamicDescript
                 final ICopyEvaluator eval0 = args[0].createEvaluator(abvs0);
                 final ICopyEvaluator eval1 = args[1].createEvaluator(abvs1);
 
+                final List<RecordBuilder> rbStack = new ArrayList<>();
+
+                final ArrayBackedValueStorage tabvs = new ArrayBackedValueStorage();
+
                 return new ICopyEvaluator() {
-                    @SuppressWarnings("unchecked")
-                    final ISerializerDeserializer<ANull> nullSerDe = AqlSerializerDeserializerProvider.INSTANCE
-                            .getSerializerDeserializer(BuiltinType.ANULL);
-                    final UTF8StringReader reader = new UTF8StringReader();
-
-                    private final Stack<RecordBuilder> rbStack = new Stack<RecordBuilder>();
-                    private final ArrayBackedValueStorage tabvs = new ArrayBackedValueStorage();
-                    private final ByteArrayAccessibleOutputStream nameOutputStream = new ByteArrayAccessibleOutputStream();
-                    private final ByteArrayInputStream namebais = new ByteArrayInputStream(
-                            nameOutputStream.getByteArray());
-                    private final DataInputStream namedis = new DataInputStream(namebais);
+
+                    private final RuntimeRecordTypeInfo runtimeRecordTypeInfo = new RuntimeRecordTypeInfo();
+                    private final DeepEqualAssessor deepEqualAssesor = new DeepEqualAssessor();
 
                     @Override
                     public void evaluate(IFrameTupleReference tuple) throws AlgebricksException {
@@ -141,7 +136,7 @@ public class RecordMergeDescriptor extends AbstractScalarFunctionDynamicDescript
                         ARecordVisitablePointable rp1 = (ARecordVisitablePointable) vp1;
 
                         try {
-                            mergeFields(recType, rp0, rp1, true, 0);
+                            mergeFields(outRecType, rp0, rp1, true, 0);
 
                             rbStack.get(0).write(output.getDataOutput(), true);
                         } catch (IOException | AsterixException e) {
@@ -151,39 +146,44 @@ public class RecordMergeDescriptor extends AbstractScalarFunctionDynamicDescript
 
                     private void mergeFields(ARecordType combinedType, ARecordVisitablePointable leftRecord,
                             ARecordVisitablePointable rightRecord, boolean openFromParent, int nestedLevel)
-                                    throws IOException, AsterixException, AlgebricksException {
+                            throws IOException, AsterixException, AlgebricksException {
                         if (rbStack.size() < (nestedLevel + 1)) {
-                            rbStack.push(new RecordBuilder());
+                            rbStack.add(new RecordBuilder());
                         }
 
                         rbStack.get(nestedLevel).reset(combinedType);
                         rbStack.get(nestedLevel).init();
+
                         //Add all fields from left record
                         for (int i = 0; i < leftRecord.getFieldNames().size(); i++) {
                             IVisitablePointable leftName = leftRecord.getFieldNames().get(i);
                             IVisitablePointable leftValue = leftRecord.getFieldValues().get(i);
+                            IVisitablePointable leftType = leftRecord.getFieldTypeTags().get(i);
                             boolean foundMatch = false;
                             for (int j = 0; j < rightRecord.getFieldNames().size(); j++) {
                                 IVisitablePointable rightName = rightRecord.getFieldNames().get(j);
                                 IVisitablePointable rightValue = rightRecord.getFieldValues().get(j);
-                                if (rightName.equals(leftName)) {
-                                    //Field was found on the right. Merge Sub Records
-                                    if (rightValue.getByteArray()[0] != ATypeTag.RECORD.serialize()
-                                            || leftValue.getByteArray()[0] != ATypeTag.RECORD.serialize()) {
-                                        //The fields need to be records in order to merge
-                                        throw new AlgebricksException("Duplicate field found");
-                                    } else {
+                                IVisitablePointable rightType = rightRecord.getFieldTypeTags().get(j);
+                                // Check if same fieldname
+                                if (PointableHelper.isEqual(leftName, rightName)
+                                        && !deepEqualAssesor.isEqual(leftValue, rightValue)) {
+                                    //Field was found on the right and are subrecords, merge them
+                                    if (PointableHelper.sameType(ATypeTag.RECORD, rightType)
+                                            && PointableHelper.sameType(ATypeTag.RECORD, leftType)) {
                                         //We are merging two sub records
                                         addFieldToSubRecord(combinedType, leftName, leftValue, rightValue,
                                                 openFromParent, nestedLevel);
+                                        foundMatch = true;
+                                    } else {
+                                        throw new AlgebricksException("Duplicate field found");
                                     }
-                                    foundMatch = true;
                                 }
                             }
                             if (!foundMatch) {
                                 addFieldToSubRecord(combinedType, leftName, leftValue, null, openFromParent,
                                         nestedLevel);
                             }
+
                         }
                         //Repeat for right side (ignoring duplicates this time)
                         for (int j = 0; j < rightRecord.getFieldNames().size(); j++) {
@@ -203,29 +203,30 @@ public class RecordMergeDescriptor extends AbstractScalarFunctionDynamicDescript
                         }
                     }
 
-                    //Takes in a record type, field name, and the field values (which are record) from two records
-                    //Merges them into one record of combinedType
-                    //And adds that record as a field to the Record in subrb
-                    //the second value can be null, indicated that you just add the value of left as a field to subrb
+                    /*
+                     * Takes in a record type, field name, and the field values (which are record) from two records
+                     * Merges them into one record of combinedType
+                     * And adds that record as a field to the Record in subrb
+                     * the second value can be null, indicated that you just add the value of left as a field to subrb
+                     *
+                     */
                     private void addFieldToSubRecord(ARecordType combinedType, IVisitablePointable fieldNamePointable,
                             IVisitablePointable leftValue, IVisitablePointable rightValue, boolean openFromParent,
                             int nestedLevel) throws IOException, AsterixException, AlgebricksException {
 
-                        nameOutputStream.reset();
-                        nameOutputStream.write(fieldNamePointable.getByteArray(),
-                                fieldNamePointable.getStartOffset() + 1, fieldNamePointable.getLength());
-                        namedis.reset();
-                        String fieldName = reader.readUTF(namedis);
+                        runtimeRecordTypeInfo.reset(combinedType);
+                        int pos = runtimeRecordTypeInfo.getFieldIndex(fieldNamePointable.getByteArray(),
+                                fieldNamePointable.getStartOffset() + 1, fieldNamePointable.getLength() - 1);
 
                         //Add the merged field
-                        if (combinedType.isClosedField(fieldName)) {
-                            int pos = combinedType.getFieldIndex(fieldName);
+                        if (combinedType != null && pos >= 0) {
                             if (rightValue == null) {
                                 rbStack.get(nestedLevel).addField(pos, leftValue);
                             } else {
-                                mergeFields((ARecordType) combinedType.getFieldType(fieldName),
+                                mergeFields((ARecordType) combinedType.getFieldTypes()[pos],
                                         (ARecordVisitablePointable) leftValue, (ARecordVisitablePointable) rightValue,
                                         false, nestedLevel + 1);
+
                                 tabvs.reset();
                                 rbStack.get(nestedLevel + 1).write(tabvs.getDataOutput(), true);
                                 rbStack.get(nestedLevel).addField(pos, tabvs);
@@ -234,7 +235,7 @@ public class RecordMergeDescriptor extends AbstractScalarFunctionDynamicDescript
                             if (rightValue == null) {
                                 rbStack.get(nestedLevel).addField(fieldNamePointable, leftValue);
                             } else {
-                                mergeFields((ARecordType) combinedType.getFieldType(fieldName),
+                                mergeFields(DefaultOpenFieldType.NESTED_OPEN_RECORD_TYPE,
                                         (ARecordVisitablePointable) leftValue, (ARecordVisitablePointable) rightValue,
                                         false, nestedLevel + 1);
                                 tabvs.reset();

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/functions/records/RecordRemoveFieldsDescriptor.java
----------------------------------------------------------------------
diff --git a/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/functions/records/RecordRemoveFieldsDescriptor.java b/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/functions/records/RecordRemoveFieldsDescriptor.java
new file mode 100644
index 0000000..0add4f0
--- /dev/null
+++ b/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/functions/records/RecordRemoveFieldsDescriptor.java
@@ -0,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.runtime.evaluators.functions.records;
+
+import org.apache.asterix.om.functions.AsterixBuiltinFunctions;
+import org.apache.asterix.om.functions.IFunctionDescriptor;
+import org.apache.asterix.om.functions.IFunctionDescriptorFactory;
+import org.apache.asterix.om.types.AOrderedListType;
+import org.apache.asterix.om.types.ARecordType;
+import org.apache.asterix.om.types.ATypeTag;
+import org.apache.asterix.om.types.IAType;
+import org.apache.asterix.runtime.evaluators.base.AbstractScalarFunctionDynamicDescriptor;
+import org.apache.hyracks.algebricks.common.exceptions.AlgebricksException;
+import org.apache.hyracks.algebricks.core.algebra.functions.FunctionIdentifier;
+import org.apache.hyracks.algebricks.runtime.base.ICopyEvaluatorFactory;
+
+public class RecordRemoveFieldsDescriptor extends AbstractScalarFunctionDynamicDescriptor {
+
+    private static final long serialVersionUID = 1L;
+
+    private static final byte SER_NULL_TYPE_TAG = ATypeTag.NULL.serialize();
+    private static final byte SER_ORDEREDLIST_TYPE_TAG = ATypeTag.ORDEREDLIST.serialize();
+
+    public static final IFunctionDescriptorFactory FACTORY = new IFunctionDescriptorFactory() {
+        public IFunctionDescriptor createFunctionDescriptor() {
+            return new RecordRemoveFieldsDescriptor();
+        }
+    };
+
+    private  RecordRemoveFieldsDescriptor() {
+    }
+
+    private ARecordType outputRecordType;
+    private ARecordType inputRecType;
+    private AOrderedListType inputListType;
+
+    public void reset(IAType outType, IAType inType, IAType inListType) {
+        outputRecordType = (ARecordType) outType;
+        inputRecType = (ARecordType) inType;
+        inputListType = (AOrderedListType) inListType;
+    }
+
+    public ICopyEvaluatorFactory createEvaluatorFactory(final ICopyEvaluatorFactory[] args) throws AlgebricksException {
+        return new RecordRemoveFieldsEvalFactory(args[0], args[1], outputRecordType, inputRecType, inputListType);
+    }
+
+    @Override
+    public FunctionIdentifier getIdentifier() {
+        return AsterixBuiltinFunctions.REMOVE_FIELDS;
+    }
+
+}
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/functions/records/RecordRemoveFieldsEvalFactory.java
----------------------------------------------------------------------
diff --git a/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/functions/records/RecordRemoveFieldsEvalFactory.java b/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/functions/records/RecordRemoveFieldsEvalFactory.java
new file mode 100644
index 0000000..a74f055
--- /dev/null
+++ b/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/functions/records/RecordRemoveFieldsEvalFactory.java
@@ -0,0 +1,235 @@
+/*
+ * 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.runtime.evaluators.functions.records;
+
+import java.io.IOException;
+import java.util.ArrayDeque;
+import java.util.ArrayList;
+import java.util.Deque;
+import java.util.Iterator;
+import java.util.List;
+
+import org.apache.asterix.builders.RecordBuilder;
+import org.apache.asterix.common.exceptions.AsterixException;
+import org.apache.asterix.formats.nontagged.AqlSerializerDeserializerProvider;
+import org.apache.asterix.om.base.ANull;
+import org.apache.asterix.om.functions.AsterixBuiltinFunctions;
+import org.apache.asterix.om.pointables.AListVisitablePointable;
+import org.apache.asterix.om.pointables.ARecordVisitablePointable;
+import org.apache.asterix.om.pointables.PointableAllocator;
+import org.apache.asterix.om.pointables.base.DefaultOpenFieldType;
+import org.apache.asterix.om.pointables.base.IVisitablePointable;
+import org.apache.asterix.om.types.AOrderedListType;
+import org.apache.asterix.om.types.ARecordType;
+import org.apache.asterix.om.types.ATypeTag;
+import org.apache.asterix.om.types.BuiltinType;
+import org.apache.asterix.om.types.EnumDeserializer;
+import org.apache.asterix.om.types.runtime.RuntimeRecordTypeInfo;
+import org.apache.asterix.runtime.evaluators.functions.PointableHelper;
+import org.apache.hyracks.algebricks.common.exceptions.AlgebricksException;
+import org.apache.hyracks.algebricks.runtime.base.ICopyEvaluator;
+import org.apache.hyracks.algebricks.runtime.base.ICopyEvaluatorFactory;
+import org.apache.hyracks.api.dataflow.value.ISerializerDeserializer;
+import org.apache.hyracks.api.exceptions.HyracksDataException;
+import org.apache.hyracks.data.std.api.IDataOutputProvider;
+import org.apache.hyracks.data.std.util.ArrayBackedValueStorage;
+import org.apache.hyracks.dataflow.common.data.accessors.IFrameTupleReference;
+
+class RecordRemoveFieldsEvalFactory implements ICopyEvaluatorFactory {
+    private static final long serialVersionUID = 1L;
+
+    private static final byte SER_NULL_TYPE_TAG = ATypeTag.NULL.serialize();
+    private static final byte SER_ORDEREDLIST_TYPE_TAG = ATypeTag.ORDEREDLIST.serialize();
+    private static final byte SER_RECORD_TYPE_TAG = ATypeTag.RECORD.serialize();
+    @SuppressWarnings("unchecked")
+    private final ISerializerDeserializer<ANull> nullSerDe = AqlSerializerDeserializerProvider.INSTANCE
+            .getSerializerDeserializer(BuiltinType.ANULL);
+    private ICopyEvaluatorFactory inputRecordEvalFactory;
+    private ICopyEvaluatorFactory removeFieldPathsFactory;
+    private ARecordType requiredRecType;
+    private ARecordType inputRecType;
+    private AOrderedListType inputListType;
+
+    public RecordRemoveFieldsEvalFactory(ICopyEvaluatorFactory inputRecordEvalFactory,
+            ICopyEvaluatorFactory removeFieldPathsFactory, ARecordType requiredRecType, ARecordType inputRecType,
+            AOrderedListType inputListType) {
+        this.inputRecordEvalFactory = inputRecordEvalFactory;
+        this.removeFieldPathsFactory = removeFieldPathsFactory;
+        this.requiredRecType = requiredRecType;
+        this.inputRecType = inputRecType;
+        this.inputListType = inputListType;
+
+    }
+
+    @Override
+    public ICopyEvaluator createEvaluator(final IDataOutputProvider output) throws AlgebricksException {
+
+        final PointableAllocator pa = new PointableAllocator();
+        final IVisitablePointable vp0 = pa.allocateRecordValue(inputRecType);
+        final IVisitablePointable vp1 = pa.allocateListValue(inputListType);
+        final ArrayBackedValueStorage outInput0 = new ArrayBackedValueStorage();
+        final ArrayBackedValueStorage outInput1 = new ArrayBackedValueStorage();
+        final ICopyEvaluator eval0 = inputRecordEvalFactory.createEvaluator(outInput0);
+        final ICopyEvaluator eval1 = removeFieldPathsFactory.createEvaluator(outInput1);
+
+        return new ICopyEvaluator() {
+            private final RuntimeRecordTypeInfo runtimeRecordTypeInfo = new RuntimeRecordTypeInfo();
+
+            private final List<RecordBuilder> rbStack = new ArrayList<>();
+            private final ArrayBackedValueStorage tabvs = new ArrayBackedValueStorage();
+            private final Deque<IVisitablePointable> recordPath = new ArrayDeque<>();
+
+
+            @Override
+            public void evaluate(IFrameTupleReference tuple) throws AlgebricksException {
+                outInput0.reset();
+                outInput1.reset();
+
+                eval0.evaluate(tuple);
+                eval1.evaluate(tuple);
+
+                if (outInput0.getByteArray()[0] == SER_NULL_TYPE_TAG) {
+                    try {
+                        nullSerDe.serialize(ANull.NULL, output.getDataOutput());
+                    } catch (HyracksDataException e) {
+                        throw new AlgebricksException(e);
+                    }
+                    return;
+                }
+
+                if (outInput0.getByteArray()[0] != SER_RECORD_TYPE_TAG) {
+                    throw new AlgebricksException(AsterixBuiltinFunctions.REMOVE_FIELDS.getName()
+                            + ": expects input type " + inputRecType + ", but got "
+                            + EnumDeserializer.ATYPETAGDESERIALIZER.deserialize(outInput0.getByteArray()[0]));
+                }
+
+                if (outInput1.getByteArray()[0] != SER_ORDEREDLIST_TYPE_TAG) {
+                    throw new AlgebricksException(AsterixBuiltinFunctions.REMOVE_FIELDS.getName()
+                            + ": expects input type " + inputListType + ", but got "
+                            + EnumDeserializer.ATYPETAGDESERIALIZER.deserialize(outInput1.getByteArray()[0]));
+                }
+
+                vp0.set(outInput0);
+                vp1.set(outInput1);
+
+                ARecordVisitablePointable recordPointable = (ARecordVisitablePointable) vp0;
+                AListVisitablePointable listPointable = (AListVisitablePointable) vp1;
+
+                try {
+                    recordPath.clear();
+                    rbStack.clear();
+                    processRecord(requiredRecType, recordPointable, listPointable, 0);
+                    rbStack.get(0).write(output.getDataOutput(), true);
+                } catch (IOException | AsterixException e) {
+                    throw new AlgebricksException(e);
+                }
+            }
+
+            private void processRecord(ARecordType requiredType, ARecordVisitablePointable srp,
+                    AListVisitablePointable inputList, int nestedLevel) throws IOException, AsterixException,
+                    AlgebricksException {
+                if (rbStack.size() < (nestedLevel + 1)) {
+                    rbStack.add(new RecordBuilder());
+                }
+
+                rbStack.get(nestedLevel).reset(requiredType);
+                rbStack.get(nestedLevel).init();
+
+                List<IVisitablePointable> fieldNames = srp.getFieldNames();
+                List<IVisitablePointable> fieldValues = srp.getFieldValues();
+                List<IVisitablePointable> fieldTypes = srp.getFieldTypeTags();
+
+                for (int i = 0; i < fieldNames.size(); i++) {
+                    IVisitablePointable subRecFieldName = fieldNames.get(i);
+                    recordPath.push(subRecFieldName);
+                    if (isValidPath(inputList)) {
+                        if (requiredType != null && requiredType.getTypeTag() != ATypeTag.ANY) {
+                            addKeptFieldToSubRecord(requiredType, subRecFieldName, fieldValues.get(i),
+                                    fieldTypes.get(i), inputList, nestedLevel);
+                        } else {
+                            addKeptFieldToSubRecord(DefaultOpenFieldType.NESTED_OPEN_RECORD_TYPE, subRecFieldName,
+                                    fieldValues.get(i), fieldTypes.get(i), inputList, nestedLevel);
+                        }
+                    }
+                    recordPath.pop();
+                }
+            }
+
+            private void addKeptFieldToSubRecord(ARecordType requiredType, IVisitablePointable fieldNamePointable,
+                    IVisitablePointable fieldValuePointable, IVisitablePointable fieldTypePointable,
+                    AListVisitablePointable inputList, int nestedLevel) throws IOException, AsterixException,
+                    AlgebricksException {
+
+                runtimeRecordTypeInfo.reset(requiredType);
+                int pos = runtimeRecordTypeInfo.getFieldIndex(fieldNamePointable.getByteArray(),
+                        fieldNamePointable.getStartOffset() + 1, fieldNamePointable.getLength() - 1);
+                if (pos >= 0) { // Closed field
+                    if (PointableHelper.sameType(ATypeTag.RECORD, fieldTypePointable)) {
+                        processRecord((ARecordType) requiredType.getFieldTypes()[pos],
+                                (ARecordVisitablePointable) fieldValuePointable, inputList, nestedLevel + 1);
+                        tabvs.reset();
+                        rbStack.get(nestedLevel + 1).write(tabvs.getDataOutput(), true);
+                        rbStack.get(nestedLevel).addField(pos, tabvs);
+                    } else {
+                        rbStack.get(nestedLevel).addField(pos, fieldValuePointable);
+                    }
+                } else { // Open field
+                    if (PointableHelper.sameType(ATypeTag.RECORD, fieldTypePointable)) {
+                        processRecord(null, (ARecordVisitablePointable) fieldValuePointable, inputList, nestedLevel + 1);
+                        tabvs.reset();
+                        rbStack.get(nestedLevel + 1).write(tabvs.getDataOutput(), true);
+                        rbStack.get(nestedLevel).addField(fieldNamePointable, tabvs);
+                    } else {
+                        rbStack.get(nestedLevel).addField(fieldNamePointable, fieldValuePointable);
+                    }
+                }
+            }
+
+            private boolean isValidPath(AListVisitablePointable inputList) throws HyracksDataException {
+                List<IVisitablePointable> items = inputList.getItems();
+                List<IVisitablePointable> typeTags = inputList.getItemTags();
+
+                int pathLen = recordPath.size();
+                for (int i = 0; i < items.size(); i++) {
+                    IVisitablePointable item = items.get(i);
+                    if (PointableHelper.sameType(ATypeTag.ORDEREDLIST, typeTags.get(i))) {
+                        List<IVisitablePointable> inputPathItems = ((AListVisitablePointable) item).getItems();
+
+                        if (pathLen == inputPathItems.size()) {
+                            boolean match = true;
+                            Iterator<IVisitablePointable> fpi = recordPath.iterator();
+                            for (int j = inputPathItems.size() - 1; j >= 0; j--) {
+                                match &= PointableHelper.isEqual(inputPathItems.get(j), fpi.next());
+                                if (!match)
+                                    break;
+                            }
+                            if (match)
+                                return false; // Not a valid path for the output record
+                        }
+                    } else {
+                        if (PointableHelper.isEqual(recordPath.getFirst(), item)) {
+                            return false;
+                        }
+                    }
+                }
+                return true;
+            }
+        };
+    }
+}

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/visitors/DeepEqualityVisitor.java
----------------------------------------------------------------------
diff --git a/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/visitors/DeepEqualityVisitor.java b/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/visitors/DeepEqualityVisitor.java
new file mode 100644
index 0000000..cd2718e
--- /dev/null
+++ b/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/visitors/DeepEqualityVisitor.java
@@ -0,0 +1,114 @@
+/*
+ * 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.runtime.evaluators.visitors;
+
+import java.util.HashMap;
+import java.util.Map;
+
+import org.apache.asterix.common.exceptions.AsterixException;
+import org.apache.asterix.om.pointables.AFlatValuePointable;
+import org.apache.asterix.om.pointables.AListVisitablePointable;
+import org.apache.asterix.om.pointables.ARecordVisitablePointable;
+import org.apache.asterix.om.pointables.base.IVisitablePointable;
+import org.apache.asterix.om.pointables.visitor.IVisitablePointableVisitor;
+import org.apache.asterix.om.types.ATypeTag;
+import org.apache.asterix.om.types.hierachy.ATypeHierarchy;
+import org.apache.asterix.om.types.hierachy.ATypeHierarchy.Domain;
+import org.apache.asterix.runtime.evaluators.functions.PointableHelper;
+import org.apache.hyracks.algebricks.common.utils.Pair;
+import org.apache.hyracks.api.exceptions.HyracksDataException;
+
+public class DeepEqualityVisitor implements IVisitablePointableVisitor<Void, Pair<IVisitablePointable, Boolean>> {
+    private final Map<IVisitablePointable, ListDeepEqualityChecker> lpointableToEquality = new HashMap<>();
+    private final Map<IVisitablePointable, RecordDeepEqualityChecker> rpointableToEquality = new HashMap<>();
+
+    @Override
+    public Void visit(AListVisitablePointable pointable, Pair<IVisitablePointable, Boolean> arg)
+            throws AsterixException {
+        ListDeepEqualityChecker listDeepEqualityChecker = lpointableToEquality.get(pointable);
+        if (listDeepEqualityChecker == null) {
+            listDeepEqualityChecker = new ListDeepEqualityChecker();
+            lpointableToEquality.put(pointable, listDeepEqualityChecker);
+        }
+
+        try {
+            arg.second = listDeepEqualityChecker.accessList(pointable, arg.first, this);
+        } catch (Exception e) {
+            throw new AsterixException(e);
+        }
+
+        return null;
+    }
+
+    @Override
+    public Void visit(ARecordVisitablePointable pointable, Pair<IVisitablePointable, Boolean> arg)
+            throws AsterixException {
+        RecordDeepEqualityChecker recDeepEqualityChecker = rpointableToEquality.get(pointable);
+        if (recDeepEqualityChecker == null) {
+            recDeepEqualityChecker = new RecordDeepEqualityChecker();
+            rpointableToEquality.put(pointable, recDeepEqualityChecker);
+        }
+
+        try {
+            arg.second = recDeepEqualityChecker.accessRecord(pointable, arg.first, this);
+        } catch (Exception e) {
+            throw new AsterixException(e);
+        }
+
+        return null;
+    }
+
+    @Override
+    public Void visit(AFlatValuePointable pointable, Pair<IVisitablePointable, Boolean> arg) throws AsterixException {
+
+        if (pointable.equals(arg.first)) {
+            arg.second = true;
+            return null;
+        }
+        try {
+            ATypeTag tt1 = PointableHelper.getTypeTag(pointable);
+            ATypeTag tt2 = PointableHelper.getTypeTag(arg.first);
+
+            if (tt1 != tt2) {
+                if (!ATypeHierarchy.isSameTypeDomain(tt1, tt2, false)) {
+                    arg.second = false;
+                } else {
+                    // If same domain, check if numberic
+                    Domain domain = ATypeHierarchy.getTypeDomain(tt1);
+                    byte b1[] = pointable.getByteArray();
+                    byte b2[] = arg.first.getByteArray();
+                    if (domain == Domain.NUMERIC) {
+                        int s1 = pointable.getStartOffset();
+                        int s2 = arg.first.getStartOffset();
+                        arg.second = (ATypeHierarchy.getDoubleValue(b1, s1) == ATypeHierarchy.getDoubleValue(b2, s2));
+                    } else {
+                        arg.second = false;
+                    }
+                }
+            } else {
+                arg.second = PointableHelper.byteArrayEqual(pointable, arg.first, 1);
+            }
+        } catch (HyracksDataException e) {
+            throw new AsterixException(e);
+        }
+
+        return null;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/visitors/DeepEqualityVisitorHelper.java
----------------------------------------------------------------------
diff --git a/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/visitors/DeepEqualityVisitorHelper.java b/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/visitors/DeepEqualityVisitorHelper.java
new file mode 100644
index 0000000..0e1f342
--- /dev/null
+++ b/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/visitors/DeepEqualityVisitorHelper.java
@@ -0,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.runtime.evaluators.visitors;
+
+import java.util.Arrays;
+
+import org.apache.asterix.dataflow.data.nontagged.comparators.ListItemBinaryComparatorFactory;
+import org.apache.asterix.dataflow.data.nontagged.hash.ListItemBinaryHashFunctionFactory;
+import org.apache.asterix.runtime.evaluators.functions.BinaryHashMap;
+import org.apache.hyracks.api.dataflow.value.IBinaryComparator;
+import org.apache.hyracks.api.dataflow.value.IBinaryHashFunction;
+
+public class DeepEqualityVisitorHelper {
+    // Default values
+    public static final int TABLE_SIZE = 100;
+    public static final int TABLE_FRAME_SIZE = 32768;
+
+    private final ListItemBinaryHashFunctionFactory listItemBinaryHashFunctionFactory = ListItemBinaryHashFunctionFactory.INSTANCE;
+    private final ListItemBinaryComparatorFactory listItemBinaryComparatorFactory = ListItemBinaryComparatorFactory.INSTANCE;
+
+    private final IBinaryHashFunction putHashFunc = listItemBinaryHashFunctionFactory.createBinaryHashFunction();
+    private final IBinaryHashFunction getHashFunc = listItemBinaryHashFunctionFactory.createBinaryHashFunction();
+    private IBinaryComparator cmp = listItemBinaryComparatorFactory.createBinaryComparator();
+    private BinaryHashMap hashMap = null;
+
+    public BinaryHashMap initializeHashMap(BinaryHashMap.BinaryEntry valEntry) {
+        return initializeHashMap(0, 0, valEntry);
+    }
+
+    public BinaryHashMap initializeHashMap(int tableSize, int tableFrameSize, BinaryHashMap.BinaryEntry valEntry) {
+        if (tableFrameSize != 0 && tableSize != 0) {
+            hashMap = new BinaryHashMap(tableSize, tableFrameSize, putHashFunc, getHashFunc, cmp);
+        } else {
+            hashMap = new BinaryHashMap(TABLE_SIZE, TABLE_FRAME_SIZE, putHashFunc, getHashFunc, cmp);
+        }
+
+        byte[] emptyValBuf = new byte[8];
+        Arrays.fill(emptyValBuf, (byte) 0);
+        valEntry.set(emptyValBuf, 0, 8);
+        return hashMap;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/visitors/ListDeepEqualityChecker.java
----------------------------------------------------------------------
diff --git a/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/visitors/ListDeepEqualityChecker.java b/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/visitors/ListDeepEqualityChecker.java
new file mode 100644
index 0000000..6d5513d
--- /dev/null
+++ b/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/visitors/ListDeepEqualityChecker.java
@@ -0,0 +1,142 @@
+/*
+ * 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.runtime.evaluators.visitors;
+
+import java.io.IOException;
+import java.util.List;
+import org.apache.asterix.common.exceptions.AsterixException;
+import org.apache.asterix.om.pointables.AListVisitablePointable;
+import org.apache.asterix.om.pointables.base.IVisitablePointable;
+import org.apache.asterix.om.types.ATypeTag;
+import org.apache.asterix.runtime.evaluators.functions.BinaryHashMap;
+import org.apache.asterix.runtime.evaluators.functions.BinaryHashMap.BinaryEntry;
+import org.apache.asterix.runtime.evaluators.functions.PointableHelper;
+import org.apache.hyracks.algebricks.common.utils.Pair;
+import org.apache.hyracks.api.exceptions.HyracksDataException;
+import org.apache.hyracks.data.std.primitive.IntegerPointable;
+
+class ListDeepEqualityChecker {
+    private DeepEqualityVisitor visitor;
+
+    private BinaryHashMap hashMap;
+    private BinaryEntry keyEntry = new BinaryEntry();
+    private BinaryEntry valEntry = new BinaryEntry();
+
+    private final DeepEqualityVisitorHelper deepEqualityVisitorHelper = new DeepEqualityVisitorHelper();
+    private final Pair<IVisitablePointable, Boolean> itemVisitorArg = new Pair<IVisitablePointable, Boolean>(null, false);
+
+    public ListDeepEqualityChecker() {
+        hashMap = deepEqualityVisitorHelper.initializeHashMap(valEntry);
+    }
+
+    public boolean accessList(IVisitablePointable listPointableLeft, IVisitablePointable listPointableRight,
+            DeepEqualityVisitor visitor) throws IOException, AsterixException {
+        this.visitor = visitor;
+
+        AListVisitablePointable listLeft = (AListVisitablePointable)listPointableLeft;
+        List<IVisitablePointable> itemsLeft = listLeft.getItems();
+        List<IVisitablePointable> itemTagTypesLeft = listLeft.getItemTags();
+
+
+        AListVisitablePointable listRight = (AListVisitablePointable)listPointableRight;
+        List<IVisitablePointable> itemsRight = listRight.getItems();
+        List<IVisitablePointable> itemTagTypesRight = listRight.getItemTags();
+
+        if (itemsLeft.size() != itemsRight.size()) return false;
+
+        boolean isOrderedRight = listLeft.ordered();
+        if (isOrderedRight != listRight.ordered())
+            return false;
+
+        if( isOrderedRight) {
+            return processOrderedList(itemsLeft, itemTagTypesLeft, itemsRight, itemTagTypesRight);
+        } else {
+            return processUnorderedList(itemsLeft, itemTagTypesLeft, itemsRight, itemTagTypesRight);
+        }
+    }
+
+    private boolean processOrderedList(List<IVisitablePointable> itemsLeft, List<IVisitablePointable> itemTagTypesLeft,
+            List<IVisitablePointable> itemsRight, List<IVisitablePointable> itemTagTypesRight)
+            throws HyracksDataException, AsterixException {
+        for(int i=0; i<itemsLeft.size(); i++) {
+            ATypeTag fieldTypeLeft = PointableHelper.getTypeTag(itemTagTypesLeft.get(i));
+            if(fieldTypeLeft.isDerivedType() && fieldTypeLeft != PointableHelper.getTypeTag(itemTagTypesRight.get(i))) {
+                return false;
+            }
+            itemVisitorArg.first = itemsRight.get(i);
+            itemsLeft.get(i).accept(visitor, itemVisitorArg);
+            if (itemVisitorArg.second == false)
+                return false;
+        }
+
+        return true;
+    }
+
+    private boolean processUnorderedList(List<IVisitablePointable> itemsLeft, List<IVisitablePointable> itemTagTypesLeft,
+            List<IVisitablePointable> itemsRight, List<IVisitablePointable> itemTagTypesRight)
+            throws HyracksDataException, AsterixException {
+
+        hashMap.clear();
+        // Build phase: Add items into hash map, starting with first list.
+        for(int i=0; i<itemsLeft.size(); i++) {
+            IVisitablePointable item = itemsLeft.get(i);
+            byte[] buf = item.getByteArray();
+            int off = item.getStartOffset();
+            int len = item.getLength();
+            keyEntry.set(buf, off, len);
+            IntegerPointable.setInteger(valEntry.buf, 0, i);
+            hashMap.put(keyEntry, valEntry);
+        }
+
+        return probeHashMap(itemsLeft, itemTagTypesLeft, itemsRight, itemTagTypesRight);
+    }
+
+
+    private boolean probeHashMap(List<IVisitablePointable> itemsLeft, List<IVisitablePointable> itemTagTypesLeft,
+            List<IVisitablePointable> itemsRight, List<IVisitablePointable> itemTagTypesRight)
+            throws HyracksDataException, AsterixException {
+        // Probe phase: Probe items from second list
+        for(int indexRight=0; indexRight<itemsRight.size(); indexRight++) {
+            IVisitablePointable itemRight = itemsRight.get(indexRight);
+            byte[] buf = itemRight.getByteArray();
+            int off = itemRight.getStartOffset();
+            int len = itemRight.getLength();
+            keyEntry.set(buf, off, len);
+            BinaryEntry entry = hashMap.get(keyEntry);
+
+            // The items doesn't match
+            if (entry == null) {
+                return false;
+            }
+
+            int indexLeft = IntegerPointable.getInteger(entry.buf, entry.off);
+            ATypeTag fieldTypeLeft = PointableHelper.getTypeTag(itemTagTypesLeft.get(indexLeft));
+            if(fieldTypeLeft.isDerivedType() && fieldTypeLeft != PointableHelper.getTypeTag(itemTagTypesRight.get(indexRight))) {
+                return false;
+            }
+
+            itemVisitorArg.first = itemRight;
+            itemsLeft.get(indexLeft).accept(visitor, itemVisitorArg);
+            if (itemVisitorArg.second == false)
+                return false;
+        }
+        return true;
+    }
+}
+

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/visitors/RecordDeepEqualityChecker.java
----------------------------------------------------------------------
diff --git a/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/visitors/RecordDeepEqualityChecker.java b/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/visitors/RecordDeepEqualityChecker.java
new file mode 100644
index 0000000..84e9cf6
--- /dev/null
+++ b/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/visitors/RecordDeepEqualityChecker.java
@@ -0,0 +1,112 @@
+/*
+ * 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.runtime.evaluators.visitors;
+
+import java.util.List;
+
+import org.apache.asterix.common.exceptions.AsterixException;
+import org.apache.asterix.dataflow.data.nontagged.serde.AInt32SerializerDeserializer;
+import org.apache.asterix.om.pointables.ARecordVisitablePointable;
+import org.apache.asterix.om.pointables.base.IVisitablePointable;
+import org.apache.asterix.om.types.ATypeTag;
+import org.apache.asterix.runtime.evaluators.functions.BinaryHashMap;
+import org.apache.asterix.runtime.evaluators.functions.PointableHelper;
+import org.apache.hyracks.algebricks.common.utils.Pair;
+import org.apache.hyracks.api.exceptions.HyracksDataException;
+import org.apache.hyracks.data.std.primitive.IntegerPointable;
+
+class RecordDeepEqualityChecker {
+    private final Pair<IVisitablePointable, Boolean> nestedVisitorArg = new Pair<IVisitablePointable, Boolean>(null,
+            false);
+    private final DeepEqualityVisitorHelper deepEqualityVisitorHelper = new DeepEqualityVisitorHelper();
+    private DeepEqualityVisitor visitor;
+    private BinaryHashMap.BinaryEntry keyEntry = new BinaryHashMap.BinaryEntry();
+    private BinaryHashMap.BinaryEntry valEntry = new BinaryHashMap.BinaryEntry();
+    private BinaryHashMap hashMap;
+
+    public RecordDeepEqualityChecker(int tableSize, int tableFrameSize) {
+        hashMap = deepEqualityVisitorHelper.initializeHashMap(tableSize, tableFrameSize, valEntry);
+    }
+
+    public RecordDeepEqualityChecker() {
+        hashMap = deepEqualityVisitorHelper.initializeHashMap(valEntry);
+    }
+
+    public boolean accessRecord(IVisitablePointable recPointableLeft, IVisitablePointable recPointableRight,
+            DeepEqualityVisitor visitor) throws HyracksDataException, AsterixException {
+
+        if (recPointableLeft.equals(recPointableRight)) {
+            return true;
+        }
+
+        this.visitor = visitor;
+
+        hashMap.clear();
+
+        ARecordVisitablePointable recLeft = (ARecordVisitablePointable) recPointableLeft;
+        List<IVisitablePointable> fieldNamesLeft = recLeft.getFieldNames();
+
+        ARecordVisitablePointable recRight = (ARecordVisitablePointable) recPointableRight;
+        List<IVisitablePointable> fieldNamesRight = recRight.getFieldNames();
+
+        int sizeLeft = fieldNamesLeft.size();
+        int sizeRight = fieldNamesRight.size();
+        if (sizeLeft != sizeRight) {
+            return false;
+        }
+
+        // Build phase: Add items into hash map, starting with first record.
+        for (int i = 0; i < sizeLeft; i++) {
+            IVisitablePointable fieldName = fieldNamesLeft.get(i);
+            keyEntry.set(fieldName.getByteArray(), fieldName.getStartOffset(), fieldName.getLength());
+            IntegerPointable.setInteger(valEntry.buf, 0, i);
+            hashMap.put(keyEntry, valEntry);
+        }
+
+        return compareValues(recLeft.getFieldTypeTags(), recLeft.getFieldValues(), fieldNamesRight,
+                recRight.getFieldTypeTags(), recRight.getFieldValues());
+    }
+
+    private boolean compareValues(List<IVisitablePointable> fieldTypesLeft, List<IVisitablePointable> fieldValuesLeft,
+            List<IVisitablePointable> fieldNamesRight, List<IVisitablePointable> fieldTypesRight,
+            List<IVisitablePointable> fieldValuesRight) throws HyracksDataException, AsterixException {
+
+        // Probe phase: Probe items from second record
+        for (int i = 0; i < fieldNamesRight.size(); i++) {
+            IVisitablePointable fieldName = fieldNamesRight.get(i);
+            keyEntry.set(fieldName.getByteArray(), fieldName.getStartOffset(), fieldName.getLength());
+            BinaryHashMap.BinaryEntry entry = hashMap.get(keyEntry);
+            if (entry == null) {
+                return false;
+            }
+
+            int fieldIdLeft = AInt32SerializerDeserializer.getInt(entry.buf, entry.off);
+            ATypeTag fieldTypeLeft = PointableHelper.getTypeTag(fieldTypesLeft.get(fieldIdLeft));
+            if (fieldTypeLeft.isDerivedType() && fieldTypeLeft != PointableHelper.getTypeTag(fieldTypesRight.get(i))) {
+                return false;
+            }
+            nestedVisitorArg.first = fieldValuesRight.get(i);
+            fieldValuesLeft.get(fieldIdLeft).accept(visitor, nestedVisitorArg);
+            if (nestedVisitorArg.second == false) {
+                return false;
+            }
+        }
+        return true;
+    }
+}

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-runtime/src/main/java/org/apache/asterix/runtime/formats/NonTaggedDataFormat.java
----------------------------------------------------------------------
diff --git a/asterix-runtime/src/main/java/org/apache/asterix/runtime/formats/NonTaggedDataFormat.java b/asterix-runtime/src/main/java/org/apache/asterix/runtime/formats/NonTaggedDataFormat.java
index 309f677..715bba7 100644
--- a/asterix-runtime/src/main/java/org/apache/asterix/runtime/formats/NonTaggedDataFormat.java
+++ b/asterix-runtime/src/main/java/org/apache/asterix/runtime/formats/NonTaggedDataFormat.java
@@ -168,87 +168,7 @@ import org.apache.asterix.runtime.evaluators.constructors.AUUIDFromStringConstru
 import org.apache.asterix.runtime.evaluators.constructors.AYearMonthDurationConstructorDescriptor;
 import org.apache.asterix.runtime.evaluators.constructors.ClosedRecordConstructorDescriptor;
 import org.apache.asterix.runtime.evaluators.constructors.OpenRecordConstructorDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.AndDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.AnyCollectionMemberDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.CastListDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.CastRecordDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.CodePointToStringDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.CountHashedGramTokensDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.CountHashedWordTokensDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.CreateCircleDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.CreateLineDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.CreateMBRDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.CreatePointDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.CreatePolygonDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.CreateRectangleDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.CreateUUIDDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.EditDistanceCheckDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.EditDistanceContainsDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.EditDistanceDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.EditDistanceListIsFilterable;
-import org.apache.asterix.runtime.evaluators.functions.EditDistanceStringIsFilterable;
-import org.apache.asterix.runtime.evaluators.functions.EmbedTypeDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.FlowRecordDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.FuzzyEqDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.GetItemDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.GramTokensDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.HashedGramTokensDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.HashedWordTokensDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.InjectFailureDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.IsNullDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.IsSystemNullDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.LenDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.NotDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.NotNullDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.NumericAbsDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.NumericAddDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.NumericCaretDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.NumericCeilingDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.NumericDivideDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.NumericFloorDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.NumericModuloDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.NumericMultiplyDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.NumericRoundDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.NumericRoundHalfToEven2Descriptor;
-import org.apache.asterix.runtime.evaluators.functions.NumericRoundHalfToEvenDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.NumericSubDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.NumericUnaryMinusDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.OrDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.OrderedListConstructorDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.PrefixLenJaccardDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.RegExpDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.SimilarityJaccardCheckDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.SimilarityJaccardDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.SimilarityJaccardPrefixCheckDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.SimilarityJaccardPrefixDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.SimilarityJaccardSortedCheckDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.SimilarityJaccardSortedDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.SpatialAreaDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.SpatialCellDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.SpatialDistanceDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.SpatialIntersectDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.StringConcatDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.StringContainsDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.StringEndsWithDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.StringEqualDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.StringJoinDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.StringLengthDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.StringLikeDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.StringLowerCaseDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.StringMatchesDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.StringMatchesWithFlagDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.StringReplaceDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.StringReplaceWithFlagsDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.StringStartsWithDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.StringToCodePointDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.StringUpperCaseDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.Substring2Descriptor;
-import org.apache.asterix.runtime.evaluators.functions.SubstringAfterDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.SubstringBeforeDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.SubstringDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.SwitchCaseDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.UnorderedListConstructorDescriptor;
-import org.apache.asterix.runtime.evaluators.functions.WordTokensDescriptor;
+import org.apache.asterix.runtime.evaluators.functions.*;
 import org.apache.asterix.runtime.evaluators.functions.binary.BinaryConcatDescriptor;
 import org.apache.asterix.runtime.evaluators.functions.binary.BinaryLengthDescriptor;
 import org.apache.asterix.runtime.evaluators.functions.binary.FindBinaryDescriptor;
@@ -264,7 +184,9 @@ import org.apache.asterix.runtime.evaluators.functions.records.FieldAccessNested
 import org.apache.asterix.runtime.evaluators.functions.records.FieldAccessNestedEvalFactory;
 import org.apache.asterix.runtime.evaluators.functions.records.GetRecordFieldValueDescriptor;
 import org.apache.asterix.runtime.evaluators.functions.records.GetRecordFieldsDescriptor;
+import org.apache.asterix.runtime.evaluators.functions.records.RecordAddFieldsDescriptor;
 import org.apache.asterix.runtime.evaluators.functions.records.RecordMergeDescriptor;
+import org.apache.asterix.runtime.evaluators.functions.records.RecordRemoveFieldsDescriptor;
 import org.apache.asterix.runtime.evaluators.functions.temporal.AdjustDateTimeForTimeZoneDescriptor;
 import org.apache.asterix.runtime.evaluators.functions.temporal.AdjustTimeForTimeZoneDescriptor;
 import org.apache.asterix.runtime.evaluators.functions.temporal.CalendarDuartionFromDateDescriptor;
@@ -556,6 +478,8 @@ public class NonTaggedDataFormat implements IDataFormat {
         temp.add(ADayTimeDurationConstructorDescriptor.FACTORY);
         temp.add(AUUIDFromStringConstructorDescriptor.FACTORY);
 
+        temp.add(DeepEqualityDescriptor.FACTORY);
+
         temp.add(CreateUUIDDescriptor.FACTORY);
         // Spatial
         temp.add(CreatePointDescriptor.FACTORY);
@@ -600,7 +524,10 @@ public class NonTaggedDataFormat implements IDataFormat {
         temp.add(SimilarityJaccardPrefixDescriptor.FACTORY);
         temp.add(SimilarityJaccardPrefixCheckDescriptor.FACTORY);
 
+        //Record functions
         temp.add(RecordMergeDescriptor.FACTORY);
+        temp.add(RecordAddFieldsDescriptor.FACTORY);
+        temp.add(RecordRemoveFieldsDescriptor.FACTORY);
         temp.add(SwitchCaseDescriptor.FACTORY);
         temp.add(RegExpDescriptor.FACTORY);
         temp.add(InjectFailureDescriptor.FACTORY);
@@ -936,6 +863,56 @@ public class NonTaggedDataFormat implements IDataFormat {
                 ((RecordMergeDescriptor) fd).reset(outType, type0, type1);
             }
         });
+
+        functionTypeInferers.put(AsterixBuiltinFunctions.DEEP_EQUAL, new FunctionTypeInferer() {
+
+            @Override public void infer(ILogicalExpression expr, IFunctionDescriptor fd,
+                    IVariableTypeEnvironment context) throws AlgebricksException {
+                AbstractFunctionCallExpression f = (AbstractFunctionCallExpression) expr;
+                IAType type0 = (IAType) context.getType(f.getArguments().get(0).getValue());
+                IAType type1 = (IAType) context.getType(f.getArguments().get(1).getValue());
+                ((DeepEqualityDescriptor) fd).reset(type0, type1);
+            }
+        });
+
+        functionTypeInferers.put(AsterixBuiltinFunctions.ADD_FIELDS, new FunctionTypeInferer() {
+
+            @Override public void infer(ILogicalExpression expr, IFunctionDescriptor fd,
+                    IVariableTypeEnvironment context) throws AlgebricksException {
+                AbstractFunctionCallExpression f = (AbstractFunctionCallExpression) expr;
+                IAType outType = (IAType) context.getType(expr);
+                IAType type0 = (IAType) context.getType(f.getArguments().get(0).getValue());
+                ILogicalExpression listExpr = f.getArguments().get(1).getValue();
+                IAType type1 = (IAType) context.getType(listExpr);
+                if (type0.getTypeTag().equals(ATypeTag.ANY)) {
+                    type0 = DefaultOpenFieldType.NESTED_OPEN_RECORD_TYPE;
+                }
+                if (type1.getTypeTag().equals(ATypeTag.ANY)) {
+                    type1 = DefaultOpenFieldType.NESTED_OPEN_AORDERED_LIST_TYPE;
+                }
+                ((RecordAddFieldsDescriptor) fd).reset(outType, type0, type1);
+            }
+        });
+
+        functionTypeInferers.put(AsterixBuiltinFunctions.REMOVE_FIELDS, new FunctionTypeInferer() {
+
+            @Override public void infer(ILogicalExpression expr, IFunctionDescriptor fd,
+                    IVariableTypeEnvironment context) throws AlgebricksException {
+                AbstractFunctionCallExpression f = (AbstractFunctionCallExpression) expr;
+                IAType outType = (IAType) context.getType(expr);
+                IAType type0 = (IAType) context.getType(f.getArguments().get(0).getValue());
+                ILogicalExpression le = f.getArguments().get(1).getValue();
+                IAType type1 = (IAType) context.getType(le);
+                if (type0.getTypeTag().equals(ATypeTag.ANY)) {
+                    type0 = DefaultOpenFieldType.NESTED_OPEN_RECORD_TYPE;
+                }
+                if (type1.getTypeTag().equals(ATypeTag.ANY)) {
+                    type1 = DefaultOpenFieldType.NESTED_OPEN_AORDERED_LIST_TYPE;
+                }
+                ((RecordRemoveFieldsDescriptor) fd).reset(outType, type0, type1);
+            }
+        });
+
         functionTypeInferers.put(AsterixBuiltinFunctions.CAST_RECORD, new FunctionTypeInferer() {
             @Override
             public void infer(ILogicalExpression expr, IFunctionDescriptor fd, IVariableTypeEnvironment context)
@@ -1107,6 +1084,7 @@ public class NonTaggedDataFormat implements IDataFormat {
                 }
             }
         });
+
     }
 
     @Override
@@ -1234,5 +1212,4 @@ public class NonTaggedDataFormat implements IDataFormat {
     public IPredicateEvaluatorFactoryProvider getPredicateEvaluatorFactoryProvider() {
         return AqlPredicateEvaluatorFactoryProvider.INSTANCE;
     }
-
 }


[2/6] incubator-asterixdb git commit: ASTERIXDB-1187, ASTERIXDB-1162 and ASTERIXDB-1252 fixes, plus new internal functions

Posted by ti...@apache.org.
http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-om/src/main/java/org/apache/asterix/om/typecomputer/impl/RecordAddFieldsTypeComputer.java
----------------------------------------------------------------------
diff --git a/asterix-om/src/main/java/org/apache/asterix/om/typecomputer/impl/RecordAddFieldsTypeComputer.java b/asterix-om/src/main/java/org/apache/asterix/om/typecomputer/impl/RecordAddFieldsTypeComputer.java
new file mode 100644
index 0000000..4f8d1f2
--- /dev/null
+++ b/asterix-om/src/main/java/org/apache/asterix/om/typecomputer/impl/RecordAddFieldsTypeComputer.java
@@ -0,0 +1,185 @@
+/*
+ * 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.om.typecomputer.impl;
+
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Map;
+
+import org.apache.asterix.om.base.AString;
+import org.apache.asterix.om.base.IAObject;
+import org.apache.asterix.om.constants.AsterixConstantValue;
+import org.apache.asterix.om.typecomputer.base.IResultTypeComputer;
+import org.apache.asterix.om.types.AOrderedListType;
+import org.apache.asterix.om.types.ARecordType;
+import org.apache.asterix.om.types.ATypeTag;
+import org.apache.asterix.om.types.AUnionType;
+import org.apache.asterix.om.types.IAType;
+import org.apache.asterix.om.types.TypeHelper;
+import org.apache.commons.lang3.mutable.Mutable;
+import org.apache.hyracks.algebricks.common.exceptions.AlgebricksException;
+import org.apache.hyracks.algebricks.core.algebra.base.ILogicalExpression;
+import org.apache.hyracks.algebricks.core.algebra.base.LogicalExpressionTag;
+import org.apache.hyracks.algebricks.core.algebra.expressions.AbstractFunctionCallExpression;
+import org.apache.hyracks.algebricks.core.algebra.expressions.AbstractLogicalExpression;
+import org.apache.hyracks.algebricks.core.algebra.expressions.ConstantExpression;
+import org.apache.hyracks.algebricks.core.algebra.expressions.IVariableTypeEnvironment;
+import org.apache.hyracks.algebricks.core.algebra.metadata.IMetadataProvider;
+
+public class RecordAddFieldsTypeComputer implements IResultTypeComputer {
+    public static final RecordAddFieldsTypeComputer INSTANCE = new RecordAddFieldsTypeComputer();
+
+    private static final String FIELD_NAME_NAME = "field-name";
+    private static final String FIELD_VALUE_VALUE = "field-value";
+
+    private RecordAddFieldsTypeComputer() {
+    }
+
+    @Override
+    public IAType computeType(ILogicalExpression expression, IVariableTypeEnvironment env,
+            IMetadataProvider<?, ?> metadataProvider) throws AlgebricksException {
+
+        AbstractFunctionCallExpression funcExpr = (AbstractFunctionCallExpression) expression;
+        IAType type0 = (IAType) env.getType(funcExpr.getArguments().get(0).getValue());
+
+        ARecordType inputRecordType = TypeComputerUtils.extractRecordType(type0);
+        if (inputRecordType == null) {
+            throw new AlgebricksException("Input record cannot be null");
+        }
+
+        AbstractLogicalExpression arg1 = (AbstractLogicalExpression) funcExpr.getArguments().get(1).getValue();
+        IAType type1 = (IAType) env.getType(arg1);
+        AOrderedListType inputOrderedListType = TypeComputerUtils.extractOrderedListType(type1);
+        if (inputOrderedListType == null) {
+            return inputRecordType;
+        }
+
+        boolean nullable = TypeHelper.canBeNull(type0) || TypeHelper.canBeNull(type1);
+        Map<String, IAType> additionalFields = new HashMap<>();
+        List<String> resultFieldNames = new ArrayList<>();
+        List<IAType> resultFieldTypes = new ArrayList<>();
+
+        resultFieldNames.addAll(Arrays.asList(inputRecordType.getFieldNames()));
+        Collections.sort(resultFieldNames);
+
+        for (String fieldName : resultFieldNames) {
+            try {
+                if (inputRecordType.getFieldType(fieldName).getTypeTag() == ATypeTag.RECORD) {
+                    ARecordType nestedType = (ARecordType) inputRecordType.getFieldType(fieldName);
+                    //Deep Copy prevents altering of input types
+                    resultFieldTypes.add(nestedType.deepCopy(nestedType));
+                } else {
+                    resultFieldTypes.add(inputRecordType.getFieldType(fieldName));
+                }
+            } catch (IOException e) {
+                throw new IllegalStateException(e);
+            }
+        }
+
+        if (!containsVariable(arg1)) {
+            AbstractFunctionCallExpression f = (AbstractFunctionCallExpression) arg1;
+            List<Mutable<ILogicalExpression>> args = f.getArguments();
+
+            AString fieldName = null;
+            IAType fieldType = null;
+
+            // Iterating through the orderlist input
+            for (Mutable<ILogicalExpression> arg : args) {
+                AbstractFunctionCallExpression recConsExpr = (AbstractFunctionCallExpression) arg.getValue();
+                ARecordType rtype = TypeComputerUtils.extractRecordType((IAType) env.getType(recConsExpr));
+                if (rtype != null) {
+                    String[] fn = rtype.getFieldNames();
+                    IAType[] ft = rtype.getFieldTypes();
+                    for (int j = 0; j < fn.length; j++) {
+                        if (fn[j].equals(FIELD_NAME_NAME)) {
+                            ILogicalExpression fieldNameExpr = recConsExpr.getArguments().get(j).getValue();
+                            switch (fieldNameExpr.getExpressionTag()) {
+                                case CONSTANT: // Top fields only
+                                    IAObject object = ((AsterixConstantValue) ((ConstantExpression) fieldNameExpr)
+                                            .getValue()).getObject();
+                                    if (object.getType().getTypeTag() == ATypeTag.STRING) {
+                                        // Get the actual "field-name" string
+                                        ILogicalExpression recFieldExpr = recConsExpr.getArguments().get(j + 1)
+                                                .getValue();
+                                        if (recFieldExpr.getExpressionTag() == LogicalExpressionTag.CONSTANT) {
+                                            fieldName = (AString) ((AsterixConstantValue) ((ConstantExpression) recFieldExpr)
+                                                    .getValue()).getObject();
+                                        }
+                                    }
+                                    break;
+                                default:
+                                    throw new AlgebricksException(fieldNameExpr + " is not supported.");
+                            }
+                        } else if (fn[j].equals(FIELD_VALUE_VALUE)) {
+                            fieldType = ft[j];
+                        }
+                    }
+                    if (fieldName != null) {
+                        additionalFields.put(fieldName.getStringValue(), fieldType);
+                    }
+                }
+            }
+
+            if (!additionalFields.isEmpty()) {
+                Iterator<Map.Entry<String, IAType>> it = additionalFields.entrySet().iterator();
+                while (it.hasNext()) {
+                    Map.Entry<String, IAType> entry = it.next();
+                    resultFieldNames.add(entry.getKey());
+                    resultFieldTypes.add(entry.getValue());
+                }
+            }
+        } // If variable ignore, deal with the addition at runtime
+
+        String resultTypeName = "appended(" + inputRecordType.getTypeName() + ")";
+        int n = resultFieldNames.size();
+        IAType resultType = new ARecordType(resultTypeName, resultFieldNames.toArray(new String[n]),
+                resultFieldTypes.toArray(new IAType[n]), true);
+        if (nullable) {
+            resultType = AUnionType.createNullableType(resultType);
+        }
+        return resultType;
+    }
+
+    // Handle variable as input
+    private boolean containsVariable(ILogicalExpression expression) {
+        if (expression.getExpressionTag() == LogicalExpressionTag.FUNCTION_CALL) {
+            AbstractFunctionCallExpression f = (AbstractFunctionCallExpression) expression;
+            List<Mutable<ILogicalExpression>> args = f.getArguments();
+            for (Mutable<ILogicalExpression> arg : args) {
+                ILogicalExpression subExpression = arg.getValue();
+                switch (subExpression.getExpressionTag()) {
+                    case VARIABLE:
+                        return true;
+                    case CONSTANT:
+                        return false;
+                    default: //FUNCTION_CALL
+                        return containsVariable(subExpression);
+                }
+            }
+        }
+        return true;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-om/src/main/java/org/apache/asterix/om/typecomputer/impl/RecordMergeTypeComputer.java
----------------------------------------------------------------------
diff --git a/asterix-om/src/main/java/org/apache/asterix/om/typecomputer/impl/RecordMergeTypeComputer.java b/asterix-om/src/main/java/org/apache/asterix/om/typecomputer/impl/RecordMergeTypeComputer.java
index 83f4f44..653b26e 100644
--- a/asterix-om/src/main/java/org/apache/asterix/om/typecomputer/impl/RecordMergeTypeComputer.java
+++ b/asterix-om/src/main/java/org/apache/asterix/om/typecomputer/impl/RecordMergeTypeComputer.java
@@ -23,7 +23,6 @@ import java.io.IOException;
 import java.util.ArrayList;
 import java.util.Collections;
 import java.util.List;
-
 import org.apache.asterix.common.exceptions.AsterixException;
 import org.apache.asterix.om.typecomputer.base.IResultTypeComputer;
 import org.apache.asterix.om.types.ARecordType;
@@ -44,21 +43,6 @@ public class RecordMergeTypeComputer implements IResultTypeComputer {
     private RecordMergeTypeComputer() {
     }
 
-    public static ARecordType extractRecordType(IAType t) {
-        if (t.getTypeTag() == ATypeTag.RECORD) {
-            return (ARecordType) t;
-        }
-
-        if (t.getTypeTag() == ATypeTag.UNION) {
-            IAType innerType = ((AUnionType) t).getNullableType();
-            if (innerType.getTypeTag() == ATypeTag.RECORD) {
-                return (ARecordType) innerType;
-            }
-        }
-
-        return null;
-    }
-
     @Override
     public IAType computeType(ILogicalExpression expression, IVariableTypeEnvironment env,
             IMetadataProvider<?, ?> metadataProvider) throws AlgebricksException {
@@ -66,12 +50,12 @@ public class RecordMergeTypeComputer implements IResultTypeComputer {
         IAType t0 = (IAType) env.getType(f.getArguments().get(0).getValue());
         IAType t1 = (IAType) env.getType(f.getArguments().get(1).getValue());
         boolean nullable = TypeHelper.canBeNull(t0) || TypeHelper.canBeNull(t1);
-        ARecordType recType0 = extractRecordType(t0);
-        ARecordType recType1 = extractRecordType(t1);
+        ARecordType recType0 = TypeComputerUtils.extractRecordType(t0);
+        ARecordType recType1 = TypeComputerUtils.extractRecordType(t1);
 
         if (recType0 == null || recType1 == null) {
-            throw new AlgebricksException(
-                    "record-merge expects possibly NULL records as arguments, but got (" + t0 + ", " + t1 + ")");
+            throw new AlgebricksException("record-merge expects possibly NULL records as arguments, but got (" + t0
+                    + ", " + t1 + ")");
         }
 
         List<String> resultFieldNames = new ArrayList<>();
@@ -79,6 +63,7 @@ public class RecordMergeTypeComputer implements IResultTypeComputer {
             resultFieldNames.add(fieldName);
         }
         Collections.sort(resultFieldNames);
+
         List<IAType> resultFieldTypes = new ArrayList<>();
         for (String fieldName : resultFieldNames) {
             try {
@@ -96,20 +81,27 @@ public class RecordMergeTypeComputer implements IResultTypeComputer {
 
         List<String> additionalFieldNames = new ArrayList<>();
         List<IAType> additionalFieldTypes = new ArrayList<>();
-        for (int i = 0; i < recType1.getFieldNames().length; ++i) {
-            String fieldName = recType1.getFieldNames()[i];
-            IAType fieldType = recType1.getFieldTypes()[i];
-            int pos = Collections.binarySearch(resultFieldNames, fieldName);
+        String fieldNames[] = recType1.getFieldNames();
+        IAType fieldTypes[] = recType1.getFieldTypes();
+        for (int i = 0; i < fieldNames.length; ++i) {
+            int pos = Collections.binarySearch(resultFieldNames, fieldNames[i]);
             if (pos >= 0) {
+                IAType resultFieldType = resultFieldTypes.get(pos);
+                if (resultFieldType.getTypeTag() != fieldTypes[i].getTypeTag()) {
+                    throw new AlgebricksException("Duplicate field " + fieldNames[i] + " encountered");
+                }
                 try {
-                    resultFieldTypes.set(pos, mergedNestedType(fieldType, resultFieldTypes.get(pos)));
+                    // Assuming fieldTypes[i].getTypeTag() = resultFieldType.getTypeTag()
+                    if (fieldTypes[i].getTypeTag() == ATypeTag.RECORD) {
+                        resultFieldTypes.set(pos, mergedNestedType(fieldTypes[i], resultFieldType));
+                    }
                 } catch (AsterixException e) {
                     throw new AlgebricksException(e);
                 }
 
             } else {
-                additionalFieldNames.add(fieldName);
-                additionalFieldTypes.add(fieldType);
+                additionalFieldNames.add(fieldNames[i]);
+                additionalFieldTypes.add(fieldTypes[i]);
             }
         }
 
@@ -117,9 +109,9 @@ public class RecordMergeTypeComputer implements IResultTypeComputer {
         resultFieldTypes.addAll(additionalFieldTypes);
         String resultTypeName = "merged(" + recType0.getTypeName() + ", " + recType1.getTypeName() + ")";
         boolean isOpen = recType0.isOpen() || recType1.isOpen();
-        IAType resultType = null;
-        resultType = new ARecordType(resultTypeName, resultFieldNames.toArray(new String[] {}),
-                resultFieldTypes.toArray(new IAType[] {}), isOpen);
+
+        IAType resultType = new ARecordType(resultTypeName, resultFieldNames.toArray(new String[] {}),
+                    resultFieldTypes.toArray(new IAType[] {}), isOpen);
 
         if (nullable) {
             resultType = AUnionType.createNullableType(resultType);
@@ -127,32 +119,32 @@ public class RecordMergeTypeComputer implements IResultTypeComputer {
         return resultType;
     }
 
-    IAType mergedNestedType(IAType fieldType1, IAType fieldType0) throws AlgebricksException, AsterixException {
+    private IAType mergedNestedType(IAType fieldType1, IAType fieldType0) throws AlgebricksException, AsterixException {
         if (fieldType1.getTypeTag() != ATypeTag.RECORD || fieldType0.getTypeTag() != ATypeTag.RECORD) {
-            throw new AlgebricksException("Duplicate field \"" + fieldType1.getTypeName() + "\" encountered");
+            throw new AlgebricksException("Duplicate field " + fieldType1.getTypeName() + " encountered");
         }
 
-        ARecordType returnType = (ARecordType) fieldType0;
+        ARecordType resultType = (ARecordType) fieldType0;
         ARecordType fieldType1Copy = (ARecordType) fieldType1;
 
         for (int i = 0; i < fieldType1Copy.getFieldTypes().length; i++) {
             try {
-                int pos = returnType.getFieldIndex(fieldType1Copy.getFieldNames()[i]);
+                int pos = resultType.getFieldIndex(fieldType1Copy.getFieldNames()[i]);
                 if (pos >= 0) {
-                    if (fieldType1Copy.getFieldTypes()[i].getTypeTag() != ATypeTag.RECORD) {
-                        break;
+                    // If a sub-record do merge, else ignore and let the values decide what to do
+                    if (fieldType1Copy.getFieldTypes()[i].getTypeTag() == ATypeTag.RECORD) {
+                        IAType[] oldTypes = resultType.getFieldTypes();
+                        oldTypes[pos] = mergedNestedType(fieldType1Copy.getFieldTypes()[i],
+                                resultType.getFieldTypes()[pos]);
+                        resultType = new ARecordType(resultType.getTypeName(), resultType.getFieldNames(), oldTypes,
+                                resultType.isOpen());
                     }
-                    IAType[] oldTypes = returnType.getFieldTypes();
-                    oldTypes[pos] = mergedNestedType(fieldType1Copy.getFieldTypes()[i],
-                            returnType.getFieldTypes()[pos]);
-                    returnType = new ARecordType(returnType.getTypeName(), returnType.getFieldNames(), oldTypes,
-                            returnType.isOpen());
                 } else {
-                    IAType[] combinedFieldTypes = ArrayUtils.addAll(returnType.getFieldTypes().clone(),
+                    IAType[] combinedFieldTypes = ArrayUtils.addAll(resultType.getFieldTypes().clone(),
                             fieldType1Copy.getFieldTypes()[i]);
-                    returnType = new ARecordType(returnType.getTypeName(),
-                            ArrayUtils.addAll(returnType.getFieldNames(), fieldType1Copy.getFieldNames()[i]),
-                            combinedFieldTypes, returnType.isOpen());
+                    resultType = new ARecordType(resultType.getTypeName(), ArrayUtils.addAll(
+                            resultType.getFieldNames(), fieldType1Copy.getFieldNames()[i]), combinedFieldTypes,
+                            resultType.isOpen());
                 }
 
             } catch (IOException | AsterixException e) {
@@ -160,6 +152,6 @@ public class RecordMergeTypeComputer implements IResultTypeComputer {
             }
         }
 
-        return returnType;
+        return resultType;
     }
 }

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-om/src/main/java/org/apache/asterix/om/typecomputer/impl/RecordRemoveFieldsTypeComputer.java
----------------------------------------------------------------------
diff --git a/asterix-om/src/main/java/org/apache/asterix/om/typecomputer/impl/RecordRemoveFieldsTypeComputer.java b/asterix-om/src/main/java/org/apache/asterix/om/typecomputer/impl/RecordRemoveFieldsTypeComputer.java
new file mode 100644
index 0000000..9f4d155
--- /dev/null
+++ b/asterix-om/src/main/java/org/apache/asterix/om/typecomputer/impl/RecordRemoveFieldsTypeComputer.java
@@ -0,0 +1,328 @@
+/*
+ * 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.om.typecomputer.impl;
+
+import java.io.IOException;
+import java.util.ArrayDeque;
+import java.util.ArrayList;
+import java.util.Deque;
+import java.util.HashSet;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Set;
+
+import org.apache.asterix.om.base.AOrderedList;
+import org.apache.asterix.om.base.AString;
+import org.apache.asterix.om.base.IAObject;
+import org.apache.asterix.om.constants.AsterixConstantValue;
+import org.apache.asterix.om.pointables.base.DefaultOpenFieldType;
+import org.apache.asterix.om.typecomputer.base.IResultTypeComputer;
+import org.apache.asterix.om.types.AOrderedListType;
+import org.apache.asterix.om.types.ARecordType;
+import org.apache.asterix.om.types.ATypeTag;
+import org.apache.asterix.om.types.BuiltinType;
+import org.apache.asterix.om.types.IAType;
+import org.apache.commons.lang3.mutable.Mutable;
+import org.apache.hyracks.algebricks.common.exceptions.AlgebricksException;
+import org.apache.hyracks.algebricks.core.algebra.base.ILogicalExpression;
+import org.apache.hyracks.algebricks.core.algebra.base.LogicalExpressionTag;
+import org.apache.hyracks.algebricks.core.algebra.expressions.AbstractFunctionCallExpression;
+import org.apache.hyracks.algebricks.core.algebra.expressions.AbstractLogicalExpression;
+import org.apache.hyracks.algebricks.core.algebra.expressions.ConstantExpression;
+import org.apache.hyracks.algebricks.core.algebra.expressions.IVariableTypeEnvironment;
+import org.apache.hyracks.algebricks.core.algebra.metadata.IMetadataProvider;
+
+/**
+ * Cases to support:
+ * remove-fields($record, ["foo", ["bar", "access"]]),
+ * where ["bar", "access"] is equivalent to the path bar->access
+ */
+public class RecordRemoveFieldsTypeComputer implements IResultTypeComputer {
+
+    public static final RecordRemoveFieldsTypeComputer INSTANCE = new RecordRemoveFieldsTypeComputer();
+
+    private RecordRemoveFieldsTypeComputer() {
+    }
+
+    private void getPathFromConstantExpression(ILogicalExpression expression, Set<String> fieldNameSet,
+            List<List<String>> pathList) throws AlgebricksException {
+        ConstantExpression ce = (ConstantExpression) expression;
+        if (!(ce.getValue() instanceof AsterixConstantValue)) {
+            throw new AlgebricksException("Expecting a list of strings and found " + ce.getValue() + " instead.");
+        }
+        IAObject item = ((AsterixConstantValue) ce.getValue()).getObject();
+        ATypeTag type = item.getType().getTypeTag();
+
+        switch (type) {
+            case STRING:
+                String fn = ((AString) item).getStringValue();
+                fieldNameSet.add(fn);
+                break;
+            case ORDEREDLIST:
+                AOrderedList pathOrdereList = (AOrderedList) item;
+                String fieldName = ((AString) pathOrdereList.getItem(0)).getStringValue();
+                fieldNameSet.add(fieldName);
+                List<String> path = new ArrayList<>();
+                for (int i = 0; i < pathOrdereList.size(); i++) {
+                    path.add(((AString) pathOrdereList.getItem(i)).getStringValue());
+                }
+                pathList.add(path);
+                break;
+            default:
+                throw new AlgebricksException("Unsupport type: " + type);
+        }
+    }
+
+    private List<String> getListFromExpression(ILogicalExpression expression) throws AlgebricksException {
+        AbstractFunctionCallExpression funcExp = (AbstractFunctionCallExpression) expression;
+        List<Mutable<ILogicalExpression>> args = funcExp.getArguments();
+
+        List<String> list = new ArrayList<>();
+        for (Mutable<ILogicalExpression> arg : args) {
+            // At this point all elements has to be a constant
+            // Input list has only one level of nesting (list of list or list of strings)
+            ConstantExpression ce = (ConstantExpression) arg.getValue();
+            if (!(ce.getValue() instanceof AsterixConstantValue)) {
+                throw new AlgebricksException("Expecting a list of strings and found " + ce.getValue() + " instead.");
+            }
+            IAObject item = ((AsterixConstantValue) ce.getValue()).getObject();
+            ATypeTag type = item.getType().getTypeTag();
+            if (type == ATypeTag.STRING) {
+                list.add(((AString) item).getStringValue());
+            } else {
+                throw new AlgebricksException(type + " is currently not supported. Please check your function call.");
+            }
+        }
+
+        return list;
+    }
+
+    private void getPathFromFunctionExpression(ILogicalExpression expression, Set<String> fieldNameSet,
+            List<List<String>> pathList) throws AlgebricksException {
+
+        List<String> path = getListFromExpression(expression);
+        // Add the path head to remove set
+        fieldNameSet.add(path.get(0));
+        pathList.add(path);
+
+    }
+
+    private void computeTypeFromNonConstantExpression(ILogicalExpression expression, Set<String> fieldNameSet,
+            List<List<String>> pathList) throws AlgebricksException {
+        AbstractFunctionCallExpression funcExp = (AbstractFunctionCallExpression) expression;
+        List<Mutable<ILogicalExpression>> args = funcExp.getArguments();
+
+        for (Mutable<ILogicalExpression> arg : args) {
+            ILogicalExpression le = arg.getValue();
+            switch (le.getExpressionTag()) {
+                case CONSTANT:
+                    getPathFromConstantExpression(le, fieldNameSet, pathList);
+                    break;
+                case FUNCTION_CALL:
+                    getPathFromFunctionExpression(le, fieldNameSet, pathList);
+                    break;
+                default:
+                    throw new AlgebricksException("Unsupported expression: " + le);
+            }
+        }
+    }
+
+    @Override
+    public IAType computeType(ILogicalExpression expression, IVariableTypeEnvironment env,
+            IMetadataProvider<?, ?> metadataProvider) throws AlgebricksException {
+
+        AbstractFunctionCallExpression funcExpr = (AbstractFunctionCallExpression) expression;
+        IAType type0 = (IAType) env.getType(funcExpr.getArguments().get(0).getValue());
+
+        List<List<String>> pathList = new ArrayList<>();
+        Set<String> fieldNameSet = new HashSet<>();
+        Deque<String> fieldPathStack = new ArrayDeque<>();
+
+        ARecordType inputRecordType = NonTaggedFieldAccessByNameResultType.getRecordTypeFromType(type0, expression);
+        if (inputRecordType == null) {
+            return BuiltinType.ANY;
+        }
+
+        AbstractLogicalExpression arg1 = (AbstractLogicalExpression) funcExpr.getArguments().get(1).getValue();
+        IAType inputListType = (IAType) env.getType(arg1);
+        AOrderedListType inputOrderedListType = TypeComputerUtils.extractOrderedListType(inputListType);
+        if (inputOrderedListType == null) {
+            throw new AlgebricksException(
+                    "The function 'remove-fields' expects an ordered list as the second argument, but got "
+                            + inputListType);
+        }
+
+        ATypeTag tt = inputOrderedListType.getItemType().getTypeTag();
+        if (tt == ATypeTag.STRING) { // If top-fieldlist
+            if (setFieldNameSet(arg1, fieldNameSet)) {
+                return buildOutputType(fieldPathStack, inputRecordType, fieldNameSet, pathList);
+            } else {
+                return DefaultOpenFieldType.NESTED_OPEN_RECORD_TYPE;
+            }
+        } else { // tt == ATypeTag.ANY, meaning the list is nested
+            computeTypeFromNonConstantExpression(arg1, fieldNameSet, pathList);
+            IAType resultType = buildOutputType(fieldPathStack, inputRecordType, fieldNameSet, pathList);
+            return resultType;
+        }
+    }
+
+    private boolean setFieldNameSet(ILogicalExpression expr, Set<String> fieldNameSet) {
+        if (expr.getExpressionTag() == LogicalExpressionTag.CONSTANT) {
+            AOrderedList orderedList = (AOrderedList) (((AsterixConstantValue) ((ConstantExpression) expr).getValue())
+                    .getObject());
+            for (int i = 0; i < orderedList.size(); i++) {
+                AString as = (AString) orderedList.getItem(i);
+                fieldNameSet.add(as.getStringValue());
+            }
+            return true; // Success
+        }
+        return false;
+    }
+
+    private void addField(ARecordType inputRecordType,  String fieldName, List<String> resultFieldNames, List<IAType>
+            resultFieldTypes)
+            throws AlgebricksException {
+        try {
+            resultFieldNames.add(fieldName);
+            if (inputRecordType.getFieldType(fieldName).getTypeTag() == ATypeTag.RECORD) {
+                ARecordType nestedType = (ARecordType) inputRecordType.getFieldType(fieldName);
+                //Deep Copy prevents altering of input types
+                resultFieldTypes.add(nestedType.deepCopy(nestedType));
+            } else {
+                resultFieldTypes.add(inputRecordType.getFieldType(fieldName));
+            }
+
+        } catch (IOException e) {
+            throw new AlgebricksException(e);
+        }
+    }
+
+    private IAType buildOutputType(Deque<String> fieldPathStack, ARecordType inputRecordType, Set<String> fieldNameSet,
+            List<List<String>> pathList) throws AlgebricksException {
+        IAType resultType;
+        List<String> resultFieldNames = new ArrayList<>();
+        List<IAType> resultFieldTypes = new ArrayList<>();
+
+        String[] fieldNames = inputRecordType.getFieldNames();
+        IAType[] fieldTypes = inputRecordType.getFieldTypes();
+
+        for (int i = 0; i < fieldNames.length; i++) {
+            if (!fieldNameSet.contains(fieldNames[i])) { // The main field is to be kept
+                addField(inputRecordType, fieldNames[i], resultFieldNames, resultFieldTypes);
+            } else if (!pathList.isEmpty()) { // Further check needed for nested fields
+                if (fieldTypes[i].getTypeTag() == ATypeTag.RECORD) {
+                    ARecordType subRecord = (ARecordType) fieldTypes[i];
+
+                    fieldPathStack.push(fieldNames[i]);
+                    subRecord = deepCheckAndCopy(fieldPathStack, subRecord, pathList, inputRecordType.isOpen());
+                    fieldPathStack.pop();
+                    if (subRecord != null) {
+                        resultFieldNames.add(fieldNames[i]);
+                        resultFieldTypes.add(subRecord);
+                    }
+                }
+            }
+        }
+
+        int n = resultFieldNames.size();
+        String resultTypeName = "result-record(" + inputRecordType.getTypeName() + ")";
+
+        return new ARecordType(resultTypeName, resultFieldNames.toArray(new String[n]),
+                    resultFieldTypes.toArray(new IAType[n]), true); // Make the output type open always
+
+    }
+
+    /**
+     * Comparison elements of two paths
+     * Note: l2 uses a LIFO insert and removal.
+     */
+    private <E> boolean isEqualPaths(List<E> l1, Deque<E> l2) {
+        if ((l1 == null) || (l2 == null))
+            return false;
+
+        if (l1.size() != l2.size())
+            return false;
+
+        Iterator<E> it2 = l2.iterator();
+
+        int len = l1.size();
+        for (int i = len - 1; i >= 0; i--) {
+            E o1 = l1.get(i);
+            E o2 = it2.next();
+            if (!o1.equals(o2))
+                return false;
+        }
+        return true;
+    }
+
+    private boolean isRemovePath(Deque<String> fieldPath, List<List<String>> pathList) {
+        for (List<String> removePath : pathList) {
+            if (isEqualPaths(removePath, fieldPath)) {
+                return true;
+            }
+        }
+        return false;
+    }
+
+    /*
+        A method to deep copy a record the path validation
+             i.e., keep only fields that are valid
+     */
+    private ARecordType deepCheckAndCopy(Deque<String> fieldPath, ARecordType srcRecType, List<List<String>>
+            pathList, boolean isOpen)
+            throws AlgebricksException {
+        // Make sure the current path is valid before going further
+        if (isRemovePath(fieldPath, pathList)) {
+            return null;
+        }
+
+        String srcFieldNames[] = srcRecType.getFieldNames();
+        IAType srcFieldTypes[] = srcRecType.getFieldTypes();
+
+        List<IAType> destFieldTypes = new ArrayList<>();
+        List<String> destFieldNames = new ArrayList<>();
+
+        for (int i = 0; i < srcFieldNames.length; i++) {
+            fieldPath.push(srcFieldNames[i]);
+            if (!isRemovePath(fieldPath, pathList)) {
+                if (srcFieldTypes[i].getTypeTag() == ATypeTag.RECORD) {
+                    ARecordType subRecord = (ARecordType) srcFieldTypes[i];
+                    subRecord = deepCheckAndCopy(fieldPath, subRecord, pathList, isOpen);
+                    if (subRecord != null) {
+                        destFieldNames.add(srcFieldNames[i]);
+                        destFieldTypes.add(subRecord);
+                    }
+                } else {
+                    destFieldNames.add(srcFieldNames[i]);
+                    destFieldTypes.add(srcFieldTypes[i]);
+                }
+            }
+            fieldPath.pop();
+        }
+
+        int n = destFieldNames.size();
+        if (n == 0) {
+            return null;
+        }
+        return new ARecordType(srcRecType.getTypeName(), destFieldNames.toArray(new String[n]),
+                    destFieldTypes.toArray(new IAType[n]), isOpen);
+    }
+
+}
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-om/src/main/java/org/apache/asterix/om/typecomputer/impl/TypeComputerUtils.java
----------------------------------------------------------------------
diff --git a/asterix-om/src/main/java/org/apache/asterix/om/typecomputer/impl/TypeComputerUtils.java b/asterix-om/src/main/java/org/apache/asterix/om/typecomputer/impl/TypeComputerUtils.java
new file mode 100644
index 0000000..cba988b
--- /dev/null
+++ b/asterix-om/src/main/java/org/apache/asterix/om/typecomputer/impl/TypeComputerUtils.java
@@ -0,0 +1,75 @@
+/*
+ * 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.om.typecomputer.impl;
+
+import org.apache.asterix.om.types.AOrderedListType;
+import org.apache.asterix.om.types.ARecordType;
+import org.apache.asterix.om.types.ATypeTag;
+import org.apache.asterix.om.types.AUnionType;
+import org.apache.asterix.om.types.AUnorderedListType;
+import org.apache.asterix.om.types.IAType;
+
+public class TypeComputerUtils {
+
+    public static ARecordType extractRecordType(IAType t) {
+        if (t.getTypeTag() == ATypeTag.RECORD) {
+            return (ARecordType) t;
+        }
+
+        if (t.getTypeTag() == ATypeTag.UNION) {
+            IAType innerType = ((AUnionType) t).getUnionList().get(1);
+            if (innerType.getTypeTag() == ATypeTag.RECORD) {
+                return (ARecordType) innerType;
+            }
+        }
+
+        return null;
+    }
+
+    public static AOrderedListType extractOrderedListType(IAType t) {
+        if (t.getTypeTag() == ATypeTag.ORDEREDLIST) {
+            return (AOrderedListType) t;
+        }
+
+        if (t.getTypeTag() == ATypeTag.UNION) {
+            IAType innerType = ((AUnionType) t).getUnionList().get(1);
+            if (innerType.getTypeTag() == ATypeTag.ORDEREDLIST) {
+                return (AOrderedListType) innerType;
+            }
+        }
+
+        return null;
+    }
+
+    public static AUnorderedListType extractUnorderedListType(IAType t) {
+        if (t.getTypeTag() == ATypeTag.UNORDEREDLIST) {
+            return (AUnorderedListType) t;
+        }
+
+        if (t.getTypeTag() == ATypeTag.UNION) {
+            IAType innerType = ((AUnionType) t).getUnionList().get(1);
+            if (innerType.getTypeTag() == ATypeTag.UNORDEREDLIST) {
+                return (AUnorderedListType) innerType;
+            }
+        }
+
+        return null;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-om/src/main/java/org/apache/asterix/om/types/hierachy/ATypeHierarchy.java
----------------------------------------------------------------------
diff --git a/asterix-om/src/main/java/org/apache/asterix/om/types/hierachy/ATypeHierarchy.java b/asterix-om/src/main/java/org/apache/asterix/om/types/hierachy/ATypeHierarchy.java
index 6524930..0b6b45d 100644
--- a/asterix-om/src/main/java/org/apache/asterix/om/types/hierachy/ATypeHierarchy.java
+++ b/asterix-om/src/main/java/org/apache/asterix/om/types/hierachy/ATypeHierarchy.java
@@ -45,13 +45,6 @@ import org.apache.hyracks.data.std.primitive.ShortPointable;
 
 public class ATypeHierarchy {
 
-    public static enum Domain {
-        SPATIAL,
-        NUMERIC,
-        LIST,
-        ANY
-    }
-
     private static BitSet typePromotionHierachyMap = new BitSet(ATypeTag.TYPE_COUNT * ATypeTag.TYPE_COUNT);
     private static BitSet typeDemotionHierachyMap = new BitSet(ATypeTag.TYPE_COUNT * ATypeTag.TYPE_COUNT);
     private static HashMap<Integer, ITypeConvertComputer> promoteComputerMap = new HashMap<Integer, ITypeConvertComputer>();
@@ -125,6 +118,10 @@ public class ATypeHierarchy {
         hierarchyDomains.put(ATypeTag.UNORDEREDLIST, Domain.LIST);
     }
 
+    public static Domain getTypeDomain(ATypeTag tag) {
+        return hierarchyDomains.get(tag);
+    }
+
     public static boolean isSameTypeDomain(ATypeTag tag1, ATypeTag tag2, boolean useListDomain) {
         Domain tagHierarchy1 = hierarchyDomains.get(tag1);
         Domain tagHierarchy2 = hierarchyDomains.get(tag2);
@@ -805,4 +802,11 @@ public class ATypeHierarchy {
         return value;
     }
 
+    public static enum Domain {
+        SPATIAL,
+        NUMERIC,
+        LIST,
+        ANY
+    }
+
 }

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/DeepEqualAssessor.java
----------------------------------------------------------------------
diff --git a/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/DeepEqualAssessor.java b/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/DeepEqualAssessor.java
new file mode 100644
index 0000000..b4e0375
--- /dev/null
+++ b/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/DeepEqualAssessor.java
@@ -0,0 +1,83 @@
+/*
+ * 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.runtime.evaluators.comparisons;
+
+import org.apache.asterix.common.exceptions.AsterixException;
+import org.apache.asterix.om.pointables.base.IVisitablePointable;
+import org.apache.asterix.om.types.ATypeTag;
+import org.apache.asterix.om.types.hierachy.ATypeHierarchy;
+import org.apache.asterix.om.types.hierachy.ATypeHierarchy.Domain;
+import org.apache.asterix.runtime.evaluators.functions.PointableHelper;
+import org.apache.asterix.runtime.evaluators.visitors.DeepEqualityVisitor;
+import org.apache.hyracks.algebricks.common.exceptions.AlgebricksException;
+import org.apache.hyracks.algebricks.common.utils.Pair;
+import org.apache.hyracks.api.exceptions.HyracksDataException;
+
+/**
+ * Use {@link DeepEqualityVisitor} to assess the deep equality between two
+ * pointable values, including oredered and unordered lists, record values, etc.
+ * Example: Let IVisitablePointable leftPointable, IVisitablePointable rightPointable be two
+ * value references. To assess their equality, simply use
+ * DeepEqualAssessor dea = new DeepEqualAssessor();
+ * boolean isEqual = dea.isEqual(leftPointable, rightPointable);
+ */
+
+public class DeepEqualAssessor {
+    private final DeepEqualityVisitor equalityVisitor = new DeepEqualityVisitor();
+
+    public boolean isEqual(IVisitablePointable leftPointable, IVisitablePointable rightPointable)
+            throws AlgebricksException, AsterixException {
+
+        if (leftPointable == null || rightPointable == null) {
+            return false;
+        }
+
+        if (leftPointable.equals(rightPointable)) {
+            return true;
+        }
+
+        ATypeTag leftTypeTag = PointableHelper.getTypeTag(leftPointable);
+        ATypeTag rightTypeTag = PointableHelper.getTypeTag(rightPointable);
+
+        if (leftTypeTag != rightTypeTag) {
+            // If types are numeric compare their real values instead
+            if (ATypeHierarchy.isSameTypeDomain(leftTypeTag, rightTypeTag, false)
+                    && ATypeHierarchy.getTypeDomain(leftTypeTag) == Domain.NUMERIC) {
+                try {
+                    double leftVal = ATypeHierarchy.getDoubleValue(leftPointable.getByteArray(),
+                            leftPointable.getStartOffset());
+                    double rightVal = ATypeHierarchy.getDoubleValue(rightPointable.getByteArray(),
+                            rightPointable.getStartOffset());
+                    return (leftVal == rightVal);
+                } catch (HyracksDataException e) {
+                    throw new AlgebricksException(e);
+                }
+
+            } else {
+                return false;
+            }
+        }
+
+        Pair<IVisitablePointable, Boolean> arg = new Pair<IVisitablePointable, Boolean>(rightPointable, Boolean.FALSE);
+        // Assess the nested equality
+        leftPointable.accept(equalityVisitor, arg);
+
+        return arg.second;
+    }
+}

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/functions/DeepEqualityDescriptor.java
----------------------------------------------------------------------
diff --git a/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/functions/DeepEqualityDescriptor.java b/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/functions/DeepEqualityDescriptor.java
new file mode 100644
index 0000000..e6a4232
--- /dev/null
+++ b/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/functions/DeepEqualityDescriptor.java
@@ -0,0 +1,113 @@
+/*
+ * 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.runtime.evaluators.functions;
+
+import java.io.DataOutput;
+
+import org.apache.asterix.formats.nontagged.AqlSerializerDeserializerProvider;
+import org.apache.asterix.om.base.ABoolean;
+import org.apache.asterix.om.functions.AsterixBuiltinFunctions;
+import org.apache.asterix.om.functions.IFunctionDescriptor;
+import org.apache.asterix.om.functions.IFunctionDescriptorFactory;
+import org.apache.asterix.om.pointables.PointableAllocator;
+import org.apache.asterix.om.pointables.base.IVisitablePointable;
+import org.apache.asterix.om.types.BuiltinType;
+import org.apache.asterix.om.types.IAType;
+import org.apache.asterix.runtime.evaluators.base.AbstractScalarFunctionDynamicDescriptor;
+import org.apache.asterix.runtime.evaluators.comparisons.DeepEqualAssessor;
+import org.apache.hyracks.algebricks.common.exceptions.AlgebricksException;
+import org.apache.hyracks.algebricks.core.algebra.functions.FunctionIdentifier;
+import org.apache.hyracks.algebricks.runtime.base.ICopyEvaluator;
+import org.apache.hyracks.algebricks.runtime.base.ICopyEvaluatorFactory;
+import org.apache.hyracks.api.dataflow.value.ISerializerDeserializer;
+import org.apache.hyracks.data.std.api.IDataOutputProvider;
+import org.apache.hyracks.data.std.util.ArrayBackedValueStorage;
+import org.apache.hyracks.dataflow.common.data.accessors.IFrameTupleReference;
+
+public class DeepEqualityDescriptor extends AbstractScalarFunctionDynamicDescriptor {
+    public static final IFunctionDescriptorFactory FACTORY = new IFunctionDescriptorFactory() {
+        public IFunctionDescriptor createFunctionDescriptor() {
+            return new DeepEqualityDescriptor();
+        }
+    };
+
+    private static final long serialVersionUID = 1L;
+    private IAType inputTypeLeft;
+    private IAType inputTypeRight;
+
+    public void reset(IAType inTypeLeft, IAType inTypeRight) {
+        this.inputTypeLeft = inTypeLeft;
+        this.inputTypeRight = inTypeRight;
+    }
+
+    @Override
+    public ICopyEvaluatorFactory createEvaluatorFactory(final ICopyEvaluatorFactory[] args) {
+        final ICopyEvaluatorFactory evalFactoryLeft = args[0];
+        final ICopyEvaluatorFactory evalFactoryRight = args[1];
+
+        return new ICopyEvaluatorFactory() {
+            private static final long serialVersionUID = 1L;
+            private final ISerializerDeserializer boolSerde = AqlSerializerDeserializerProvider.INSTANCE
+                    .getSerializerDeserializer(BuiltinType.ABOOLEAN);
+
+            @Override
+            public ICopyEvaluator createEvaluator(final IDataOutputProvider output) throws AlgebricksException {
+                final DataOutput out = output.getDataOutput();
+                final ArrayBackedValueStorage abvsLeft = new ArrayBackedValueStorage();
+                final ICopyEvaluator evalLeft = evalFactoryLeft.createEvaluator(abvsLeft);
+
+                final ArrayBackedValueStorage abvsRight = new ArrayBackedValueStorage();
+                final ICopyEvaluator evalRight = evalFactoryRight.createEvaluator(abvsRight);
+                final DeepEqualAssessor deepEqualAssessor = new DeepEqualAssessor();
+
+                return new ICopyEvaluator() {
+                    private final PointableAllocator allocator = new PointableAllocator();
+                    private final IVisitablePointable pointableLeft = allocator.allocateFieldValue(inputTypeLeft);
+                    private final IVisitablePointable pointableRight = allocator.allocateFieldValue(inputTypeRight);
+
+                    @Override
+                    public void evaluate(IFrameTupleReference tuple) throws AlgebricksException {
+                        try {
+                            abvsLeft.reset();
+                            abvsRight.reset();
+                            evalLeft.evaluate(tuple);
+                            evalRight.evaluate(tuple);
+                            pointableLeft.set(abvsLeft);
+                            pointableRight.set(abvsRight);
+
+                            // Using deep equality assessment to assess the equality of the two values
+                            boolean isEqual = deepEqualAssessor.isEqual(pointableLeft, pointableRight);
+                            ABoolean result = isEqual ? ABoolean.TRUE : ABoolean.FALSE;
+
+                            boolSerde.serialize(result, out);
+                        } catch (Exception ioe) {
+                            throw new AlgebricksException(ioe);
+                        }
+                    }
+                };
+            }
+        };
+    }
+
+    @Override
+    public FunctionIdentifier getIdentifier() {
+        return AsterixBuiltinFunctions.DEEP_EQUAL;
+    }
+}

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/functions/PointableHelper.java
----------------------------------------------------------------------
diff --git a/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/functions/PointableHelper.java b/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/functions/PointableHelper.java
new file mode 100644
index 0000000..24e66f2
--- /dev/null
+++ b/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/functions/PointableHelper.java
@@ -0,0 +1,129 @@
+/*
+ * 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.runtime.evaluators.functions;
+
+import java.io.DataOutput;
+import java.io.IOException;
+
+import org.apache.asterix.common.exceptions.AsterixException;
+import org.apache.asterix.om.pointables.base.IVisitablePointable;
+import org.apache.asterix.om.types.ATypeTag;
+import org.apache.asterix.om.types.EnumDeserializer;
+import org.apache.hyracks.algebricks.common.exceptions.AlgebricksException;
+import org.apache.hyracks.api.dataflow.value.IBinaryComparator;
+import org.apache.hyracks.api.exceptions.HyracksDataException;
+import org.apache.hyracks.data.std.accessors.PointableBinaryComparatorFactory;
+import org.apache.hyracks.data.std.api.IMutableValueStorage;
+import org.apache.hyracks.data.std.api.IValueReference;
+import org.apache.hyracks.data.std.primitive.UTF8StringPointable;
+import org.apache.hyracks.util.string.UTF8StringWriter;
+
+/**
+ * An utility class for some frequently used methods like checking the equality between two pointables (binary values)
+ * (e.g., field names), string value of a fieldname pointable, getting the typetag of a pointable, etc.
+ * Note: To get the typetag of a fieldvalue (i) in a record, it is recommended to use the getFieldTypeTags().get(i)
+ * method rather than getting it from fhe field value itself.
+ */
+
+public class PointableHelper {
+    private static final IBinaryComparator STRING_BINARY_COMPARATOR = PointableBinaryComparatorFactory.of(
+            UTF8StringPointable.FACTORY).createBinaryComparator();
+    private final UTF8StringWriter utf8Writer;
+
+    public PointableHelper() {
+        utf8Writer = new UTF8StringWriter();
+    }
+
+    public static int compareStringBinValues(IValueReference a, IValueReference b) throws HyracksDataException {
+        // start+1 and len-1 due to type tag ignore (only interested in String value)
+        return STRING_BINARY_COMPARATOR.compare(a.getByteArray(), a.getStartOffset() + 1, a.getLength() - 1,
+                b.getByteArray(), b.getStartOffset() + 1, b.getLength() - 1);
+    }
+
+    public static boolean isEqual(IValueReference a, IValueReference b) throws HyracksDataException {
+        return (compareStringBinValues(a, b) == 0);
+    }
+
+    public static boolean byteArrayEqual(IValueReference valueRef1, IValueReference valueRef2) {
+        return byteArrayEqual(valueRef1, valueRef2, 3);
+    }
+
+    public static boolean byteArrayEqual(IValueReference valueRef1, IValueReference valueRef2, int dataOffset) {
+        if (valueRef1 == null || valueRef2 == null) {
+            return false;
+        }
+        if (valueRef1 == valueRef2) {
+            return true;
+        }
+
+        int length1 = valueRef1.getLength();
+        int length2 = valueRef2.getLength();
+
+        if (length1 != length2) {
+            return false;
+        }
+
+        byte[] bytes1 = valueRef1.getByteArray();
+        byte[] bytes2 = valueRef2.getByteArray();
+        int start1 = valueRef1.getStartOffset() + dataOffset;
+        int start2 = valueRef2.getStartOffset() + dataOffset;
+
+        int end = start1 + length1 - dataOffset;
+
+        for (int i = start1, j = start2; i < end; i++, j++) {
+            if (bytes1[i] != bytes2[j]) {
+                return false;
+            }
+        }
+
+        return true;
+    }
+
+    public static boolean sameType(ATypeTag typeTag, IVisitablePointable visitablePointable) {
+        return (getTypeTag(visitablePointable) == typeTag);
+    }
+
+    public static ATypeTag getTypeTag(IValueReference visitablePointable) {
+        byte[] bytes = visitablePointable.getByteArray();
+        int s = visitablePointable.getStartOffset();
+        return EnumDeserializer.ATYPETAGDESERIALIZER.deserialize(bytes[s]);
+    }
+
+    /**
+     * @param str
+     *            The input string
+     * @param vs
+     *            The storage buffer
+     * @param writeTag
+     *            Specifying whether a tag for the string should also be written
+     * @throws AlgebricksException
+     */
+    public void serializeString(String str, IMutableValueStorage vs, boolean writeTag) throws AsterixException {
+        vs.reset();
+        try {
+            DataOutput output = vs.getDataOutput();
+            if (writeTag) {
+                output.write(ATypeTag.STRING.serialize());
+            }
+            utf8Writer.writeUTF8(str, output);
+        } catch (IOException e) {
+            throw new AsterixException("Could not serialize " + str);
+        }
+    }
+}

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/functions/records/RecordAddFieldsDescriptor.java
----------------------------------------------------------------------
diff --git a/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/functions/records/RecordAddFieldsDescriptor.java b/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/functions/records/RecordAddFieldsDescriptor.java
new file mode 100644
index 0000000..c26daca
--- /dev/null
+++ b/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/functions/records/RecordAddFieldsDescriptor.java
@@ -0,0 +1,287 @@
+/*
+ * 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.runtime.evaluators.functions.records;
+
+import java.io.IOException;
+import java.util.List;
+
+import org.apache.asterix.builders.RecordBuilder;
+import org.apache.asterix.common.exceptions.AsterixException;
+import org.apache.asterix.dataflow.data.nontagged.comparators.ListItemBinaryComparatorFactory;
+import org.apache.asterix.dataflow.data.nontagged.hash.ListItemBinaryHashFunctionFactory;
+import org.apache.asterix.formats.nontagged.AqlSerializerDeserializerProvider;
+import org.apache.asterix.om.base.ANull;
+import org.apache.asterix.om.functions.AsterixBuiltinFunctions;
+import org.apache.asterix.om.functions.IFunctionDescriptor;
+import org.apache.asterix.om.functions.IFunctionDescriptorFactory;
+import org.apache.asterix.om.pointables.AListVisitablePointable;
+import org.apache.asterix.om.pointables.ARecordVisitablePointable;
+import org.apache.asterix.om.pointables.PointableAllocator;
+import org.apache.asterix.om.pointables.base.DefaultOpenFieldType;
+import org.apache.asterix.om.pointables.base.IVisitablePointable;
+import org.apache.asterix.om.typecomputer.impl.TypeComputerUtils;
+import org.apache.asterix.om.types.AOrderedListType;
+import org.apache.asterix.om.types.ARecordType;
+import org.apache.asterix.om.types.ATypeTag;
+import org.apache.asterix.om.types.BuiltinType;
+import org.apache.asterix.om.types.EnumDeserializer;
+import org.apache.asterix.om.types.IAType;
+import org.apache.asterix.om.types.runtime.RuntimeRecordTypeInfo;
+import org.apache.asterix.runtime.evaluators.base.AbstractScalarFunctionDynamicDescriptor;
+import org.apache.asterix.runtime.evaluators.functions.BinaryHashMap;
+import org.apache.asterix.runtime.evaluators.functions.PointableHelper;
+import org.apache.hyracks.algebricks.common.exceptions.AlgebricksException;
+import org.apache.hyracks.algebricks.core.algebra.functions.FunctionIdentifier;
+import org.apache.hyracks.algebricks.runtime.base.ICopyEvaluator;
+import org.apache.hyracks.algebricks.runtime.base.ICopyEvaluatorFactory;
+import org.apache.hyracks.api.dataflow.value.IBinaryComparator;
+import org.apache.hyracks.api.dataflow.value.IBinaryHashFunction;
+import org.apache.hyracks.api.dataflow.value.ISerializerDeserializer;
+import org.apache.hyracks.api.exceptions.HyracksDataException;
+import org.apache.hyracks.data.std.api.IDataOutputProvider;
+import org.apache.hyracks.data.std.util.ArrayBackedValueStorage;
+import org.apache.hyracks.dataflow.common.data.accessors.IFrameTupleReference;
+
+public class RecordAddFieldsDescriptor extends AbstractScalarFunctionDynamicDescriptor {
+
+    public static final IFunctionDescriptorFactory FACTORY = new IFunctionDescriptorFactory() {
+        public IFunctionDescriptor createFunctionDescriptor() {
+            return new RecordAddFieldsDescriptor();
+        }
+    };
+    private static final long serialVersionUID = 1L;
+    private ARecordType outRecType;
+    private ARecordType inRecType;
+    private AOrderedListType inListType;
+    private IAType inputFieldListItemType;
+
+    public void reset(IAType outType, IAType inType0, IAType inType1) {
+        outRecType = TypeComputerUtils.extractRecordType(outType);
+        inRecType = TypeComputerUtils.extractRecordType(inType0);
+        inListType = TypeComputerUtils.extractOrderedListType(inType1);
+        inputFieldListItemType = inListType.getItemType();
+        if (inputFieldListItemType == null || inputFieldListItemType.getTypeTag() == ATypeTag.ANY) {
+            inputFieldListItemType = DefaultOpenFieldType.NESTED_OPEN_RECORD_TYPE;
+        }
+    }
+
+    @Override
+    public ICopyEvaluatorFactory createEvaluatorFactory(final ICopyEvaluatorFactory[] args) throws AlgebricksException {
+        return new ICopyEvaluatorFactory() {
+
+            private static final long serialVersionUID = 1L;
+            private final byte SER_NULL_TYPE_TAG = ATypeTag.NULL.serialize();
+            private final byte SER_ORDERED_TYPE_TAG = ATypeTag.ORDEREDLIST.serialize();
+            private final byte SER_RECORD_TYPE_TAG = ATypeTag.RECORD.serialize();
+
+            @SuppressWarnings("unchecked")
+            private final ISerializerDeserializer<ANull> nullSerDe = AqlSerializerDeserializerProvider.INSTANCE
+                    .getSerializerDeserializer(BuiltinType.ANULL);
+
+            @Override
+            public ICopyEvaluator createEvaluator(final IDataOutputProvider output) throws AlgebricksException {
+                final PointableAllocator allocator = new PointableAllocator();
+                final IVisitablePointable vp0 = allocator.allocateRecordValue(inRecType);
+                final IVisitablePointable vp1 = allocator.allocateListValue(inListType);
+
+                final ArrayBackedValueStorage abvs0 = new ArrayBackedValueStorage();
+                final ArrayBackedValueStorage abvs1 = new ArrayBackedValueStorage();
+
+                final ICopyEvaluator eval0 = args[0].createEvaluator(abvs0);
+                final ICopyEvaluator eval1 = args[1].createEvaluator(abvs1);
+
+                final ArrayBackedValueStorage fieldNamePointable = new ArrayBackedValueStorage();
+                final ArrayBackedValueStorage fieldValuePointer = new ArrayBackedValueStorage();
+                final PointableHelper pointableHelper = new PointableHelper();
+                try {
+                    pointableHelper.serializeString("field-name", fieldNamePointable, true);
+                    pointableHelper.serializeString("field-value", fieldValuePointer, true);
+                } catch (AsterixException e) {
+                    throw new AlgebricksException(e);
+                }
+
+                return new ICopyEvaluator() {
+                    public static final int TABLE_FRAME_SIZE = 32768; // the default 32k frame size
+                    public static final int TABLE_SIZE = 100; // the default 32k frame size
+                    private final RecordBuilder recordBuilder = new RecordBuilder();
+                    private final RuntimeRecordTypeInfo requiredRecordTypeInfo = new RuntimeRecordTypeInfo();
+
+                    private final IBinaryHashFunction putHashFunc = ListItemBinaryHashFunctionFactory.INSTANCE
+                            .createBinaryHashFunction();
+                    private final IBinaryHashFunction getHashFunc = ListItemBinaryHashFunctionFactory.INSTANCE
+                            .createBinaryHashFunction();
+                    private final BinaryHashMap.BinaryEntry keyEntry = new BinaryHashMap.BinaryEntry();
+                    private final BinaryHashMap.BinaryEntry valEntry = new BinaryHashMap.BinaryEntry();
+                    private final IVisitablePointable tempValReference = allocator.allocateEmpty();
+                    private final IBinaryComparator cmp = ListItemBinaryComparatorFactory.INSTANCE
+                            .createBinaryComparator();
+                    private BinaryHashMap hashMap = new BinaryHashMap(TABLE_SIZE, TABLE_FRAME_SIZE, putHashFunc,
+                            getHashFunc, cmp);
+
+                    @Override
+                    public void evaluate(IFrameTupleReference tuple) throws AlgebricksException {
+                        recordBuilder.reset(outRecType);
+                        requiredRecordTypeInfo.reset(outRecType);
+                        abvs0.reset();
+                        abvs1.reset();
+
+                        eval0.evaluate(tuple);
+                        eval1.evaluate(tuple);
+
+                        if (abvs0.getByteArray()[0] == SER_NULL_TYPE_TAG
+                                || abvs1.getByteArray()[0] == SER_NULL_TYPE_TAG) {
+                            try {
+                                nullSerDe.serialize(ANull.NULL, output.getDataOutput());
+                            } catch (HyracksDataException e) {
+                                throw new AlgebricksException(e);
+                            }
+                            return;
+                        }
+
+                        // Make sure we get a valid record
+                        if (abvs0.getByteArray()[0] != SER_RECORD_TYPE_TAG) {
+                            throw new AlgebricksException("Expected an ordederlist of type " + inRecType + " but "
+                                    + "got "
+                                    + EnumDeserializer.ATYPETAGDESERIALIZER.deserialize(abvs0.getByteArray()[0]));
+                        }
+
+                        // Make sure we get a valid list
+                        if (abvs1.getByteArray()[0] != SER_ORDERED_TYPE_TAG) {
+                            throw new AlgebricksException("Expected an ordederlist of type " + inListType + " but "
+                                    + "got "
+                                    + EnumDeserializer.ATYPETAGDESERIALIZER.deserialize(abvs1.getByteArray()[0]));
+                        }
+
+                        vp0.set(abvs0);
+                        vp1.set(abvs1);
+
+                        try {
+                            ARecordVisitablePointable recordPointable = (ARecordVisitablePointable) vp0;
+                            AListVisitablePointable listPointable = (AListVisitablePointable) vp1;
+
+                            // Initialize our hashmap
+                            int tableSize = recordPointable.getFieldNames().size() + listPointable.getItems().size();
+                            // Construct a new hash table only if table size is larger than the default
+                            // Thus avoiding unnecessary object construction
+                            if (hashMap == null || tableSize > TABLE_SIZE) {
+                                hashMap = new BinaryHashMap(tableSize, TABLE_FRAME_SIZE, putHashFunc, getHashFunc, cmp);
+                            } else {
+                                hashMap.clear();
+                            }
+                            addFields(recordPointable, listPointable);
+                            recordBuilder.write(output.getDataOutput(), true);
+                        } catch (IOException | AsterixException e) {
+                            throw new AlgebricksException(e);
+                        }
+                    }
+
+                    private void addFields(ARecordVisitablePointable inputRecordPointer,
+                            AListVisitablePointable listPointable) throws AlgebricksException {
+                        List<IVisitablePointable> inputRecordFieldNames = inputRecordPointer.getFieldNames();
+                        List<IVisitablePointable> inputRecordFieldValues = inputRecordPointer.getFieldValues();
+                        List<IVisitablePointable> inputFields = listPointable.getItems();
+                        IVisitablePointable namePointable = null;
+                        IVisitablePointable valuePointable = null;
+                        int numInputRecordFields = inputRecordFieldNames.size();
+
+                        try {
+                            // Add original record without duplicate checking
+                            for (int i = 0; i < numInputRecordFields; ++i) {
+                                IVisitablePointable fnp = inputRecordFieldNames.get(i);
+                                IVisitablePointable fvp = inputRecordFieldValues.get(i);
+                                int pos = requiredRecordTypeInfo.getFieldIndex(fnp.getByteArray(),
+                                        fnp.getStartOffset() + 1, fnp.getLength() - 1);
+                                if (pos >= 0) {
+                                    recordBuilder.addField(pos, fvp);
+                                } else {
+                                    recordBuilder.addField(fnp, fvp);
+                                }
+                                keyEntry.set(fnp.getByteArray(), fnp.getStartOffset(), fnp.getLength());
+                                valEntry.set(fvp.getByteArray(), fvp.getStartOffset(), fvp.getLength());
+                                hashMap.put(keyEntry, valEntry);
+                            }
+
+                            // Get the fields from a list of records
+                            for (int i = 0; i < inputFields.size(); i++) {
+                                if (!PointableHelper.sameType(ATypeTag.RECORD, inputFields.get(i))) {
+                                    throw new AsterixException("Expected list of record, got "
+                                            + PointableHelper.getTypeTag(inputFields.get(i)));
+                                }
+                                List<IVisitablePointable> names = ((ARecordVisitablePointable) inputFields.get(i))
+                                        .getFieldNames();
+                                List<IVisitablePointable> values = ((ARecordVisitablePointable) inputFields.get(i))
+                                        .getFieldValues();
+
+                                // Get name and value of the field to be added
+                                // Use loop to account for the cases where users switches the order of the fields
+                                IVisitablePointable fieldName;
+                                for (int j = 0; j < names.size(); j++) {
+                                    fieldName = names.get(j);
+                                    // if fieldName is "field-name" then read the name
+                                    if (PointableHelper.byteArrayEqual(fieldNamePointable, fieldName)) {
+                                        namePointable = values.get(j);
+                                    } else { // otherwise the fieldName is "field-value". Thus, read the value
+                                        valuePointable = values.get(j);
+                                    }
+                                }
+
+                                if (namePointable == null || valuePointable == null) {
+                                    throw new AlgebricksException("Trying to add a null field name or field value");
+                                }
+
+                                // Check that the field being added is a valid field
+                                int pos = requiredRecordTypeInfo.getFieldIndex(namePointable.getByteArray(),
+                                        namePointable.getStartOffset() + 1, namePointable.getLength() - 1);
+
+                                keyEntry.set(namePointable.getByteArray(), namePointable.getStartOffset(),
+                                        namePointable.getLength());
+                                // Check if already in our built record
+                                BinaryHashMap.BinaryEntry entry = hashMap.get(keyEntry);
+                                if (entry != null) {
+                                    tempValReference.set(entry.buf, entry.off, entry.len);
+                                    // If value is not equal throw conflicting duplicate field, otherwise ignore
+                                    if (!PointableHelper.byteArrayEqual(valuePointable, tempValReference)) {
+                                        throw new AlgebricksException("Conflicting duplicate field found.");
+                                    }
+                                } else {
+                                    if (pos > -1) {
+                                        recordBuilder.addField(pos, valuePointable);
+                                    } else {
+                                        recordBuilder.addField(namePointable, valuePointable);
+                                    }
+                                    valEntry.set(valuePointable.getByteArray(), valuePointable.getStartOffset(),
+                                            valuePointable.getLength());
+                                    hashMap.put(keyEntry, valEntry);
+                                }
+                            }
+                        } catch (AsterixException | HyracksDataException e) {
+                            throw new AlgebricksException(e);
+                        }
+                    }
+                };
+            }
+        };
+    }
+
+    @Override
+    public FunctionIdentifier getIdentifier() {
+        return AsterixBuiltinFunctions.ADD_FIELDS;
+    }
+}


[5/6] incubator-asterixdb git commit: ASTERIXDB-1187, ASTERIXDB-1162 and ASTERIXDB-1252 fixes, plus new internal functions

Posted by ti...@apache.org.
http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/tiny-social-example/tiny-social-example.4.query.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/tiny-social-example/tiny-social-example.4.query.aql b/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/tiny-social-example/tiny-social-example.4.query.aql
new file mode 100644
index 0000000..42ab667
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/tiny-social-example/tiny-social-example.4.query.aql
@@ -0,0 +1,29 @@
+/*
+ * 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  : Testing record-remove-fields under different queries.
+* Expected Res : Success
+* Date         : 04 Aug 2015
+*/
+use dataverse TinySocial;
+
+for $r in dataset TweetMessages
+let $result := record-remove-fields($r, ["sender-location", ["user", "screen-name"]])
+order by $result
+return $result

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/results/comparison/deep_equal/documentation-example/documentation-example.1.adm
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/results/comparison/deep_equal/documentation-example/documentation-example.1.adm b/asterix-app/src/test/resources/runtimets/results/comparison/deep_equal/documentation-example/documentation-example.1.adm
new file mode 100644
index 0000000..f32a580
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/results/comparison/deep_equal/documentation-example/documentation-example.1.adm
@@ -0,0 +1 @@
+true
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/results/comparison/deep_equal/documentation-example/documentation-example.2.adm
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/results/comparison/deep_equal/documentation-example/documentation-example.2.adm b/asterix-app/src/test/resources/runtimets/results/comparison/deep_equal/documentation-example/documentation-example.2.adm
new file mode 100644
index 0000000..f32a580
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/results/comparison/deep_equal/documentation-example/documentation-example.2.adm
@@ -0,0 +1 @@
+true
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/results/comparison/deep_equal/documentation-example/documentation-example.3.adm
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/results/comparison/deep_equal/documentation-example/documentation-example.3.adm b/asterix-app/src/test/resources/runtimets/results/comparison/deep_equal/documentation-example/documentation-example.3.adm
new file mode 100644
index 0000000..f32a580
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/results/comparison/deep_equal/documentation-example/documentation-example.3.adm
@@ -0,0 +1 @@
+true
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/results/comparison/deep_equal/documentation-example/documentation-example.4.adm
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/results/comparison/deep_equal/documentation-example/documentation-example.4.adm b/asterix-app/src/test/resources/runtimets/results/comparison/deep_equal/documentation-example/documentation-example.4.adm
new file mode 100644
index 0000000..f32a580
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/results/comparison/deep_equal/documentation-example/documentation-example.4.adm
@@ -0,0 +1 @@
+true
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/results/comparison/deep_equal/documentation-example/documentation-example.5.adm
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/results/comparison/deep_equal/documentation-example/documentation-example.5.adm b/asterix-app/src/test/resources/runtimets/results/comparison/deep_equal/documentation-example/documentation-example.5.adm
new file mode 100644
index 0000000..f32a580
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/results/comparison/deep_equal/documentation-example/documentation-example.5.adm
@@ -0,0 +1 @@
+true
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/results/comparison/deep_equal/open-records-example/open-records-example.3.adm
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/results/comparison/deep_equal/open-records-example/open-records-example.3.adm b/asterix-app/src/test/resources/runtimets/results/comparison/deep_equal/open-records-example/open-records-example.3.adm
new file mode 100644
index 0000000..02e4a84
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/results/comparison/deep_equal/open-records-example/open-records-example.3.adm
@@ -0,0 +1 @@
+false
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/results/records/record-add-fields/documentation-example/documentation-example.1.adm
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/results/records/record-add-fields/documentation-example/documentation-example.1.adm b/asterix-app/src/test/resources/runtimets/results/records/record-add-fields/documentation-example/documentation-example.1.adm
new file mode 100644
index 0000000..c5cecbf
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/results/records/record-add-fields/documentation-example/documentation-example.1.adm
@@ -0,0 +1 @@
+{ "address": { "city": "Irvine", "state": "CA" }, "id": 1, "project": "AsterixDB", "related": [ "Hivestrix", "Preglix", "Apache VXQuery" ], "employment-location": point("30.0,70.0") }

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/results/records/record-add-fields/documentation-example/documentation-example.2.adm
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/results/records/record-add-fields/documentation-example/documentation-example.2.adm b/asterix-app/src/test/resources/runtimets/results/records/record-add-fields/documentation-example/documentation-example.2.adm
new file mode 100644
index 0000000..f0e4583
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/results/records/record-add-fields/documentation-example/documentation-example.2.adm
@@ -0,0 +1 @@
+{ "address": { "city": "Irvine", "state": "CA" }, "id": 1, "project": "AsterixDB", "related": [ "Hivestrix", "Preglix", "Apache VXQuery" ], "employment-type": "visitor" }
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/results/records/record-add-fields/documentation-example/documentation-example.3.adm
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/results/records/record-add-fields/documentation-example/documentation-example.3.adm b/asterix-app/src/test/resources/runtimets/results/records/record-add-fields/documentation-example/documentation-example.3.adm
new file mode 100644
index 0000000..f913d7b
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/results/records/record-add-fields/documentation-example/documentation-example.3.adm
@@ -0,0 +1 @@
+{ "address": { "city": "Irvine", "state": "CA" }, "id": 1, "project": "AsterixDB", "related": [ "Hivestrix", "Preglix", "Apache VXQuery" ], "employment-years": 2 }
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/results/records/record-add-fields/highly-nested-open/highly-nested-open.3.adm
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/results/records/record-add-fields/highly-nested-open/highly-nested-open.3.adm b/asterix-app/src/test/resources/runtimets/results/records/record-add-fields/highly-nested-open/highly-nested-open.3.adm
new file mode 100644
index 0000000..6d78345
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/results/records/record-add-fields/highly-nested-open/highly-nested-open.3.adm
@@ -0,0 +1,4 @@
+{ "id": 1, "animal-info": "Test information", "class": { "id": 1, "fullClassification": { "id": 1, "Kingdom": "Animalia", "lower": { "id": 1, "Phylum": "Chordata", "lower": { "id": 1, "Class": "Mammalia", "lower": { "id": 1, "Order": "Carnivora", "lower": { "id": 1, "Family": "Mustelinae", "lower": { "id": 1, "Genus": "Gulo", "lower": { "id": 1, "Species": "Gulo" } } } } } } } } }
+{ "id": 2, "animal-info": "Test information", "class": { "id": 2, "fullClassification": { "id": 2, "Kingdom": "Animalia", "lower": { "id": 2, "Phylum": "Chordata", "lower": { "id": 2, "Class": "Mammalia", "lower": { "id": 2, "Order": "Artiodactyla", "lower": { "id": 2, "Family": "Giraffidae", "lower": { "id": 2, "Genus": "Okapia", "lower": { "id": 2, "Species": "Johnstoni" } } } } } } } } }
+{ "id": 3, "animal-info": "Test information", "class": { "id": 3, "fullClassification": { "id": 3, "Kingdom": "Animalia", "lower": { "id": 3, "Phylum": "Chordata", "lower": { "id": 3, "Class": "Mammalia", "lower": { "id": 3, "Order": "Atlantogenata", "lower": { "id": 3, "Family": "Afrotheria", "lower": { "id": 3, "Genus": "Paenungulata", "lower": { "id": 3, "Species": "Hyracoidea" } } } } } } } } }
+{ "id": 4, "animal-info": "Test information", "class": { "id": 4, "fullClassification": { "id": 4, "Kingdom": "Animalia", "lower": { "id": 4, "Phylum": "Chordata", "lower": { "id": 4, "Class": "Aves", "lower": { "id": 4, "Order": "Accipitriformes", "lower": { "id": 4, "Family": "Accipitridae", "lower": { "id": 4, "Genus": "Buteo", "lower": { "id": 4, "Species": "Jamaicensis" } } } } } } } } }
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/results/records/record-add-fields/tiny-social-example/tiny-social-example.4.adm
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/results/records/record-add-fields/tiny-social-example/tiny-social-example.4.adm b/asterix-app/src/test/resources/runtimets/results/records/record-add-fields/tiny-social-example/tiny-social-example.4.adm
new file mode 100644
index 0000000..f74a56a
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/results/records/record-add-fields/tiny-social-example/tiny-social-example.4.adm
@@ -0,0 +1,10 @@
+{ "message-text": " like samsung the platform is good", "referred-topics": {{ "samsung", "platform" }}, "send-time": datetime("2011-08-25T10:10:00.000Z"), "sender-location": point("36.21,72.6"), "tweetid": "7", "user": { "screen-name": "ChangEwing_573", "lang": "en", "friends_count": 182, "statuses_count": 394, "name": "Chang Ewing", "followers_count": 32136 }, "fb-author-id": 1 }
+, { "message-text": " like samsung the platform is good", "referred-topics": {{ "samsung", "platform" }}, "send-time": datetime("2011-08-25T10:10:00.000Z"), "sender-location": point("36.21,72.6"), "tweetid": "7", "user": { "screen-name": "ChangEwing_573", "lang": "en", "friends_count": 182, "statuses_count": 394, "name": "Chang Ewing", "followers_count": 32136 }, "fb-author-id": 1 }
+, { "message-text": " like samsung the platform is good", "referred-topics": {{ "samsung", "platform" }}, "send-time": datetime("2011-08-25T10:10:00.000Z"), "sender-location": point("36.21,72.6"), "tweetid": "7", "user": { "screen-name": "ChangEwing_573", "lang": "en", "friends_count": 182, "statuses_count": 394, "name": "Chang Ewing", "followers_count": 32136 }, "fb-author-id": 1 }
+, { "message-text": " like samsung the platform is good", "referred-topics": {{ "samsung", "platform" }}, "send-time": datetime("2011-08-25T10:10:00.000Z"), "sender-location": point("36.21,72.6"), "tweetid": "7", "user": { "screen-name": "ChangEwing_573", "lang": "en", "friends_count": 182, "statuses_count": 394, "name": "Chang Ewing", "followers_count": 32136 }, "fb-author-id": 1 }
+, { "message-text": " like samsung the platform is good", "referred-topics": {{ "samsung", "platform" }}, "send-time": datetime("2011-08-25T10:10:00.000Z"), "sender-location": point("36.21,72.6"), "tweetid": "7", "user": { "screen-name": "ChangEwing_573", "lang": "en", "friends_count": 182, "statuses_count": 394, "name": "Chang Ewing", "followers_count": 32136 }, "fb-author-id": 1 }
+, { "message-text": " like samsung the platform is good", "referred-topics": {{ "samsung", "platform" }}, "send-time": datetime("2011-08-25T10:10:00.000Z"), "sender-location": point("36.21,72.6"), "tweetid": "7", "user": { "screen-name": "ChangEwing_573", "lang": "en", "friends_count": 182, "statuses_count": 394, "name": "Chang Ewing", "followers_count": 32136 }, "fb-author-id": 2 }
+, { "message-text": " like samsung the platform is good", "referred-topics": {{ "samsung", "platform" }}, "send-time": datetime("2011-08-25T10:10:00.000Z"), "sender-location": point("36.21,72.6"), "tweetid": "7", "user": { "screen-name": "ChangEwing_573", "lang": "en", "friends_count": 182, "statuses_count": 394, "name": "Chang Ewing", "followers_count": 32136 }, "fb-author-id": 2 }
+, { "message-text": " like samsung the platform is good", "referred-topics": {{ "samsung", "platform" }}, "send-time": datetime("2011-08-25T10:10:00.000Z"), "sender-location": point("36.21,72.6"), "tweetid": "7", "user": { "screen-name": "ChangEwing_573", "lang": "en", "friends_count": 182, "statuses_count": 394, "name": "Chang Ewing", "followers_count": 32136 }, "fb-author-id": 3 }
+, { "message-text": " like samsung the platform is good", "referred-topics": {{ "samsung", "platform" }}, "send-time": datetime("2011-08-25T10:10:00.000Z"), "sender-location": point("36.21,72.6"), "tweetid": "7", "user": { "screen-name": "ChangEwing_573", "lang": "en", "friends_count": 182, "statuses_count": 394, "name": "Chang Ewing", "followers_count": 32136 }, "fb-author-id": 3 }
+, { "message-text": " like samsung the platform is good", "referred-topics": {{ "samsung", "platform" }}, "send-time": datetime("2011-08-25T10:10:00.000Z"), "sender-location": point("36.21,72.6"), "tweetid": "7", "user": { "screen-name": "ChangEwing_573", "lang": "en", "friends_count": 182, "statuses_count": 394, "name": "Chang Ewing", "followers_count": 32136 }, "fb-author-id": 5 }
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/results/records/record-merge/documentation-example/documentation-example.1.adm
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/results/records/record-merge/documentation-example/documentation-example.1.adm b/asterix-app/src/test/resources/runtimets/results/records/record-merge/documentation-example/documentation-example.1.adm
new file mode 100644
index 0000000..828f1d9
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/results/records/record-merge/documentation-example/documentation-example.1.adm
@@ -0,0 +1 @@
+{ "address": { "city": "Irvine", "state": "CA" }, "id": 1, "project": "AsterixDB", "related": [ "Hivestrix", "Preglix", "Apache VXQuery" ], "user_id": 22, "employer": "UC Irvine", "employment-type": "visitor" }
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/results/records/record-merge/documentation-example/documentation-example.2.adm
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/results/records/record-merge/documentation-example/documentation-example.2.adm b/asterix-app/src/test/resources/runtimets/results/records/record-merge/documentation-example/documentation-example.2.adm
new file mode 100644
index 0000000..c9d7d57
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/results/records/record-merge/documentation-example/documentation-example.2.adm
@@ -0,0 +1 @@
+{ "address": { "city": "Irvine", "state": "CA" }, "id": 1, "project": "AsterixDB", "related": [ "Hivestrix", "Preglix", "Apache VXQuery" ], "user_id": 22, "employer": "UC Irvine", "employment-location": point("30.0,70.0") }
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/results/records/record-merge/documentation-example/documentation-example.3.adm
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/results/records/record-merge/documentation-example/documentation-example.3.adm b/asterix-app/src/test/resources/runtimets/results/records/record-merge/documentation-example/documentation-example.3.adm
new file mode 100644
index 0000000..e452429
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/results/records/record-merge/documentation-example/documentation-example.3.adm
@@ -0,0 +1 @@
+{ "address": { "city": "Irvine", "state": "CA" }, "id": 1, "project": "AsterixDB", "related": [ "Hivestrix", "Preglix", "Apache VXQuery" ], "user_id": 22, "employer": "UC Irvine" }
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/results/records/record-merge/highly-nested-open/highly-nested-open.3.adm
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/results/records/record-merge/highly-nested-open/highly-nested-open.3.adm b/asterix-app/src/test/resources/runtimets/results/records/record-merge/highly-nested-open/highly-nested-open.3.adm
new file mode 100644
index 0000000..6d78345
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/results/records/record-merge/highly-nested-open/highly-nested-open.3.adm
@@ -0,0 +1,4 @@
+{ "id": 1, "animal-info": "Test information", "class": { "id": 1, "fullClassification": { "id": 1, "Kingdom": "Animalia", "lower": { "id": 1, "Phylum": "Chordata", "lower": { "id": 1, "Class": "Mammalia", "lower": { "id": 1, "Order": "Carnivora", "lower": { "id": 1, "Family": "Mustelinae", "lower": { "id": 1, "Genus": "Gulo", "lower": { "id": 1, "Species": "Gulo" } } } } } } } } }
+{ "id": 2, "animal-info": "Test information", "class": { "id": 2, "fullClassification": { "id": 2, "Kingdom": "Animalia", "lower": { "id": 2, "Phylum": "Chordata", "lower": { "id": 2, "Class": "Mammalia", "lower": { "id": 2, "Order": "Artiodactyla", "lower": { "id": 2, "Family": "Giraffidae", "lower": { "id": 2, "Genus": "Okapia", "lower": { "id": 2, "Species": "Johnstoni" } } } } } } } } }
+{ "id": 3, "animal-info": "Test information", "class": { "id": 3, "fullClassification": { "id": 3, "Kingdom": "Animalia", "lower": { "id": 3, "Phylum": "Chordata", "lower": { "id": 3, "Class": "Mammalia", "lower": { "id": 3, "Order": "Atlantogenata", "lower": { "id": 3, "Family": "Afrotheria", "lower": { "id": 3, "Genus": "Paenungulata", "lower": { "id": 3, "Species": "Hyracoidea" } } } } } } } } }
+{ "id": 4, "animal-info": "Test information", "class": { "id": 4, "fullClassification": { "id": 4, "Kingdom": "Animalia", "lower": { "id": 4, "Phylum": "Chordata", "lower": { "id": 4, "Class": "Aves", "lower": { "id": 4, "Order": "Accipitriformes", "lower": { "id": 4, "Family": "Accipitridae", "lower": { "id": 4, "Genus": "Buteo", "lower": { "id": 4, "Species": "Jamaicensis" } } } } } } } } }
\ No newline at end of file


[6/6] incubator-asterixdb git commit: ASTERIXDB-1187, ASTERIXDB-1162 and ASTERIXDB-1252 fixes, plus new internal functions

Posted by ti...@apache.org.
ASTERIXDB-1187, ASTERIXDB-1162 and ASTERIXDB-1252 fixes, plus new internal functions

This change contains the following updates and fixes:
- New deep-equality function which also handles numeric equality,
e.g., [2.0, 2, 1.0] == [2, 2, 1].
- New internal functions for record manipulation, including add and remove fields from records
- Fixes for ASTERIXDB-1187: The RecordMergeDescriptor does not fully support
open record merge. Merging records with open fields results in "NullPointerException".
- Fixes to address issue ASTERIXDB-1162: dealing with closed or partly closed record
added to an open record field.
- Fixes issue ASTERIXDB-1252: Problems with Autogenerated Key

Change-Id: I3621ebdd71c7cd91b50d77a972ad863cea7fcbc2
Reviewed-on: https://asterix-gerrit.ics.uci.edu/298
Tested-by: Jenkins <je...@fulliautomatix.ics.uci.edu>
Reviewed-by: Till Westmann <ti...@apache.org>


Project: http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/repo
Commit: http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/commit/4053f390
Tree: http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/tree/4053f390
Diff: http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/diff/4053f390

Branch: refs/heads/master
Commit: 4053f390af30d7d8cbf906fd874291a28a1b1c0b
Parents: 633acc4
Author: Heri Ramampiaro <he...@gmail.com>
Authored: Mon Jan 11 00:21:39 2016 +0100
Committer: Till Westmann <ti...@apache.org>
Committed: Mon Jan 11 08:16:05 2016 -0800

----------------------------------------------------------------------
 .../comparison/deep_equal/DeepEqualQueries.xml  |  28 +
 .../deep-equal.1.query.aql                      |  28 +
 .../deep-equal.2.query.aql                      |  19 +
 .../deep-equal.3.query.aql                      |  19 +
 .../deep-equal.4.query.aql                      |  19 +
 .../deep-equal.5.query.aql                      |  19 +
 .../open-records-example/deep-equal.1.ddl.aql   |  45 ++
 .../deep-equal.2.update.aql                     |  38 ++
 .../open-records-example/deep-equal.3.query.aql |  22 +
 .../queries/records/RecordsQueries.xml          |  46 ++
 .../documentation-example.1.query.aql           |  28 +
 .../documentation-example.2.query.aql           |  28 +
 .../documentation-example.3.query.aql           |  28 +
 .../highly-nested-open.1.ddl.aql                |  72 ++
 .../highly-nested-open.2.update.aql             |  27 +
 .../highly-nested-open.3.query.aql              |  30 +
 .../tiny-social-example.1.ddl.aql               |  68 ++
 .../tiny-social-example.2.ddl.aql               |  43 ++
 .../tiny-social-example.3.update.aql            |  36 +
 .../tiny-social-example.4.query.aql             |  30 +
 .../documentation-example.1.query.aql           |  28 +
 .../documentation-example.2.query.aql           |  32 +
 .../documentation-example.3.query.aql           |  32 +
 .../highly-nested-open.1.ddl.aql                |  72 ++
 .../highly-nested-open.2.update.aql             |  27 +
 .../highly-nested-open.3.query.aql              |  30 +
 .../tiny-social-example.1.ddl.aql               |  67 ++
 .../tiny-social-example.2.ddl.aql               |  42 ++
 .../tiny-social-example.3.update.aql            |  36 +
 .../tiny-social-example.4.query.aql             |  30 +
 .../documentation-example.1.query.aql           |  28 +
 .../documentation-example.2.query.aql           |  28 +
 .../documentation-example.3.query.aql           |  28 +
 .../highly-nested-open.1.ddl.aql                |  72 ++
 .../highly-nested-open.2.update.aql             |  27 +
 .../highly-nested-open.3.query.aql              |  29 +
 .../tiny-social-example.1.ddl.aql               |  67 ++
 .../tiny-social-example.2.ddl.aql               |  42 ++
 .../tiny-social-example.3.update.aql            |  36 +
 .../tiny-social-example.4.query.aql             |  29 +
 .../documentation-example.1.adm                 |   1 +
 .../documentation-example.2.adm                 |   1 +
 .../documentation-example.3.adm                 |   1 +
 .../documentation-example.4.adm                 |   1 +
 .../documentation-example.5.adm                 |   1 +
 .../open-records-example.3.adm                  |   1 +
 .../documentation-example.1.adm                 |   1 +
 .../documentation-example.2.adm                 |   1 +
 .../documentation-example.3.adm                 |   1 +
 .../highly-nested-open/highly-nested-open.3.adm |   4 +
 .../tiny-social-example.4.adm                   |  10 +
 .../documentation-example.1.adm                 |   1 +
 .../documentation-example.2.adm                 |   1 +
 .../documentation-example.3.adm                 |   1 +
 .../highly-nested-open/highly-nested-open.3.adm |   4 +
 .../tiny-social-example.4.adm                   | 180 +++++
 .../documentation-example.1.adm                 |   1 +
 .../documentation-example.2.adm                 |   1 +
 .../documentation-example.3.adm                 |   1 +
 .../highly-nested-open/highly-nested-open.3.adm |   4 +
 .../tiny-social-example.4.adm                   |  12 +
 .../src/test/resources/runtimets/testsuite.xml  |   8 +-
 asterix-doc/src/site/markdown/aql/functions.md  | 679 +++++++++++--------
 .../asterix/builders/IARecordBuilder.java       |   2 +-
 .../AqlSerializerDeserializerProvider.java      |  10 +-
 .../om/functions/AsterixBuiltinFunctions.java   |  31 +-
 .../pointables/ARecordVisitablePointable.java   |  10 +-
 .../om/pointables/cast/ARecordCaster.java       |  16 +-
 .../impl/RecordAddFieldsTypeComputer.java       | 185 +++++
 .../impl/RecordMergeTypeComputer.java           |  84 ++-
 .../impl/RecordRemoveFieldsTypeComputer.java    | 328 +++++++++
 .../om/typecomputer/impl/TypeComputerUtils.java |  75 ++
 .../om/types/hierachy/ATypeHierarchy.java       |  18 +-
 .../comparisons/DeepEqualAssessor.java          |  83 +++
 .../functions/DeepEqualityDescriptor.java       | 113 +++
 .../evaluators/functions/PointableHelper.java   | 129 ++++
 .../records/RecordAddFieldsDescriptor.java      | 287 ++++++++
 .../records/RecordMergeDescriptor.java          | 125 ++--
 .../records/RecordRemoveFieldsDescriptor.java   |  68 ++
 .../records/RecordRemoveFieldsEvalFactory.java  | 235 +++++++
 .../visitors/DeepEqualityVisitor.java           | 114 ++++
 .../visitors/DeepEqualityVisitorHelper.java     |  59 ++
 .../visitors/ListDeepEqualityChecker.java       | 142 ++++
 .../visitors/RecordDeepEqualityChecker.java     | 112 +++
 .../runtime/formats/NonTaggedDataFormat.java    | 141 ++--
 85 files changed, 4220 insertions(+), 518 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/DeepEqualQueries.xml
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/DeepEqualQueries.xml b/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/DeepEqualQueries.xml
new file mode 100644
index 0000000..83d0061
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/DeepEqualQueries.xml
@@ -0,0 +1,28 @@
+<!--
+ ! 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-case FilePath="comparison/deep_equal">
+        <compilation-unit name="documentation-example">
+            <output-dir compare="Text">documentation-example</output-dir>
+        </compilation-unit>
+    </test-case>
+    <test-case FilePath="comparison/deep_equal">
+        <compilation-unit name="open-records-example">
+            <output-dir compare="Text">open-records-example</output-dir>
+        </compilation-unit>
+    </test-case>
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/documentation-example/deep-equal.1.query.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/documentation-example/deep-equal.1.query.aql b/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/documentation-example/deep-equal.1.query.aql
new file mode 100644
index 0000000..85e24c3
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/documentation-example/deep-equal.1.query.aql
@@ -0,0 +1,28 @@
+/*
+ * 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.
+ */
+let $r1 := {"id":1,
+    "project":"AsterixDB",
+    "address":{"city":"Irvine", "state":"CA"},
+    "related":["Hivestrix", "Preglix", "Apache VXQuery"] }
+
+let $r2 := {"id":1,
+    "project":"AsterixDB",
+    "address":{"city":"Irvine", "state":"CA"},
+    "related":["Hivestrix", "Preglix", "Apache VXQuery"] }
+return deep-equal($r1, $r2)
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/documentation-example/deep-equal.2.query.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/documentation-example/deep-equal.2.query.aql b/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/documentation-example/deep-equal.2.query.aql
new file mode 100644
index 0000000..d41702e
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/documentation-example/deep-equal.2.query.aql
@@ -0,0 +1,19 @@
+/*
+ * 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.
+ */
+ deep-equal(["Hivestrix", "Preglix", "Apache VXQuery"], ["Hivestrix", "Preglix", "Apache VXQuery"]);
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/documentation-example/deep-equal.3.query.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/documentation-example/deep-equal.3.query.aql b/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/documentation-example/deep-equal.3.query.aql
new file mode 100644
index 0000000..7279b64
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/documentation-example/deep-equal.3.query.aql
@@ -0,0 +1,19 @@
+/*
+ * 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.
+ */
+deep-equal({{{"s":"Hivestrix", "v":"0.1.0"}, "Preglix", "Apache VXQuery"}}, {{ "Apache VXQuery",{"s":"Hivestrix", "v":"0.1.0"}, "Preglix"}});
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/documentation-example/deep-equal.4.query.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/documentation-example/deep-equal.4.query.aql b/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/documentation-example/deep-equal.4.query.aql
new file mode 100644
index 0000000..333c9d6
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/documentation-example/deep-equal.4.query.aql
@@ -0,0 +1,19 @@
+/*
+ * 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.
+ */
+deep-equal("test","test");
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/documentation-example/deep-equal.5.query.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/documentation-example/deep-equal.5.query.aql b/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/documentation-example/deep-equal.5.query.aql
new file mode 100644
index 0000000..06fa4cd
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/documentation-example/deep-equal.5.query.aql
@@ -0,0 +1,19 @@
+/*
+ * 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.
+ */
+deep-equal([1,2.0,3],[1,2,3.0]);
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/open-records-example/deep-equal.1.ddl.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/open-records-example/deep-equal.1.ddl.aql b/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/open-records-example/deep-equal.1.ddl.aql
new file mode 100644
index 0000000..aa26843
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/open-records-example/deep-equal.1.ddl.aql
@@ -0,0 +1,45 @@
+/*
+ * 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.
+ */
+
+create dataverse feeds if not exists;
+use dataverse feeds;
+
+drop dataset SourceInfo if exists
+drop type SourceType if exists
+create type SourceType as open {
+   id: int32
+}
+
+create dataset SourceInfo(SourceType)
+primary key id;
+
+drop dataset StreamDocuments if exists
+drop type StreamType if exists
+create type StreamType as open {
+        doc_id: string,
+        stream_id: string,
+        title_cleansed: string,
+        body_cleansed: string,
+        dir_name: string,
+        anchor_cleansed: string,
+        language: string,
+        schost: string
+}
+create dataset StreamDocuments(StreamType)
+primary key doc_id;
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/open-records-example/deep-equal.2.update.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/open-records-example/deep-equal.2.update.aql b/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/open-records-example/deep-equal.2.update.aql
new file mode 100644
index 0000000..2867286
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/open-records-example/deep-equal.2.update.aql
@@ -0,0 +1,38 @@
+/*
+ * 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.
+ */
+use dataverse feeds;
+insert into dataset StreamDocuments (
+       { "doc_id": "doc3",
+        "stream_id": "3dd",
+        "title_cleansed": "",
+        "body_cleansed": "ccc aharon barak born in Israel jeremy mckinnon",
+        "dir_name": "2010-11-24-00",
+        "anchor_cleansed": "",
+        "language": "EN",
+        "schost": "http...",
+        "name":"social"
+});
+
+insert into dataset SourceInfo (
+{
+"id": 1,
+"name":"social",
+"description":"social media data"
+}
+);
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/open-records-example/deep-equal.3.query.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/open-records-example/deep-equal.3.query.aql b/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/open-records-example/deep-equal.3.query.aql
new file mode 100644
index 0000000..0355e31
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/comparison/deep_equal/open-records-example/deep-equal.3.query.aql
@@ -0,0 +1,22 @@
+/*
+ * 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.
+ */
+use dataverse feeds;
+for $x in dataset StreamDocuments
+for $extra in dataset SourceInfo
+return deep-equal($x,$extra);
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/records/RecordsQueries.xml
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/records/RecordsQueries.xml b/asterix-app/src/test/resources/runtimets/queries/records/RecordsQueries.xml
index 93a3a99..283120f 100644
--- a/asterix-app/src/test/resources/runtimets/queries/records/RecordsQueries.xml
+++ b/asterix-app/src/test/resources/runtimets/queries/records/RecordsQueries.xml
@@ -129,3 +129,49 @@
                 <expected-error>org.apache.asterix.common.exceptions.AsterixException</expected-error>
             </compilation-unit>
         </test-case>
+        <!-- RECORD MANIPULATION TESTS -->
+        <test-case FilePath="records/record-merge">
+            <compilation-unit name="documentation-example">
+                <output-dir compare="Text">documentation-example</output-dir>
+            </compilation-unit>
+        </test-case>
+        <test-case FilePath="records/record-merge">
+            <compilation-unit name="tiny-social-example-only-records">
+                <output-dir compare="Text">tiny-social-example-only-records</output-dir>
+            </compilation-unit>
+        </test-case>
+        <test-case FilePath="records/record-merge">
+            <compilation-unit name="highly-nested-open">
+                <output-dir compare="Text">highly-nested-open</output-dir>
+            </compilation-unit>
+        </test-case>
+        <test-case FilePath="records/record-add-fields">
+            <compilation-unit name="documentation-example">
+                <output-dir compare="Text">documentation-example</output-dir>
+            </compilation-unit>
+        </test-case>
+        <test-case FilePath="records/record-add-fields">
+            <compilation-unit name="tiny-social-example-only-records">
+                <output-dir compare="Text">tiny-social-example-only-records</output-dir>
+            </compilation-unit>
+        </test-case>
+        <test-case FilePath="records/record-add-fields">
+            <compilation-unit name="highly-nested-open">
+                <output-dir compare="Text">highly-nested-open</output-dir>
+            </compilation-unit>
+        </test-case>
+        <test-case FilePath="records/record-remove-fields">
+            <compilation-unit name="documentation-example">
+                <output-dir compare="Text">documentation-example</output-dir>
+            </compilation-unit>
+        </test-case>
+        <test-case FilePath="records/record-remove-fields">
+            <compilation-unit name="tiny-social-example-only-records">
+                <output-dir compare="Text">tiny-social-example-only-records</output-dir>
+            </compilation-unit>
+        </test-case>
+        <test-case FilePath="records/record-remove-fields">
+            <compilation-unit name="highly-nested-open">
+                <output-dir compare="Text">highly-nested-open</output-dir>
+            </compilation-unit>
+        </test-case>

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/documentation-example/documentation-example.1.query.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/documentation-example/documentation-example.1.query.aql b/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/documentation-example/documentation-example.1.query.aql
new file mode 100644
index 0000000..5e76429
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/documentation-example/documentation-example.1.query.aql
@@ -0,0 +1,28 @@
+/*
+ * 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  : Testing record-add-fields under different queries.
+* Expected Res : Success
+* Date         : 04 Aug 2015
+*/
+        let $r1 := {"id":1,
+            "project":"AsterixDB",
+            "address":{"city":"Irvine", "state":"CA"},
+            "related":["Hivestrix", "Preglix", "Apache VXQuery"] }
+        return record-add-fields($r1, [{"field-name":"employment-location", "field-value":create-point(30.0,70.0)}])

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/documentation-example/documentation-example.2.query.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/documentation-example/documentation-example.2.query.aql b/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/documentation-example/documentation-example.2.query.aql
new file mode 100644
index 0000000..856aed2
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/documentation-example/documentation-example.2.query.aql
@@ -0,0 +1,28 @@
+/*
+ * 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  : Testing record-add-fields under different queries.
+* Expected Res : Success
+* Date         : 04 Aug 2015
+*/
+        let $r1 := {"id":1,
+            "project":"AsterixDB",
+            "address":{"city":"Irvine", "state":"CA"},
+            "related":["Hivestrix", "Preglix", "Apache VXQuery"] }
+        return record-add-fields($r1, [{"field-name":"employment-type", "field-value":"visitor"}])
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/documentation-example/documentation-example.3.query.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/documentation-example/documentation-example.3.query.aql b/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/documentation-example/documentation-example.3.query.aql
new file mode 100644
index 0000000..aad677b
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/documentation-example/documentation-example.3.query.aql
@@ -0,0 +1,28 @@
+/*
+ * 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  : Testing record-add-fields under different queries.
+* Expected Res : Success
+* Date         : 04 Aug 2015
+*/
+        let $r1 := {"id":1,
+            "project":"AsterixDB",
+            "address":{"city":"Irvine", "state":"CA"},
+            "related":["Hivestrix", "Preglix", "Apache VXQuery"] }
+        return record-add-fields($r1, [{"field-name":"employment-years", "field-value":2}])

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/highly-nested-open/highly-nested-open.1.ddl.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/highly-nested-open/highly-nested-open.1.ddl.aql b/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/highly-nested-open/highly-nested-open.1.ddl.aql
new file mode 100644
index 0000000..94556f0
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/highly-nested-open/highly-nested-open.1.ddl.aql
@@ -0,0 +1,72 @@
+/*
+ * 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  : Testing record-add-fields under different queries.
+* Expected Res : Success
+* Date         : 04 Aug 2015
+*/
+drop dataverse test if exists;
+create dataverse test;
+
+use dataverse test;
+
+create type S as open{
+    id: int64
+}
+
+create type GS as open{
+    id: int64,
+    Genus: string
+}
+
+create type FGS as open{
+    id: int64,
+    Family: string
+}
+
+create type OFGS as open{
+    id: int64,
+    Order: string
+}
+
+create type COFGS as open{
+    id: int64,
+    Class: string
+}
+
+create type PCOFGS as open{
+    id: int64,
+    Phylum: string
+}
+
+create type KPCOFGS as open{
+    id: int64,
+    Kingdom: string
+}
+
+create type Classification as open{
+    id: int64
+}
+
+create type Animal as open{
+    id: int64
+}
+
+create dataset Animals(Animal)
+primary key id;

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/highly-nested-open/highly-nested-open.2.update.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/highly-nested-open/highly-nested-open.2.update.aql b/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/highly-nested-open/highly-nested-open.2.update.aql
new file mode 100644
index 0000000..cab8eb7
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/highly-nested-open/highly-nested-open.2.update.aql
@@ -0,0 +1,27 @@
+/*
+ * 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  : Testing record-add-fields under different queries.
+* Expected Res : Success
+* Date         : 04 Aug 2015
+*/
+use dataverse test;
+
+load dataset Animals using localfs
+(("path"="asterix_nc1://data/classifications/animals.adm"),("format"="adm"));

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/highly-nested-open/highly-nested-open.3.query.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/highly-nested-open/highly-nested-open.3.query.aql b/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/highly-nested-open/highly-nested-open.3.query.aql
new file mode 100644
index 0000000..fb937e4
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/highly-nested-open/highly-nested-open.3.query.aql
@@ -0,0 +1,30 @@
+/*
+ * 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  : Testing record-add-fields under different queries.
+* Expected Res : Success
+* Date         : 04 Aug 2015
+*/
+use dataverse test;
+
+let $rec:=[{"field-name":"animal-info", "field-value":"Test information"}]
+for $test in dataset Animals
+let $result := record-add-fields($test, $rec)
+order by $result.id
+return $result;
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/tiny-social-example/tiny-social-example.1.ddl.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/tiny-social-example/tiny-social-example.1.ddl.aql b/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/tiny-social-example/tiny-social-example.1.ddl.aql
new file mode 100644
index 0000000..5aedc05
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/tiny-social-example/tiny-social-example.1.ddl.aql
@@ -0,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.
+ */
+/*
+* Description  : Testing record-add-fields under different queries.
+* Expected Res : Success
+* Date         : 04 Aug 2015
+*/
+
+drop dataverse TinySocial if exists;
+create dataverse TinySocial;
+use dataverse TinySocial;
+
+create type TwitterUserType as open {
+        screen-name: string,
+        lang: string,
+        friends_count: int64,
+        statuses_count: int64,
+        name: string,
+        followers_count: int64
+}
+
+create type TweetMessageType as closed {
+        tweetid: string,
+        user: TwitterUserType,
+        sender-location: point?,
+        send-time: datetime,
+        referred-topics: {{ string }},
+        message-text: string
+}
+
+create type EmploymentType as open {
+        organization-name: string,
+        start-date: date,
+        end-date: date?
+}
+
+create type FacebookUserType as closed {
+        id: int64,
+        alias: string,
+        name: string,
+        user-since: datetime,
+        friend-ids: {{ int64 }},
+        employment: [EmploymentType]
+}
+
+create type FacebookMessageType as closed {
+        message-id: int64,
+        author-id: int64,
+        in-response-to: int64?,
+        sender-location: point?,
+        message: string
+}

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/tiny-social-example/tiny-social-example.2.ddl.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/tiny-social-example/tiny-social-example.2.ddl.aql b/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/tiny-social-example/tiny-social-example.2.ddl.aql
new file mode 100644
index 0000000..c47f048
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/tiny-social-example/tiny-social-example.2.ddl.aql
@@ -0,0 +1,43 @@
+/*
+ * 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  : Testing record-add-fields under different queries.
+* Expected Res : Success
+* Date         : 04 Aug 2015
+*/
+
+use dataverse TinySocial;
+
+create dataset FacebookUsers(FacebookUserType)
+primary key id;
+
+create dataset FacebookMessages(FacebookMessageType)
+primary key message-id;
+
+create dataset TwitterUsers(TwitterUserType)
+primary key screen-name;
+
+create dataset TweetMessages(TweetMessageType)
+primary key tweetid
+hints(cardinality=100);
+
+create index fbUserSinceIdx on FacebookUsers(user-since);
+create index fbAuthorIdx on FacebookMessages(author-id) type btree;
+create index fbSenderLocIndex on FacebookMessages(sender-location) type rtree;
+create index fbMessageIdx on FacebookMessages(message) type keyword;
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/tiny-social-example/tiny-social-example.3.update.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/tiny-social-example/tiny-social-example.3.update.aql b/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/tiny-social-example/tiny-social-example.3.update.aql
new file mode 100644
index 0000000..80f1615
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/tiny-social-example/tiny-social-example.3.update.aql
@@ -0,0 +1,36 @@
+/*
+ * 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  : Testing record-add-fields under different queries.
+* Expected Res : Success
+* Date         : 04 Aug 2015
+*/
+use dataverse TinySocial;
+
+load dataset FacebookUsers using localfs
+(("path"="nc1://data/tinysocial/fbu.adm"),("format"="adm"));
+
+load dataset FacebookMessages using localfs
+(("path"="nc1://data/tinysocial/fbm.adm"),("format"="adm"));
+
+load dataset TwitterUsers using localfs
+(("path"="nc1://data/tinysocial/twu.adm"),("format"="adm"));
+
+load dataset TweetMessages using localfs
+(("path"="nc1://data/tinysocial/twm.adm"),("format"="adm"));

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/tiny-social-example/tiny-social-example.4.query.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/tiny-social-example/tiny-social-example.4.query.aql b/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/tiny-social-example/tiny-social-example.4.query.aql
new file mode 100644
index 0000000..ec7c77d
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/records/record-add-fields/tiny-social-example/tiny-social-example.4.query.aql
@@ -0,0 +1,30 @@
+/*
+ * 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  : Testing record-add-fields under different queries.
+* Expected Res : Success
+* Date         : 04 Aug 2015
+*/
+use dataverse TinySocial;
+
+for $r in dataset TweetMessages
+for $f in dataset FacebookMessages
+let $result := record-add-fields($r, [{"field-name":"fb-author-id", "field-value":$f.author-id}])
+order by $result
+return $result

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/records/record-merge/documentation-example/documentation-example.1.query.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/records/record-merge/documentation-example/documentation-example.1.query.aql b/asterix-app/src/test/resources/runtimets/queries/records/record-merge/documentation-example/documentation-example.1.query.aql
new file mode 100644
index 0000000..7abb690
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/records/record-merge/documentation-example/documentation-example.1.query.aql
@@ -0,0 +1,28 @@
+/*
+ * 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  : record-merge under different queries.
+* Expected Res : Success
+* Date         : 04 Aug 2015
+*/
+let $r1 := {"id":1, "project":"AsterixDB",
+"address":{"city":"Irvine", "state":"CA"}, "related":["Hivestrix", "Preglix", "Apache VXQuery"]}
+let $r2 := {"user_id": 22, "employer": "UC Irvine", "employment-type": "visitor" }
+let $result := record-merge($r1, $r2)
+return $result

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/records/record-merge/documentation-example/documentation-example.2.query.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/records/record-merge/documentation-example/documentation-example.2.query.aql b/asterix-app/src/test/resources/runtimets/queries/records/record-merge/documentation-example/documentation-example.2.query.aql
new file mode 100644
index 0000000..137cdfb
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/records/record-merge/documentation-example/documentation-example.2.query.aql
@@ -0,0 +1,32 @@
+/*
+ * 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  : record-merge under different queries.
+* Expected Res : Success
+* Date         : 04 Aug 2015
+*/
+        let $r1 := {"id":1,
+              "project":"AsterixDB",
+              "address":{"city":"Irvine", "state":"CA"},
+              "related":["Hivestrix", "Preglix", "Apache VXQuery"] }
+
+        let $r2 := {"user_id": 22,
+              "employer": "UC Irvine",
+              "employment-location": create-point(30.0,70.0) }
+        return  record-merge($r1, $r2)
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/records/record-merge/documentation-example/documentation-example.3.query.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/records/record-merge/documentation-example/documentation-example.3.query.aql b/asterix-app/src/test/resources/runtimets/queries/records/record-merge/documentation-example/documentation-example.3.query.aql
new file mode 100644
index 0000000..92ee00f
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/records/record-merge/documentation-example/documentation-example.3.query.aql
@@ -0,0 +1,32 @@
+/*
+ * 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  : record-merge under different queries.
+* Expected Res : Success
+* Date         : 04 Aug 2015
+*/
+        let $r1 := {"id":1,
+              "project":"AsterixDB",
+              "address":{"city":"Irvine", "state":"CA"},
+              "related":["Hivestrix", "Preglix", "Apache VXQuery"] }
+
+        let $r2 := {"user_id": 22,
+              "employer": "UC Irvine",
+              "address":{"city":"Irvine", "state":"CA"} }
+        return  record-merge($r1, $r2)

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/records/record-merge/highly-nested-open/highly-nested-open.1.ddl.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/records/record-merge/highly-nested-open/highly-nested-open.1.ddl.aql b/asterix-app/src/test/resources/runtimets/queries/records/record-merge/highly-nested-open/highly-nested-open.1.ddl.aql
new file mode 100644
index 0000000..d4af896
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/records/record-merge/highly-nested-open/highly-nested-open.1.ddl.aql
@@ -0,0 +1,72 @@
+/*
+ * 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  : Testing record-merge under different queries.
+* Expected Res : Success
+* Date         : 04 Aug 2015
+*/
+drop dataverse test if exists;
+create dataverse test;
+
+use dataverse test;
+
+create type S as open{
+    id: int64
+}
+
+create type GS as open{
+    id: int64,
+    Genus: string
+}
+
+create type FGS as open{
+    id: int64,
+    Family: string
+}
+
+create type OFGS as open{
+    id: int64,
+    Order: string
+}
+
+create type COFGS as open{
+    id: int64,
+    Class: string
+}
+
+create type PCOFGS as open{
+    id: int64,
+    Phylum: string
+}
+
+create type KPCOFGS as open{
+    id: int64,
+    Kingdom: string
+}
+
+create type Classification as open{
+    id: int64
+}
+
+create type Animal as open{
+    id: int64
+}
+
+create dataset Animals(Animal)
+primary key id;

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/records/record-merge/highly-nested-open/highly-nested-open.2.update.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/records/record-merge/highly-nested-open/highly-nested-open.2.update.aql b/asterix-app/src/test/resources/runtimets/queries/records/record-merge/highly-nested-open/highly-nested-open.2.update.aql
new file mode 100644
index 0000000..7db2401
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/records/record-merge/highly-nested-open/highly-nested-open.2.update.aql
@@ -0,0 +1,27 @@
+/*
+ * 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  : Testing record-merge under different queries.
+* Expected Res : Success
+* Date         : 04 Aug 2015
+*/
+use dataverse test;
+
+load dataset Animals using localfs
+(("path"="asterix_nc1://data/classifications/animals.adm"),("format"="adm"));

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/records/record-merge/highly-nested-open/highly-nested-open.3.query.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/records/record-merge/highly-nested-open/highly-nested-open.3.query.aql b/asterix-app/src/test/resources/runtimets/queries/records/record-merge/highly-nested-open/highly-nested-open.3.query.aql
new file mode 100644
index 0000000..70a3ad5
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/records/record-merge/highly-nested-open/highly-nested-open.3.query.aql
@@ -0,0 +1,30 @@
+/*
+ * 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  : Testing record-merge under different queries.
+* Expected Res : Success
+* Date         : 04 Aug 2015
+*/
+use dataverse test;
+
+let $rec:={"animal-info": "Test information"}
+for $test in dataset Animals
+let $result := record-merge($test, $rec)
+order by $result.id
+return $result;
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/records/record-merge/tiny-social-example/tiny-social-example.1.ddl.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/records/record-merge/tiny-social-example/tiny-social-example.1.ddl.aql b/asterix-app/src/test/resources/runtimets/queries/records/record-merge/tiny-social-example/tiny-social-example.1.ddl.aql
new file mode 100644
index 0000000..fbc09c9
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/records/record-merge/tiny-social-example/tiny-social-example.1.ddl.aql
@@ -0,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.
+ */
+/*
+* Description  : Testing record-merge under different queries.
+* Expected Res : Success
+* Date         : 04 Aug 2015
+*/
+drop dataverse TinySocial if exists;
+create dataverse TinySocial;
+use dataverse TinySocial;
+
+create type TwitterUserType as open {
+        screen-name: string,
+        lang: string,
+        friends_count: int64,
+        statuses_count: int64,
+        name: string,
+        followers_count: int64
+}
+
+create type TweetMessageType as closed {
+        tweetid: string,
+        user: TwitterUserType,
+        sender-location: point?,
+        send-time: datetime,
+        referred-topics: {{ string }},
+        message-text: string
+}
+
+create type EmploymentType as open {
+        organization-name: string,
+        start-date: date,
+        end-date: date?
+}
+
+create type FacebookUserType as closed {
+        id: int64,
+        alias: string,
+        name: string,
+        user-since: datetime,
+        friend-ids: {{ int64 }},
+        employment: [EmploymentType]
+}
+
+create type FacebookMessageType as closed {
+        message-id: int64,
+        author-id: int64,
+        in-response-to: int64?,
+        sender-location: point?,
+        message: string
+}

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/records/record-merge/tiny-social-example/tiny-social-example.2.ddl.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/records/record-merge/tiny-social-example/tiny-social-example.2.ddl.aql b/asterix-app/src/test/resources/runtimets/queries/records/record-merge/tiny-social-example/tiny-social-example.2.ddl.aql
new file mode 100644
index 0000000..97ee993
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/records/record-merge/tiny-social-example/tiny-social-example.2.ddl.aql
@@ -0,0 +1,42 @@
+/*
+ * 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  : Testing record-merge under different queries.
+* Expected Res : Success
+* Date         : 04 Aug 2015
+*/
+use dataverse TinySocial;
+
+create dataset FacebookUsers(FacebookUserType)
+primary key id;
+
+create dataset FacebookMessages(FacebookMessageType)
+primary key message-id;
+
+create dataset TwitterUsers(TwitterUserType)
+primary key screen-name;
+
+create dataset TweetMessages(TweetMessageType)
+primary key tweetid
+hints(cardinality=100);
+
+create index fbUserSinceIdx on FacebookUsers(user-since);
+create index fbAuthorIdx on FacebookMessages(author-id) type btree;
+create index fbSenderLocIndex on FacebookMessages(sender-location) type rtree;
+create index fbMessageIdx on FacebookMessages(message) type keyword;

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/records/record-merge/tiny-social-example/tiny-social-example.3.update.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/records/record-merge/tiny-social-example/tiny-social-example.3.update.aql b/asterix-app/src/test/resources/runtimets/queries/records/record-merge/tiny-social-example/tiny-social-example.3.update.aql
new file mode 100644
index 0000000..5bc4f5c
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/records/record-merge/tiny-social-example/tiny-social-example.3.update.aql
@@ -0,0 +1,36 @@
+/*
+ * 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  : Testing record-merge under different queries.
+* Expected Res : Success
+* Date         : 04 Aug 2015
+*/
+use dataverse TinySocial;
+
+load dataset FacebookUsers using localfs
+(("path"="nc1://data/tinysocial/fbu.adm"),("format"="adm"));
+
+load dataset FacebookMessages using localfs
+(("path"="nc1://data/tinysocial/fbm.adm"),("format"="adm"));
+
+load dataset TwitterUsers using localfs
+(("path"="nc1://data/tinysocial/twu.adm"),("format"="adm"));
+
+load dataset TweetMessages using localfs
+(("path"="nc1://data/tinysocial/twm.adm"),("format"="adm"));

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/records/record-merge/tiny-social-example/tiny-social-example.4.query.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/records/record-merge/tiny-social-example/tiny-social-example.4.query.aql b/asterix-app/src/test/resources/runtimets/queries/records/record-merge/tiny-social-example/tiny-social-example.4.query.aql
new file mode 100644
index 0000000..8601155
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/records/record-merge/tiny-social-example/tiny-social-example.4.query.aql
@@ -0,0 +1,30 @@
+/*
+ * 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  : Testing record-merge under different queries.
+* Expected Res : Success
+* Date         : 04 Aug 2015
+*/
+use dataverse TinySocial;
+
+for $r in dataset TweetMessages
+for $f in dataset FacebookMessages
+let $result := record-merge($r, $f)
+order by $result
+return $result

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/documentation-example/documentation-example.1.query.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/documentation-example/documentation-example.1.query.aql b/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/documentation-example/documentation-example.1.query.aql
new file mode 100644
index 0000000..9ff79ac
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/documentation-example/documentation-example.1.query.aql
@@ -0,0 +1,28 @@
+/*
+ * 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  : record-remove-fields under different queries.
+* Expected Res : Success
+* Date         : 04 Aug 2015
+*/
+        let $r1 := {"id":1,
+            "project":"AsterixDB",
+            "address":{"city":"Irvine", "state":"CA"},
+            "related":["Hivestrix", "Preglix", "Apache VXQuery"] }
+        return record-remove-fields($r1, ["project"])

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/documentation-example/documentation-example.2.query.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/documentation-example/documentation-example.2.query.aql b/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/documentation-example/documentation-example.2.query.aql
new file mode 100644
index 0000000..7600912
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/documentation-example/documentation-example.2.query.aql
@@ -0,0 +1,28 @@
+/*
+ * 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  : record-remove-fields under different queries.
+* Expected Res : Success
+* Date         : 04 Aug 2015
+*/
+        let $r1 := {"id":1,
+            "project":"AsterixDB",
+            "address":{"city":"Irvine", "state":"CA"},
+            "related":["Hivestrix", "Preglix", "Apache VXQuery"] }
+        return record-remove-fields($r1, [["address", "city"]])
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/documentation-example/documentation-example.3.query.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/documentation-example/documentation-example.3.query.aql b/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/documentation-example/documentation-example.3.query.aql
new file mode 100644
index 0000000..9409891
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/documentation-example/documentation-example.3.query.aql
@@ -0,0 +1,28 @@
+/*
+ * 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  : record-remove-fields under different queries.
+* Expected Res : Success
+* Date         : 04 Aug 2015
+*/
+        let $r1 := {"id":1,
+            "project":"AsterixDB",
+            "address":{"city":"Irvine", "state":"CA"},
+            "related":["Hivestrix", "Preglix", "Apache VXQuery"] }
+        return record-remove-fields($r1, [["address", "state"], ["address", "city"]])
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/highly-nested-open/highly-nested-open.1.ddl.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/highly-nested-open/highly-nested-open.1.ddl.aql b/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/highly-nested-open/highly-nested-open.1.ddl.aql
new file mode 100644
index 0000000..d850caa
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/highly-nested-open/highly-nested-open.1.ddl.aql
@@ -0,0 +1,72 @@
+/*
+ * 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  : Testing record-remove-fields under different queries.
+* Expected Res : Success
+* Date         : 04 Aug 2015
+*/
+drop dataverse test if exists;
+create dataverse test;
+
+use dataverse test;
+
+create type S as open{
+    id: int64
+}
+
+create type GS as open{
+    id: int64,
+    Genus: string
+}
+
+create type FGS as open{
+    id: int64,
+    Family: string
+}
+
+create type OFGS as open{
+    id: int64,
+    Order: string
+}
+
+create type COFGS as open{
+    id: int64,
+    Class: string
+}
+
+create type PCOFGS as open{
+    id: int64,
+    Phylum: string
+}
+
+create type KPCOFGS as open{
+    id: int64,
+    Kingdom: string
+}
+
+create type Classification as open{
+    id: int64
+}
+
+create type Animal as open{
+    id: int64
+}
+
+create dataset Animals(Animal)
+primary key id;

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/highly-nested-open/highly-nested-open.2.update.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/highly-nested-open/highly-nested-open.2.update.aql b/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/highly-nested-open/highly-nested-open.2.update.aql
new file mode 100644
index 0000000..d96edf0
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/highly-nested-open/highly-nested-open.2.update.aql
@@ -0,0 +1,27 @@
+/*
+ * 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  : Testing record-remove-fields under different queries.
+* Expected Res : Success
+* Date         : 04 Aug 2015
+*/
+use dataverse test;
+
+load dataset Animals using localfs
+(("path"="asterix_nc1://data/classifications/animals.adm"),("format"="adm"));

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/highly-nested-open/highly-nested-open.3.query.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/highly-nested-open/highly-nested-open.3.query.aql b/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/highly-nested-open/highly-nested-open.3.query.aql
new file mode 100644
index 0000000..af8c258
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/highly-nested-open/highly-nested-open.3.query.aql
@@ -0,0 +1,29 @@
+/*
+ * 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  : Testing record-remove-fields under different queries.
+* Expected Res : Success
+* Date         : 04 Aug 2015
+*/
+use dataverse test;
+
+for $test in dataset Animals
+let $result := record-remove-fields($test, [["class", "fullClassification"]])
+order by $result.id
+return $result;
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/tiny-social-example/tiny-social-example.1.ddl.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/tiny-social-example/tiny-social-example.1.ddl.aql b/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/tiny-social-example/tiny-social-example.1.ddl.aql
new file mode 100644
index 0000000..6ade854
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/tiny-social-example/tiny-social-example.1.ddl.aql
@@ -0,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.
+ */
+/*
+* Description  : Testing record-remove-fields under different queries.
+* Expected Res : Success
+* Date         : 04 Aug 2015
+*/
+drop dataverse TinySocial if exists;
+create dataverse TinySocial;
+use dataverse TinySocial;
+
+create type TwitterUserType as open {
+        screen-name: string,
+        lang: string,
+        friends_count: int64,
+        statuses_count: int64,
+        name: string,
+        followers_count: int64
+}
+
+create type TweetMessageType as closed {
+        tweetid: string,
+        user: TwitterUserType,
+        sender-location: point?,
+        send-time: datetime,
+        referred-topics: {{ string }},
+        message-text: string
+}
+
+create type EmploymentType as open {
+        organization-name: string,
+        start-date: date,
+        end-date: date?
+}
+
+create type FacebookUserType as closed {
+        id: int64,
+        alias: string,
+        name: string,
+        user-since: datetime,
+        friend-ids: {{ int64 }},
+        employment: [EmploymentType]
+}
+
+create type FacebookMessageType as closed {
+        message-id: int64,
+        author-id: int64,
+        in-response-to: int64?,
+        sender-location: point?,
+        message: string
+}

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/tiny-social-example/tiny-social-example.2.ddl.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/tiny-social-example/tiny-social-example.2.ddl.aql b/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/tiny-social-example/tiny-social-example.2.ddl.aql
new file mode 100644
index 0000000..d9e2569
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/tiny-social-example/tiny-social-example.2.ddl.aql
@@ -0,0 +1,42 @@
+/*
+ * 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  : Testing record-remove-fields under different queries.
+* Expected Res : Success
+* Date         : 04 Jun 2015
+*/
+use dataverse TinySocial;
+
+create dataset FacebookUsers(FacebookUserType)
+primary key id;
+
+create dataset FacebookMessages(FacebookMessageType)
+primary key message-id;
+
+create dataset TwitterUsers(TwitterUserType)
+primary key screen-name;
+
+create dataset TweetMessages(TweetMessageType)
+primary key tweetid
+hints(cardinality=100);
+
+create index fbUserSinceIdx on FacebookUsers(user-since);
+create index fbAuthorIdx on FacebookMessages(author-id) type btree;
+create index fbSenderLocIndex on FacebookMessages(sender-location) type rtree;
+create index fbMessageIdx on FacebookMessages(message) type keyword;

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/tiny-social-example/tiny-social-example.3.update.aql
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/tiny-social-example/tiny-social-example.3.update.aql b/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/tiny-social-example/tiny-social-example.3.update.aql
new file mode 100644
index 0000000..542b97e
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/queries/records/record-remove-fields/tiny-social-example/tiny-social-example.3.update.aql
@@ -0,0 +1,36 @@
+/*
+ * 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  : Testing record-remove-fields under different queries.
+* Expected Res : Success
+* Date         : 04 Jun 2015
+*/
+use dataverse TinySocial;
+
+load dataset FacebookUsers using localfs
+(("path"="nc1://data/tinysocial/fbu.adm"),("format"="adm"));
+
+load dataset FacebookMessages using localfs
+(("path"="nc1://data/tinysocial/fbm.adm"),("format"="adm"));
+
+load dataset TwitterUsers using localfs
+(("path"="nc1://data/tinysocial/twu.adm"),("format"="adm"));
+
+load dataset TweetMessages using localfs
+(("path"="nc1://data/tinysocial/twm.adm"),("format"="adm"));



[3/6] incubator-asterixdb git commit: ASTERIXDB-1187, ASTERIXDB-1162 and ASTERIXDB-1252 fixes, plus new internal functions

Posted by ti...@apache.org.
http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/results/records/record-remove-fields/tiny-social-example/tiny-social-example.4.adm
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/results/records/record-remove-fields/tiny-social-example/tiny-social-example.4.adm b/asterix-app/src/test/resources/runtimets/results/records/record-remove-fields/tiny-social-example/tiny-social-example.4.adm
new file mode 100644
index 0000000..5f622d7
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/results/records/record-remove-fields/tiny-social-example/tiny-social-example.4.adm
@@ -0,0 +1,12 @@
+{ "tweetid": "7", "user": { "lang": "en", "friends_count": 182, "statuses_count": 394, "name": "Chang Ewing", "followers_count": 32136 }, "send-time": datetime("2011-08-25T10:10:00.000Z"), "referred-topics": {{ "samsung", "platform" }}, "message-text": " like samsung the platform is good" }
+, { "tweetid": "3", "user": { "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "send-time": datetime("2006-11-04T10:10:00.000Z"), "referred-topics": {{ "motorola", "speed" }}, "message-text": " like motorola the speed is good:)" }
+, { "tweetid": "6", "user": { "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "send-time": datetime("2010-05-07T10:10:00.000Z"), "referred-topics": {{ "iphone", "voice-clarity" }}, "message-text": " like iphone the voice-clarity is good:)" }
+, { "tweetid": "5", "user": { "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "send-time": datetime("2006-08-04T10:10:00.000Z"), "referred-topics": {{ "motorola", "speed" }}, "message-text": " can't stand motorola its speed is terrible:(" }
+, { "tweetid": "11", "user": { "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Nila Milliron", "followers_count": 22649 }, "send-time": datetime("2008-03-09T10:10:00.000Z"), "referred-topics": {{ "iphone", "platform" }}, "message-text": " can't stand iphone its platform is terrible" }
+, { "tweetid": "10", "user": { "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "send-time": datetime("2008-01-26T10:10:00.000Z"), "referred-topics": {{ "verizon", "voice-clarity" }}, "message-text": " hate verizon its voice-clarity is OMG:(" }
+, { "tweetid": "2", "user": { "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "send-time": datetime("2010-05-13T10:10:00.000Z"), "referred-topics": {{ "verizon", "shortcut-menu" }}, "message-text": " like verizon its shortcut-menu is awesome:)" }
+, { "tweetid": "1", "user": { "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "send-time": datetime("2008-04-26T10:10:00.000Z"), "referred-topics": {{ "t-mobile", "customization" }}, "message-text": " love t-mobile its customization is good:)" }
+, { "tweetid": "12", "user": { "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Oli Jackson", "followers_count": 22649 }, "send-time": datetime("2010-02-13T10:10:00.000Z"), "referred-topics": {{ "samsung", "voice-command" }}, "message-text": " like samsung the voice-command is amazing:)" }
+, { "tweetid": "8", "user": { "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "send-time": datetime("2005-10-14T10:10:00.000Z"), "referred-topics": {{ "t-mobile", "shortcut-menu" }}, "message-text": " like t-mobile the shortcut-menu is awesome:)" }
+, { "tweetid": "4", "user": { "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "send-time": datetime("2011-12-26T10:10:00.000Z"), "referred-topics": {{ "sprint", "voice-command" }}, "message-text": " like sprint the voice-command is mind-blowing:)" }
+, { "tweetid": "9", "user": { "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "send-time": datetime("2012-07-21T10:10:00.000Z"), "referred-topics": {{ "verizon", "voicemail-service" }}, "message-text": " love verizon its voicemail-service is awesome" }

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/testsuite.xml
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/testsuite.xml b/asterix-app/src/test/resources/runtimets/testsuite.xml
index 0e48f39..c4c8fc4 100644
--- a/asterix-app/src/test/resources/runtimets/testsuite.xml
+++ b/asterix-app/src/test/resources/runtimets/testsuite.xml
@@ -18,9 +18,10 @@
  !-->
 <!DOCTYPE test-suite [
 
-        <!ENTITY RecordsQueries SYSTEM "queries/records/RecordsQueries.xml">
+<!ENTITY RecordsQueries SYSTEM "queries/records/RecordsQueries.xml">
+<!ENTITY DeepEqualQueries SYSTEM "queries/comparison/deep_equal/DeepEqualQueries.xml">
+]>
 
-        ]>
 <test-suite
         xmlns="urn:xml.testframework.asterix.apache.org"
         ResultOffsetPath="results"
@@ -4417,6 +4418,9 @@
     <test-group name="records">
         &RecordsQueries;
     </test-group>
+    <test-group name="deep-equal">
+        &DeepEqualQueries;
+    </test-group>
     <test-group name="scan">
         <test-case FilePath="scan">
             <compilation-unit name="10">

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-doc/src/site/markdown/aql/functions.md
----------------------------------------------------------------------
diff --git a/asterix-doc/src/site/markdown/aql/functions.md b/asterix-doc/src/site/markdown/aql/functions.md
index 2786d2a..1907689 100644
--- a/asterix-doc/src/site/markdown/aql/functions.md
+++ b/asterix-doc/src/site/markdown/aql/functions.md
@@ -37,11 +37,11 @@ Asterix provides various classes of functions to support operations on numeric,
 ### abs ###
  * Syntax:
 
-        abs(numeric_expression)
+        abs(numeric_value)
 
  * Computes the absolute value of the argument.
  * Arguments:
-    * `numeric_expression`: A `int8`/`int16`/`int32`/`int64`/`float`/`double` value.
+    * `numeric_value`: A `int8`/`int16`/`int32`/`int64`/`float`/`double` value.
  * Return Value:
     * The absolute value of the argument with the same type as the input argument, or `null` if the argument is a `null` value.
 
@@ -63,11 +63,11 @@ Asterix provides various classes of functions to support operations on numeric,
 ### ceiling ###
  * Syntax:
 
-        ceiling(numeric_expression)
+        ceiling(numeric_value)
 
  * Computes the smallest (closest to negative infinity) number with no fractional part that is not less than the value of the argument. If the argument is already equal to mathematical integer, then the result is the same as the argument.
  * Arguments:
-    * `numeric_expression`: A `int8`/`int16`/`int32`/`int64`/`float`/`double` value.
+    * `numeric_value`: A `int8`/`int16`/`int32`/`int64`/`float`/`double` value.
  * Return Value:
     * The ceiling value for the given number in the same type as the input argument, or `null` if the input is `null`.
 
@@ -89,11 +89,11 @@ Asterix provides various classes of functions to support operations on numeric,
 ### floor ###
  * Syntax:
 
-        floor(numeric_expression)
+        floor(numeric_value)
 
  * Computes the largest (closest to positive infinity) number with no fractional part that is not greater than the value. If the argument is already equal to mathematical integer, then the result is the same as the argument.
  * Arguments:
-    * `numeric_expression`: A `int8`/`int16`/`int32`/`int64`/`float`/`double` value.
+    * `numeric_value`: A `int8`/`int16`/`int32`/`int64`/`float`/`double` value.
  * Return Value:
     * The floor value for the given number in the same type as the input argument, or `null` if the input is `null`.
 
@@ -115,11 +115,11 @@ Asterix provides various classes of functions to support operations on numeric,
 ### round ###
  * Syntax:
 
-        round(numeric_expression)
+        round(numeric_value)
 
  * Computes the number with no fractional part that is closest (and also closest to positive infinity) to the argument.
  * Arguments:
-    * `numeric_expression`: A `int8`/`int16`/`int32`/`int64`/`float`/`double` value.
+    * `numeric_value`: A `int8`/`int16`/`int32`/`int64`/`float`/`double` value.
  * Return Value:
     * The rounded value for the given number in the same type as the input argument, or `null` if the input is `null`.
 
@@ -141,11 +141,11 @@ Asterix provides various classes of functions to support operations on numeric,
 ### round-half-to-even ###
  * Syntax:
 
-        round-half-to-even(numeric_expression, [precision])
+        round-half-to-even(numeric_value, [precision])
 
- * Computes the closest numeric value to `numeric_expression` that is a multiple of ten to the power of minus `precision`. `precision` is optional and by default value `0` is used.
+ * Computes the closest numeric value to `numeric_value` that is a multiple of ten to the power of minus `precision`. `precision` is optional and by default value `0` is used.
  * Arguments:
-    * `numeric_expression`: A `int8`/`int16`/`int32`/`int64`/`float`/`double` value.
+    * `numeric_value`: A `int8`/`int16`/`int32`/`int64`/`float`/`double` value.
     * `precision`: An optional integer field representing the number of digits in the fraction of the the result
  * Return Value:
     * The rounded value for the given number in the same type as the input argument, or `null` if the input is `null`.
@@ -172,24 +172,24 @@ Asterix provides various classes of functions to support operations on numeric,
 ### string-to-codepoint ###
  * Syntax:
 
-        string-to-codepoint(string_expression)
+        string-to-codepoint(string)
 
- * Converts the string `string_expression` to its code-based representation.
+ * Converts the string `string` to its code-based representation.
  * Arguments:
-    * `string_expression` : A `string` that will be converted.
+    * `string` : A `string` that will be converted.
  * Return Value:
-    * An `OrderedList` of the code points for the string `string_expression`.
+    * An `OrderedList` of the code points for the string `string`.
 
 ### codepoint-to-string ###
  * Syntax:
 
-        codepoint-to-string(list_expression)
+        codepoint-to-string(list)
 
- * Converts the ordered code-based representation `list_expression` to the corresponding string.
+ * Converts the ordered code-based representation `list` to the corresponding string.
  * Arguments:
-    * `list_expression` : An `OrderedList` of code-points.
+    * `list` : An `OrderedList` of code-points.
  * Return Value:
-    * A `string` representation of `list_expression`.
+    * A `string` representation of `list`.
 
  * Example:
 
@@ -209,14 +209,14 @@ Asterix provides various classes of functions to support operations on numeric,
 ### contains ###
  * Syntax:
 
-        contains(string_expression, substring_to_contain)
+        contains(string, substring_to_contain)
 
- * Checks whether the string `string_expression` contains the string `substring_to_contain`
+ * Checks whether the string `string` contains the string `substring_to_contain`
  * Arguments:
-    * `string_expression` : A `string` that might contain the given substring.
+    * `string` : A `string` that might contain the given substring.
     * `substring_to_contain` : A target `string` that might be contained.
  * Return Value:
-    * A `boolean` value, `true` if `string_expression` contains `substring_to_contain`, and `false` otherwise.
+    * A `boolean` value, `true` if `string` contains `substring_to_contain`, and `false` otherwise.
  * Note: An [n-gram index](similarity.html#UsingIndexesToSupportSimilarityQueries) can be utilized for this function.
  * Example:
 
@@ -237,14 +237,14 @@ Asterix provides various classes of functions to support operations on numeric,
 ### like ###
  * Syntax:
 
-        like(string_expression, string_pattern)
+        like(string, string_pattern)
 
- * Checks whether the string `string_expression` contains the string pattern `string_pattern`. Compared to the `contains` function, the `like` function also supports regular expressions.
+ * Checks whether the string `string` contains the string pattern `string_pattern`. Compared to the `contains` function, the `like` function also supports regular expressions.
  * Arguments:
-    * `string_expression` : A `string` that might contain the pattern or `null`.
+    * `string` : A `string` that might contain the pattern or `null`.
     * `string_pattern` : A pattern `string` that might be contained or `null`.
  * Return Value:
-    * A `boolean` value, `true` if `string_expression` contains the pattern `string_pattern`, and `false` otherwise.
+    * A `boolean` value, `true` if `string` contains the pattern `string_pattern`, and `false` otherwise.
 
  * Example:
 
@@ -265,14 +265,14 @@ Asterix provides various classes of functions to support operations on numeric,
 ### starts-with ###
  * Syntax:
 
-        starts-with(string_expression, substring_to_start_with)
+        starts-with(string, substring_to_start_with)
 
- * Checks whether the string `string_expression` starts with the string `substring_to_start_with`.
+ * Checks whether the string `string` starts with the string `substring_to_start_with`.
  * Arguments:
-    * `string_expression` : A `string` that might start with the given string.
+    * `string` : A `string` that might start with the given string.
     * `substring_to_start_with` : A `string` that might be contained as the starting substring.
  * Return Value:
-    * A `boolean`, returns `true` if `string_expression` starts with the string `substring_to_start_with`, and `false` otherwise.
+    * A `boolean`, returns `true` if `string` starts with the string `substring_to_start_with`, and `false` otherwise.
 
  * Example:
 
@@ -294,14 +294,14 @@ Asterix provides various classes of functions to support operations on numeric,
 ### ends-with ###
  * Syntax:
 
-        ends-with(string_expression, substring_to_end_with)
+        ends-with(string, substring_to_end_with)
 
- * Checks whether the string `string_expression` ends with the string `substring_to_end_with`.
+ * Checks whether the string `string` ends with the string `substring_to_end_with`.
  * Arguments:
-    * `string_expression` : A `string` that might end with the given string.
+    * `string` : A `string` that might end with the given string.
     * `substring_to_end_with` : A `string` that might be contained as the ending substring.
  * Return Value:
-    * A `boolean`, returns `true` if `string_expression` ends with the string `substring_to_end_with`, and `false` otherwise.
+    * A `boolean`, returns `true` if `string` ends with the string `substring_to_end_with`, and `false` otherwise.
 
  * Example:
 
@@ -322,11 +322,11 @@ Asterix provides various classes of functions to support operations on numeric,
 ### string-concat ###
  * Syntax:
 
-        string-concat(list_expression)
+        string-concat(list)
 
- * Concatenates a list of strings `list_expression` into a single string.
+ * Concatenates a list of strings `list` into a single string.
  * Arguments:
-    * `list_expression` : An `OrderedList` or `UnorderedList` of `string`s (could be `null`) to be concatenated.
+    * `list` : An `OrderedList` or `UnorderedList` of `string`s (could be `null`) to be concatenated.
  * Return Value:
     * Returns the concatenated `string` value.
 
@@ -346,12 +346,12 @@ Asterix provides various classes of functions to support operations on numeric,
 ### string-join ###
  * Syntax:
 
-        string-join(list_expression, string_expression)
+        string-join(list, string)
 
- * Joins a list of strings `list_expression` with the given separator `string_expression` into a single string.
+ * Joins a list of strings `list` with the given separator `string` into a single string.
  * Arguments:
-    * `list_expression` : An `OrderedList` or `UnorderedList` of strings (could be `null`) to be joined.
-    * `string_expression` : A `string` as the separator.
+    * `list` : An `OrderedList` or `UnorderedList` of strings (could be `null`) to be joined.
+    * `string` : A `string` as the separator.
  * Return Value:
     * Returns the joined `String`.
 
@@ -371,13 +371,13 @@ Asterix provides various classes of functions to support operations on numeric,
 ### lowercase ###
  * Syntax:
 
-        lowercase(string_expression)
+        lowercase(string)
 
- * Converts a given string `string_expression` to its lowercase form.
+ * Converts a given string `string` to its lowercase form.
  * Arguments:
-    * `string_expression` : A `string` to be converted.
+    * `string` : A `string` to be converted.
  * Return Value:
-    * Returns a `string` as the lowercase form of the given `string_expression`.
+    * Returns a `string` as the lowercase form of the given `string`.
 
  * Example:
 
@@ -394,13 +394,13 @@ Asterix provides various classes of functions to support operations on numeric,
 ### uppercase ###
  * Syntax:
 
- uppercase(string_expression)
+        uppercase(string)
 
- * Converts a given string `string_expression` to its uppercase form.
+ * Converts a given string `string` to its uppercase form.
  * Arguments:
-    * `string_expression` : A `string` to be converted.
+    * `string` : A `string` to be converted.
  * Return Value:
-    * Returns a `string` as the uppercase form of the given `string_expression`.
+    * Returns a `string` as the uppercase form of the given `string`.
 
  * Example:
 
@@ -414,42 +414,17 @@ Asterix provides various classes of functions to support operations on numeric,
 
         ASTERIX
 
-
-### uppercase ###
- * Syntax:
-
-        uppercase(string_expression)
-
- * Converts a given string `string_expression` to its uppercase form.
- * Arguments:
-    * `string_expression` : A `string` to be converted.
- * Return Value:
-    * Returns a `string` as the uppercase form of the given `string_expression`.
-
- * Example:
-
-        use dataverse TinySocial;
-
-        let $i := "asterix"
-        return uppercase($i)
-
-
- * The expected result is:
-
-        ASTERIX
-
-
 ### matches ###
  * Syntax:
 
-        matches(string_expression, string_pattern)
+        matches(string, string_pattern)
 
- * Checks whether the strings `string_expression` matches the given pattern `string_pattern` (A Java regular expression pattern).
+ * Checks whether the strings `string` matches the given pattern `string_pattern` (A Java regular expression pattern).
  * Arguments:
-    * `string_expression` : A `string` that might contain the pattern.
+    * `string` : A `string` that might contain the pattern.
     * `string_pattern` : A pattern `string` to be matched.
  * Return Value:
-    * A `boolean`, returns `true` if `string_expression` matches the pattern `string_pattern`, and `false` otherwise.
+    * A `boolean`, returns `true` if `string` matches the pattern `string_pattern`, and `false` otherwise.
 
  * Example:
 
@@ -469,11 +444,11 @@ Asterix provides various classes of functions to support operations on numeric,
 ### replace ###
  * Syntax:
 
-        replace(string_expression, string_pattern, string_replacement[, string_flags])
+        replace(string, string_pattern, string_replacement[, string_flags])
 
- * Checks whether the string `string_expression` matches the given pattern `string_pattern`, and replace the matched pattern `string_pattern` with the new pattern `string_replacement`.
+ * Checks whether the string `string` matches the given pattern `string_pattern`, and replace the matched pattern `string_pattern` with the new pattern `string_replacement`.
  * Arguments:
-    * `string_expression` : A `string` that might contain the pattern.
+    * `string` : A `string` that might contain the pattern.
     * `string_pattern` : A pattern `string` to be matched.
     * `string_replacement` : A pattern `string` to be used as the replacement.
     * `string_flag` : (Optional) A `string` with flags to be used during replace.
@@ -498,13 +473,13 @@ Asterix provides various classes of functions to support operations on numeric,
 ### string-length ###
  * Syntax:
 
-        string-length(string_expression)
+        string-length(string)
 
- * Returns the length of the string `string_expression`.
+ * Returns the length of the string `string`.
  * Arguments:
-    * `string_expression` : A `string` or `null` that represents the string to be checked.
+    * `string` : A `string` or `null` that represents the string to be checked.
  * Return Value:
-    * An `int64` that represents the length of `string_expression`.
+    * An `int64` that represents the length of `string`.
 
  * Example:
 
@@ -536,12 +511,12 @@ Asterix provides various classes of functions to support operations on numeric,
 ### substring ###
  * Syntax:
 
-        substring(string_expression, offset[, length])
+        substring(string, offset[, length])
 
- * Returns the substring from the given string `string_expression` based on the given start offset `offset` with the optional `length`.
+ * Returns the substring from the given string `string` based on the given start offset `offset` with the optional `length`.
  * Arguments:
-    * `string_expression` : A `string` to be extracted.
-    * `offset` : An `int64` as the starting offset of the substring in `string_expression`.
+    * `string` : A `string` to be extracted.
+    * `offset` : An `int64` as the starting offset of the substring in `string`.
     * `length` : (Optional) An `int64` as the length of the substring.
  * Return Value:
     * A `string` that represents the substring.
@@ -563,11 +538,11 @@ Asterix provides various classes of functions to support operations on numeric,
 ### substring-before ###
  * Syntax:
 
-        substring-before(string_expression, string_pattern)
+        substring-before(string, string_pattern)
 
- * Returns the substring from the given string `string_expression` before the given pattern `string_pattern`.
+ * Returns the substring from the given string `string` before the given pattern `string_pattern`.
  * Arguments:
-    * `string_expression` : A `string` to be extracted.
+    * `string` : A `string` to be extracted.
     * `string_pattern` : A `string` pattern to be searched.
  * Return Value:
     * A `string` that represents the substring.
@@ -591,11 +566,11 @@ Asterix provides various classes of functions to support operations on numeric,
 ### substring-after ###
  * Syntax:
 
-        substring-after(string_expression, string_pattern)
+        substring-after(string, string_pattern)
 
- * Returns the substring from the given string `string_expression` after the given pattern `string_pattern`.
+ * Returns the substring from the given string `string` after the given pattern `string_pattern`.
  * Arguments:
-    * `string_expression` : A `string` to be extracted.
+    * `string` : A `string` to be extracted.
     * `string_pattern` : A `string` pattern to be searched.
  * Return Value:
     * A `string` that represents the substring.
@@ -820,14 +795,14 @@ Asterix provides various classes of functions to support operations on numeric,
 ### create-line ###
  * Syntax:
 
-        create-line(point_expression1, point_expression2)
+        create-line(point1, point2)
 
- * Creates the primitive type `line` using `point_expression1` and `point_expression2`.
+ * Creates the primitive type `line` using `point1` and `point2`.
  * Arguments:
-    * `point_expression1` : A `point` that represents the start point of the line.
-    * `point_expression2` : A `point` that represents the end point of the line.
+    * `point1` : A `point` that represents the start point of the line.
+    * `point2` : A `point` that represents the end point of the line.
  * Return Value:
-    * A spatial `line` created using the points provided in `point_expression1` and `point_expression2`.
+    * A spatial `line` created using the points provided in `point1` and `point2`.
 
  * Example:
 
@@ -845,14 +820,14 @@ Asterix provides various classes of functions to support operations on numeric,
 ### create-rectangle ###
  * Syntax:
 
-        create-rectangle(point_expression1, point_expression2)
+        create-rectangle(point1, point2)
 
- * Creates the primitive type `rectangle` using `point_expression1` and `point_expression2`.
+ * Creates the primitive type `rectangle` using `point1` and `point2`.
  * Arguments:
-    * `point_expression1` : A `point` that represents the lower-left point of the rectangle.
-    * `point_expression2` : A `point` that represents the upper-right point of the rectangle.
+    * `point1` : A `point` that represents the lower-left point of the rectangle.
+    * `point2` : A `point` that represents the upper-right point of the rectangle.
  * Return Value:
-    * A spatial `rectangle` created using the points provided in `point_expression1` and `point_expression2`.
+    * A spatial `rectangle` created using the points provided in `point1` and `point2`.
 
  * Example:
 
@@ -870,14 +845,14 @@ Asterix provides various classes of functions to support operations on numeric,
 ### create-circle ###
  * Syntax:
 
-        create-circle(point_expression, radius)
+        create-circle(point, radius)
 
- * Creates the primitive type `circle` using `point_expression` and `radius`.
+ * Creates the primitive type `circle` using `point` and `radius`.
  * Arguments:
-    * `point_expression` : A `point` that represents the center of the circle.
+    * `point` : A `point` that represents the center of the circle.
     * `radius` : A `double` that represents the radius of the circle.
  * Return Value:
-    * A spatial `circle` created using the center point and the radius provided in `point_expression` and `radius`.
+    * A spatial `circle` created using the center point and the radius provided in `point` and `radius`.
 
  * Example:
 
@@ -895,13 +870,13 @@ Asterix provides various classes of functions to support operations on numeric,
 ### create-polygon ###
  * Syntax:
 
-        create-polygon(list_expression)
+        create-polygon(list)
 
- * Creates the primitive type `polygon` using the double values provided in the argument `list_expression`. Each two consecutive double values represent a point starting from the first double value in the list. Note that at least six double values should be specified, meaning a total of three points.
+ * Creates the primitive type `polygon` using the double values provided in the argument `list`. Each two consecutive double values represent a point starting from the first double value in the list. Note that at least six double values should be specified, meaning a total of three points.
  * Arguments:
-   * `list_expression` : An OrderedList of doubles representing the points of the polygon.
+   * `list` : An OrderedList of doubles representing the points of the polygon.
  * Return Value:
-   * A `polygon`, represents a spatial simple polygon created using the points provided in `list_expression`.
+   * A `polygon`, represents a spatial simple polygon created using the points provided in `list`.
 
  * Example:
 
@@ -919,13 +894,13 @@ Asterix provides various classes of functions to support operations on numeric,
 ### get-x/get-y ###
  * Syntax:
 
-        get-x(point_expression) or get-y(point_expression)
+        get-x(point) or get-y(point)
 
- * Returns the x or y coordinates of a point `point_expression`.
+ * Returns the x or y coordinates of a point `point`.
  * Arguments:
-    * `point_expression` : A `point`.
+    * `point` : A `point`.
  * Return Value:
-    * A `double` representing the x or y coordinates of the point `point_expression`.
+    * A `double` representing the x or y coordinates of the point `point`.
 
  * Example:
 
@@ -943,13 +918,13 @@ Asterix provides various classes of functions to support operations on numeric,
 ### get-points ###
  * Syntax:
 
-        get-points(spatial_expression)
+        get-points(spatial_object)
 
- * Returns an ordered list of the points forming the spatial object `spatial_expression`.
+ * Returns an ordered list of the points forming the spatial object `spatial_object`.
  * Arguments:
-    * `spatial_expression` : A `point`, `line`, `rectangle`, `circle`, or `polygon`.
+    * `spatial_object` : A `point`, `line`, `rectangle`, `circle`, or `polygon`.
  * Return Value:
-    * An `OrderedList` of the points forming the spatial object `spatial_expression`.
+    * An `OrderedList` of the points forming the spatial object `spatial_object`.
 
  * Example:
 
@@ -998,14 +973,14 @@ Asterix provides various classes of functions to support operations on numeric,
 ### spatial-distance ###
  * Syntax:
 
-        spatial-distance(point_expression1, point_expression2)
+        spatial-distance(point1, point2)
 
- * Returns the Euclidean distance between `point_expression1` and `point_expression2`.
+ * Returns the Euclidean distance between `point1` and `point2`.
  * Arguments:
-    * `point_expression1` : A `point`.
-    * `point_expression2` : A `point`.
+    * `point1` : A `point`.
+    * `point2` : A `point`.
  * Return Value:
-    * A `double` as the Euclidean distance between `point_expression1` and `point_expression2`.
+    * A `double` as the Euclidean distance between `point1` and `point2`.
 
  * Example:
 
@@ -1061,14 +1036,14 @@ Asterix provides various classes of functions to support operations on numeric,
 ### spatial-intersect ###
  * Syntax:
 
-        spatial-intersect(spatial_expression1, spatial_expression2)
+        spatial-intersect(spatial_object1, spatial_object2)
 
  * Checks whether `@arg1` and `@arg2` spatially intersect each other.
  * Arguments:
-    * `spatial_expression1` : A `point`, `line`, `rectangle`, `circle`, or `polygon`.
-    * `spatial_expression2` : A `point`, `line`, `rectangle`, `circle`, or `polygon`.
+    * `spatial_object1` : A `point`, `line`, `rectangle`, `circle`, or `polygon`.
+    * `spatial_object2` : A `point`, `line`, `rectangle`, `circle`, or `polygon`.
  * Return Value:
-    * A `boolean` representing whether `spatial_expression1` and `spatial_expression2` spatially overlap with each other.
+    * A `boolean` representing whether `spatial_object1` and `spatial_object2` spatially overlap with each other.
 
  * Example:
 
@@ -1089,16 +1064,16 @@ Asterix provides various classes of functions to support operations on numeric,
 ### spatial-cell ###
  * Syntax:
 
-        spatial-cell(point_expression1, point_expression2, x_increment, y_increment)
+        spatial-cell(point1, point2, x_increment, y_increment)
 
- * Returns the grid cell that `point_expression1` belongs to.
+ * Returns the grid cell that `point1` belongs to.
  * Arguments:
-    * `point_expression1` : A `point` representing the point of interest that its grid cell will be returned.
-    * `point_expression2` : A `point` representing the origin of the grid.
+    * `point1` : A `point` representing the point of interest that its grid cell will be returned.
+    * `point2` : A `point` representing the origin of the grid.
     * `x_increment` : A `double`, represents X increments.
     * `y_increment` : A `double`, represents Y increments.
  * Return Value:
-    * A `rectangle` representing the grid cell that `point_expression1` belongs to.
+    * A `rectangle` representing the grid cell that `point1` belongs to.
 
  * Example:
 
@@ -1194,7 +1169,7 @@ including [edit distance](http://en.wikipedia.org/wiki/Levenshtein_distance) and
 ### edit-distance-contains ###
 * Syntax:
 
-edit-distance-contains(expression1, expression2, threshold)
+        edit-distance-contains(expression1, expression2, threshold)
 
 * Checks whether `expression1` contains `expression2` with an [edit distance](http://en.wikipedia.org/wiki/Levenshtein_distance) within a given threshold.
 
@@ -1222,14 +1197,14 @@ edit-distance-contains(expression1, expression2, threshold)
 ### similarity-jaccard ###
  * Syntax:
 
-        similarity-jaccard(list_expression1, list_expression2)
+        similarity-jaccard(list1, list2)
 
- * Returns the [Jaccard similarity](http://en.wikipedia.org/wiki/Jaccard_index) of `list_expression1` and `list_expression2`.
+ * Returns the [Jaccard similarity](http://en.wikipedia.org/wiki/Jaccard_index) of `list1` and `list2`.
  * Arguments:
-    * `list_expression1` : An `UnorderedList` or `OrderedList`.
-    * `list_expression2` : An `UnorderedList` or `OrderedList`.
+    * `list1` : An `UnorderedList` or `OrderedList`.
+    * `list2` : An `UnorderedList` or `OrderedList`.
  * Return Value:
-    * A `float` that represents the Jaccard similarity of `list_expression1` and `list_expression2`.
+    * A `float` that represents the Jaccard similarity of `list1` and `list2`.
  * Note: A [keyword index](similarity.html#UsingIndexesToSupportSimilarityQueries) can be utilized for this function.
  * Example:
 
@@ -1256,18 +1231,18 @@ edit-distance-contains(expression1, expression2, threshold)
 ### similarity-jaccard-check ###
  * Syntax:
 
-        similarity-jaccard-check(list_expression1, list_expression2, threshold)
+        similarity-jaccard-check(list1, list2, threshold)
 
- * Checks whether `list_expression1` and `list_expression2` have a [Jaccard similarity](http://en.wikipedia.org/wiki/Jaccard_index) greater than or equal to threshold.  Again, the “check” version of Jaccard is faster than the "non-check" version.
+ * Checks whether `list1` and `list2` have a [Jaccard similarity](http://en.wikipedia.org/wiki/Jaccard_index) greater than or equal to threshold.  Again, the “check” version of Jaccard is faster than the "non-check" version.
 
  * Arguments:
-    * `list_expression1` : An `UnorderedList` or `OrderedList`.
-    * `list_expression2` : An `UnorderedList` or `OrderedList`.
+    * `list1` : An `UnorderedList` or `OrderedList`.
+    * `list2` : An `UnorderedList` or `OrderedList`.
     * `threshold` : A `float` that represents the similarity threshold.
  * Return Value:
     * An `OrderedList` with two items:
-     * The first item contains a `boolean` value representing whether `list_expression1` and `list_expression2` are similar.
-     * The second item contains a `float` that represents the Jaccard similarity of `list_expression1` and `list_expression2` if it is greater than or equal to the threshold, or 0 otherwise.
+     * The first item contains a `boolean` value representing whether `list1` and `list2` are similar.
+     * The second item contains a `float` that represents the Jaccard similarity of `list1` and `list2` if it is greater than or equal to the threshold, or 0 otherwise.
  * Note: A [keyword index](similarity.html#UsingIndexesToSupportSimilarityQueries) can be utilized for this function.
  * Example:
 
@@ -1339,11 +1314,11 @@ edit-distance-contains(expression1, expression2, threshold)
 
  * Syntax:
 
-        word-tokens(string_expression)
+        word-tokens(string)
 
- * Returns a list of word tokens of `string_expression` using non-alphanumeric characters as delimiters.
+ * Returns a list of word tokens of `string` using non-alphanumeric characters as delimiters.
  * Arguments:
-    * `string_expression` : A `string` that will be tokenized.
+    * `string` : A `string` that will be tokenized.
  * Return Value:
     * An `OrderedList` of `string` word tokens.
 
@@ -1368,11 +1343,11 @@ edit-distance-contains(expression1, expression2, threshold)
 <!--### hashed-word-tokens ###
  * Syntax:
 
-        hashed-word-tokens(string_expression)
+        hashed-word-tokens(string)
 
- * Returns a list of hashed word tokens of `string_expression`.
+ * Returns a list of hashed word tokens of `string`.
  * Arguments:
-    * `string_expression` : A `string` that will be tokenized.
+    * `string` : A `string` that will be tokenized.
  * Return Value:
    * An `OrderedList` of `int32` hashed tokens.
 
@@ -1397,11 +1372,11 @@ edit-distance-contains(expression1, expression2, threshold)
 ### counthashed-word-tokens ###
  * Syntax:
 
-        counthashed-word-tokens(string_expression)
+        counthashed-word-tokens(string)
 
- * Returns a list of hashed word tokens of `string_expression`. The hashing mechanism gives duplicate tokens different hash values, based on the occurrence count of that token.
+ * Returns a list of hashed word tokens of `string`. The hashing mechanism gives duplicate tokens different hash values, based on the occurrence count of that token.
  * Arguments:
-    * `string_expression` : A `String` that will be tokenized.
+    * `string` : A `String` that will be tokenized.
  * Return Value:
     * An `OrderedList` of `Int32` hashed tokens.
  * Example:
@@ -1425,13 +1400,13 @@ edit-distance-contains(expression1, expression2, threshold)
 ### gram-tokens ###
  * Syntax:
 
-        gram-tokens(string_expression, gram_length, boolean_expression)
+        gram-tokens(string, gram_length, boolean_expression)
 
- * Returns a list of gram tokens of `string_expression`, which can be obtained by scanning the characters using a sliding window of a fixed length.
+ * Returns a list of gram tokens of `string`, which can be obtained by scanning the characters using a sliding window of a fixed length.
  * Arguments:
-    * `string_expression` : A `String` that will be tokenized.
+    * `string` : A `String` that will be tokenized.
     * `gram_length` : An `Int32` as the length of grams.
-   * `boolean_expression` : A `Boolean` value to indicate whether to generate additional grams by pre- and postfixing `string_expression` with special characters.
+   * `boolean_expression` : A `Boolean` value to indicate whether to generate additional grams by pre- and postfixing `string` with special characters.
  * Return Value:
     * An `OrderedList` of String gram tokens.
 
@@ -1460,13 +1435,13 @@ edit-distance-contains(expression1, expression2, threshold)
 ### hashed-gram-tokens ###
  * Syntax:
 
-        hashed-gram-tokens(string_expression, gram_length, boolean_expression)
+        hashed-gram-tokens(string, gram_length, boolean_expression)
 
- * Returns a list of hashed gram tokens of `string_expression`.
+ * Returns a list of hashed gram tokens of `string`.
  * Arguments:
-    * `string_expression` : A `String` that will be tokenized.
+    * `string` : A `String` that will be tokenized.
     * `gram_length` : An `Int32` as the length of grams.
-    * `boolean_expression` : A `Boolean` to indicate whether to generate additional grams by pre- and postfixing `string_expression` with special characters.
+    * `boolean_expression` : A `Boolean` to indicate whether to generate additional grams by pre- and postfixing `string` with special characters.
  * Return Value:
     * An `OrderedList` of `Int32` hashed gram tokens.
 
@@ -1497,13 +1472,13 @@ edit-distance-contains(expression1, expression2, threshold)
 ### counthashed-gram-tokens ###
  * Syntax:
 
-        counthashed-gram-tokens(string_expression, gram_length, boolean_expression)
+        counthashed-gram-tokens(string, gram_length, boolean_expression)
 
- * Returns a list of hashed gram tokens of `string_expression`. The hashing mechanism gives duplicate tokens different hash values, based on the occurrence count of that token.
+ * Returns a list of hashed gram tokens of `string`. The hashing mechanism gives duplicate tokens different hash values, based on the occurrence count of that token.
  * Arguments:
-    * `string_expression` : A `String` that will be tokenized.
+    * `string` : A `String` that will be tokenized.
     * `gram_length` : An `Int32`, length of grams to generate.
-    * `boolean_expression` : A `Boolean`, whether to generate additional grams by pre- and postfixing `string_expression` with special characters.
+    * `boolean_expression` : A `Boolean`, whether to generate additional grams by pre- and postfixing `string` with special characters.
  * Return Value:
     * An `OrderedList` of `Int32` hashed gram tokens.
 
@@ -1537,11 +1512,11 @@ edit-distance-contains(expression1, expression2, threshold)
 ### get-year/get-month/get-day/get-hour/get-minute/get-second/get-millisecond ###
  * Syntax:
 
-        get-year/get-month/get-day/get-hour/get-minute/get-second/get-millisecond(temporal_expression)
+        get-year/get-month/get-day/get-hour/get-minute/get-second/get-millisecond(temporal_value)
 
  * Accessors for accessing fields in a temporal value
  * Arguments:
-    * `temporal_expression` : a temporal value represented as one of the following types: `date`, `datetime`, `time`, and `duration`.
+    * `temporal_value` : a temporal value represented as one of the following types: `date`, `datetime`, `time`, and `duration`.
  * Return Value:
     * An `int64` value representing the field to be extracted.
 
@@ -1563,12 +1538,12 @@ edit-distance-contains(expression1, expression2, threshold)
 ### adjust-datetime-for-timezone ###
  * Syntax:
 
-        adjust-datetime-for-timezone(datetime_expression, string_expression)
+        adjust-datetime-for-timezone(datetime, string)
 
- * Adjusts the given datetime `datetime_expression` by applying the timezone information `string_expression`.
+ * Adjusts the given datetime `datetime` by applying the timezone information `string`.
  * Arguments:
-    * `datetime_expression` : A `datetime` value to be adjusted.
-    * `string_expression` : A `string` representing the timezone information.
+    * `datetime` : A `datetime` value to be adjusted.
+    * `string` : A `string` representing the timezone information.
  * Return Value:
     * A `string` value representing the new datetime after being adjusted by the timezone information.
 
@@ -1599,12 +1574,12 @@ edit-distance-contains(expression1, expression2, threshold)
 ### adjust-time-for-timezone ###
  * Syntax:
 
-        adjust-time-for-timezone(time_expression, string_expression)
+        adjust-time-for-timezone(time, string)
 
- * Adjusts the given time `time_expression` by applying the timezone information `string_expression`.
+ * Adjusts the given time `time` by applying the timezone information `string`.
  * Arguments:
-    * `time_expression` : A `time` value to be adjusted.
-    * `string_expression` : A `string` representing the timezone information.
+    * `time` : A `time` value to be adjusted.
+    * `string` : A `string` representing the timezone information.
  * Return Value:
     * A `string` value representing the new time after being adjusted by the timezone information.
 
@@ -1635,14 +1610,14 @@ edit-distance-contains(expression1, expression2, threshold)
 ### calendar-duration-from-datetime ###
  * Syntax:
 
-        calendar-duration-from-datetime(datetime_expression, duration_expression)
+        calendar-duration-from-datetime(datetime, duration_value)
 
- * Gets a user-friendly representation of the duration `duration_expression` based on the given datetime `datetime_expression`.
+ * Gets a user-friendly representation of the duration `duration_value` based on the given datetime `datetime`.
  * Arguments:
-    * `datetime_expression` : A `datetime` value to be used as the reference time point.
-    * `duration_expression` : A `duration` value to be converted.
+    * `datetime` : A `datetime` value to be used as the reference time point.
+    * `duration_value` : A `duration` value to be converted.
  * Return Value:
-    * A `duration` value with the duration as `duration_expression` but with a user-friendly representation.
+    * A `duration` value with the duration as `duration_value` but with a user-friendly representation.
 
  * Example:
 
@@ -1663,11 +1638,11 @@ edit-distance-contains(expression1, expression2, threshold)
 ### get-year-month-duration/get-day-time-duration ###
  * Syntax:
 
-        get-year-month-duration/get-day-time-duration(duration_expression)
+        get-year-month-duration/get-day-time-duration(duration_value)
 
- * Extracts the correct `duration` subtype from `duration_expression`.
+ * Extracts the correct `duration` subtype from `duration_value`.
  * Arguments:
-    * `duration_expression` : A `duration` value to be converted.
+    * `duration_value` : A `duration` value to be converted.
  * Return Value:
     * A `year-month-duration` value or a `day-time-duration` value.
 
@@ -1684,11 +1659,11 @@ edit-distance-contains(expression1, expression2, threshold)
 ### months-from-year-month-duration/milliseconds-from-day-time-duration ###
 * Syntax:
 
-        months-from-year-month-duration/milliseconds-from-day-time-duration(duration_expression)
+        months-from-year-month-duration/milliseconds-from-day-time-duration(duration_value)
 
 * Extracts the number of months or the number of milliseconds from the `duration` subtype.
 * Arguments:
-    * `duration_expression` : A `duration` of the correct subtype.
+    * `duration_value` : A `duration` of the correct subtype.
 * Return Value:
     * An `int64` representing the number or months/milliseconds.
 
@@ -1706,13 +1681,13 @@ edit-distance-contains(expression1, expression2, threshold)
 ### duration-from-months/duration-from-ms ###
 * Syntax:
 
-        duration-from-months/duration-from-ms(number_expression)
+        duration-from-months/duration-from-ms(number_value)
 
-* Creates a `duration` from `number_expression`.
+* Creates a `duration` from `number_value`.
 * Arguments:
-    * `number_expression` : An `int64` representing the number of months/milliseconds
+    * `number_value` : An `int64` representing the number of months/milliseconds
 * Return Value:
-    * A `duration` containing `number_expression` value for months/milliseconds
+    * A `duration` containing `number_value` value for months/milliseconds
 
 * Example:
 
@@ -1727,13 +1702,13 @@ edit-distance-contains(expression1, expression2, threshold)
 ### duration-from-interval ###
 * Syntax:
 
-        duration-from-interval(interval_expression)
+        duration-from-interval(interval_value)
 
-* Creates a `duration` from `interval_expression`.
+* Creates a `duration` from `interval_value`.
 * Arguments:
-    * `interval_expression` : An `interval` value
+    * `interval_value` : An `interval` value
 * Return Value:
-    * A `duration` repesenting the time in the `interval_expression`
+    * A `duration` repesenting the time in the `interval_value`
 
 * Example:
 
@@ -1745,7 +1720,7 @@ edit-distance-contains(expression1, expression2, threshold)
           "dr2" : duration-from-interval($itv2),
           "dr3" : duration-from-interval($itv3),
           "dr4" : duration-from-interval(null) }
-          
+
 * The expected result is:
 
         { "dr1": day-time-duration("P52D"),
@@ -1801,22 +1776,22 @@ edit-distance-contains(expression1, expression2, threshold)
 ### get-date-from-datetime ###
  * Syntax:
 
-        get-date-from-datetime(datetime_expression)
+        get-date-from-datetime(datetime)
 
- * Gets the date value from the given datetime value `datetime_expression`.
+ * Gets the date value from the given datetime value `datetime`.
  * Arguments:
-    * `datetime_expression`: A `datetime` value to be extracted from.
+    * `datetime`: A `datetime` value to be extracted from.
  * Return Value:
     * A `date` value from the datetime.
 
 ### get-time-from-datetime ###
  * Syntax:
 
-        get-time-from-datetime(datetime_expression)
+        get-time-from-datetime(datetime)
 
- * Get the time value from the given datetime value `datetime_expression`
+ * Get the time value from the given datetime value `datetime`
  * Arguments:
-    * `datetime_expression`: A `datetime` value to be extracted from
+    * `datetime`: A `datetime` value to be extracted from
  * Return Value:
     * A `time` value from the datetime.
 
@@ -1839,11 +1814,11 @@ edit-distance-contains(expression1, expression2, threshold)
 ### day-of-week ###
 * Syntax:
 
-        day-of-week(date_expression)
+        day-of-week(date)
 
 * Finds the day of the week for a given date (1-7)
 * Arguments:
-    * `date_expression`: A `date` value (Can also be a `datetime`)
+    * `date`: A `date` value (Can also be a `datetime`)
 * Return Value:
     * An `int8` representing the day of the week (1-7)
 
@@ -1861,59 +1836,59 @@ edit-distance-contains(expression1, expression2, threshold)
 ### date-from-unix-time-in-days ###
  * Syntax:
 
-        date-from-unix-time-in-days(numeric_expression)
+        date-from-unix-time-in-days(numeric_value)
 
- * Gets a date representing the time after `numeric_expression` days since 1970-01-01.
+ * Gets a date representing the time after `numeric_value` days since 1970-01-01.
  * Arguments:
-    * `numeric_expression`: A `int8`/`int16`/`int32`/`int64` value representing the number of days.
+    * `numeric_value`: A `int8`/`int16`/`int32`/`int64` value representing the number of days.
  * Return Value:
-    * A `date` value as the time after `numeric_expression` days since 1970-01-01.
+    * A `date` value as the time after `numeric_value` days since 1970-01-01.
 
 ### datetime-from-unix-time-in-ms ###
  * Syntax:
 
-        datetime-from-unix-time-in-ms(numeric_expression)
+        datetime-from-unix-time-in-ms(numeric_value)
 
- * Gets a datetime representing the time after `numeric_expression` milliseconds since 1970-01-01T00:00:00Z.
+ * Gets a datetime representing the time after `numeric_value` milliseconds since 1970-01-01T00:00:00Z.
  * Arguments:
-    * `numeric_expression`: A `int8`/`int16`/`int32`/`int64` value representing the number of milliseconds.
+    * `numeric_value`: A `int8`/`int16`/`int32`/`int64` value representing the number of milliseconds.
  * Return Value:
-    * A `datetime` value as the time after `numeric_expression` milliseconds since 1970-01-01T00:00:00Z.
+    * A `datetime` value as the time after `numeric_value` milliseconds since 1970-01-01T00:00:00Z.
 
 ### datetime-from-unix-time-in-secs ###
  * Syntax:
 
-        datetime-from-unix-time-in-secs(numeric_expression)
+        datetime-from-unix-time-in-secs(numeric_value)
 
- * Gets a datetime representing the time after `numeric_expression` seconds since 1970-01-01T00:00:00Z.
+ * Gets a datetime representing the time after `numeric_value` seconds since 1970-01-01T00:00:00Z.
  * Arguments:
-    * `numeric_expression`: A `int8`/`int16`/`int32`/`int64` value representing the number of seconds.
+    * `numeric_value`: A `int8`/`int16`/`int32`/`int64` value representing the number of seconds.
  * Return Value:
-    * A `datetime` value as the time after `numeric_expression` seconds since 1970-01-01T00:00:00Z.
+    * A `datetime` value as the time after `numeric_value` seconds since 1970-01-01T00:00:00Z.
 
 
 ### datetime-from-date-time ###
 * Syntax:
 
-datetime-from-date-time(date_expression,time_expression)
+datetime-from-date-time(date,time)
 
-* Gets a datetime representing the combination of `date_expression` and `time_expression`
+* Gets a datetime representing the combination of `date` and `time`
     * Arguments:
-    * `date_expression`: A `date` value
-    * `time_expression` A `time` value
+    * `date`: A `date` value
+    * `time` A `time` value
 * Return Value:
-    * A `datetime` value by combining `date_expression` and `time_expression`
+    * A `datetime` value by combining `date` and `time`
 
 ### time-from-unix-time-in-ms ###
  * Syntax:
 
-        time-from-unix-time-in-ms(numeric_expression)
+        time-from-unix-time-in-ms(numeric_value)
 
- * Gets a time representing the time after `numeric_expression` milliseconds since 00:00:00.000Z.
+ * Gets a time representing the time after `numeric_value` milliseconds since 00:00:00.000Z.
  * Arguments:
-    * `numeric_expression`: A `int8`/`int16`/`int32`/`int64` value representing the number of milliseconds.
+    * `numeric_value`: A `int8`/`int16`/`int32`/`int64` value representing the number of milliseconds.
  * Return Value:
-    * A `time` value as the time after `numeric_expression` milliseconds since 00:00:00.000Z.
+    * A `time` value as the time after `numeric_value` milliseconds since 00:00:00.000Z.
 
  * Example:
 
@@ -1933,11 +1908,11 @@ datetime-from-date-time(date_expression,time_expression)
 ### parse-date/parse-time/parse-datetime ###
 * Syntax:
 
-parse-date/parse-time/parse-datetime(date_expression,formatting_expression)
+parse-date/parse-time/parse-datetime(date,formatting_expression)
 
-* Creates a `date/time/date-time` value by treating `date_expression` with formatting `formatting_expression`
+* Creates a `date/time/date-time` value by treating `date` with formatting `formatting_expression`
 * Arguments:
-    * `date_expression`: A `string` value representing the `date/time/datetime`. 
+    * `date`: A `string` value representing the `date/time/datetime`.
     * `formatting_expression` A `string` value providing the formatting for `date_expression`.Characters used to create date expression:
        * `h` hours
        * `m` minutes
@@ -1951,7 +1926,7 @@ parse-date/parse-time/parse-datetime(date_expression,formatting_expression)
        * `W` weekday
        * `-`, `'`, `/`, `.`, `,`, `T` seperators for both time and date
 * Return Value:
-    * A `date/time/date-time` value corresponding to `date_expression`
+    * A `date/time/date-time` value corresponding to `date`
 
 * Example:
 
@@ -1966,11 +1941,11 @@ parse-date/parse-time/parse-datetime(date_expression,formatting_expression)
 ### print-date/print-time/print-datetime ###
 * Syntax:
 
-print-date/print-time/print-datetime(date_expression,formatting_expression)
+        print-date/print-time/print-datetime(date,formatting_expression)
 
-* Creates a `string` representing a `date/time/date-time` value of the `date_expression` using the formatting `formatting_expression`
+* Creates a `string` representing a `date/time/date-time` value of the `date` using the formatting `formatting_expression`
 * Arguments:
-    * `date_expression`: A `date/time/datetime` value.
+    * `date`: A `date/time/datetime` value.
     * `formatting_expression` A `string` value providing the formatting for `date_expression`. Characters used to create date expression:
        * `h` hours
        * `m` minutes
@@ -1984,7 +1959,7 @@ print-date/print-time/print-datetime(date_expression,formatting_expression)
        * `W` weekday
        * `-`, `'`, `/`, `.`, `,`, `T` seperators for both time and date
 * Return Value:
-    * A `string` value corresponding to `date_expression`
+    * A `string` value corresponding to `date`
 
 * Example:
 
@@ -2045,18 +2020,18 @@ print-date/print-time/print-datetime(date_expression,formatting_expression)
 ### get-overlapping-interval ###
  * Syntax:
 
-        get-overlapping-interval(interval_expression_1, interval_expression_2)
+        get-overlapping-interval(interval1, interval2)
 
  * Gets the start/end of the given interval for the specific date/datetime/time type.
  * Arguments:
-    * `interval_expression_1`: an `interval` value
-    * `interval_expression_2`: an `interval` value
+    * `interval1`: an `interval` value
+    * `interval2`: an `interval` value
  * Return Value:
-    * Returns an `interval` that is overlapping `interval_expression_1` and `interval_expression_2`. If `interval_expression_1` and `interval_expression_2` do not overlap `null` is returned. Note each interval must be of the same type.
+    * Returns an `interval` that is overlapping `interval1` and `interval2`. If `interval1` and `interval2` do not overlap `null` is returned. Note each interval must be of the same type.
 
  * Example:
 
-        { "overlap1": get-overlapping-interval(interval-from-time(time("11:23:39"), time("18:27:19")), interval-from-time(time("12:23:39"), time("23:18:00"))), 
+        { "overlap1": get-overlapping-interval(interval-from-time(time("11:23:39"), time("18:27:19")), interval-from-time(time("12:23:39"), time("23:18:00"))),
           "overlap2": get-overlapping-interval(interval-from-time(time("12:23:39"), time("18:27:19")), interval-from-time(time("07:19:39"), time("09:18:00"))),
           "overlap3": get-overlapping-interval(interval-from-date(date("1980-11-30"), date("1999-09-09")), interval-from-date(date("2013-01-01"), date("2014-01-01"))),
           "overlap4": get-overlapping-interval(interval-from-date(date("1980-11-30"), date("2099-09-09")), interval-from-date(date("2013-01-01"), date("2014-01-01"))),
@@ -2065,11 +2040,11 @@ print-date/print-time/print-datetime(date_expression,formatting_expression)
 
  * The expected result is:
 
-        { "overlap1": interval-time("12:23:39.000Z, 18:27:19.000Z"), 
-          "overlap2": null, 
-          "overlap3": null, 
-          "overlap4": interval-date("2013-01-01, 2014-01-01"), 
-          "overlap5": interval-datetime("1989-03-04T12:23:39.000Z, 2000-10-30T18:27:19.000Z"), 
+        { "overlap1": interval-time("12:23:39.000Z, 18:27:19.000Z"),
+          "overlap2": null,
+          "overlap3": null,
+          "overlap4": interval-date("2013-01-01, 2014-01-01"),
+          "overlap5": interval-datetime("1989-03-04T12:23:39.000Z, 2000-10-30T18:27:19.000Z"),
           "overlap6": null }
 
 
@@ -2120,12 +2095,12 @@ See the [Allen's Relations](allens.html).
 ### interval-from-date ###
  * Syntax:
 
-        interval-from-date(string_expression1, string_expression2)
+        interval-from-date(string1, string2)
 
  * Constructor function for the `interval` type by parsing two date strings.
  * Arguments:
-    * `string_expression1` : The `string` value representing the starting date.
-    * `string_expression2` : The `string` value representing the ending date.
+    * `string1` : The `string` value representing the starting date.
+    * `string2` : The `string` value representing the ending date.
  * Return Value:
     * An `interval` value between the two dates.
 
@@ -2142,12 +2117,12 @@ See the [Allen's Relations](allens.html).
 ### interval-from-time ###
  * Syntax:
 
-        interval-from-time(string_expression1, string_expression2)
+        interval-from-time(string1, string2)
 
  * Constructor function for the `interval` type by parsing two time strings.
  * Arguments:
-    * `string_expression1` : The `string` value representing the starting time.
-    * `string_expression2` : The `string` value representing the ending time.
+    * `string1` : The `string` value representing the starting time.
+    * `string2` : The `string` value representing the ending time.
  * Return Value:
     * An `interval` value between the two times.
 
@@ -2164,12 +2139,12 @@ See the [Allen's Relations](allens.html).
 ### interval-from-datetime ###
  * Syntax:
 
-        interval-from-datetime(string_expression1, string_expression2)
+        interval-from-datetime(string1, string2)
 
  * Constructor function for `interval` type by parsing two datetime strings.
  * Arguments:
-    * `string_expression1` : The `string` value representing the starting datetime.
-    * `string_expression2` : The `string` value representing the ending datetime.
+    * `string1` : The `string` value representing the starting datetime.
+    * `string2` : The `string` value representing the ending datetime.
  * Return Value:
     * An `interval` value between the two datetimes.
 
@@ -2213,11 +2188,11 @@ See the [Allen's Relations](allens.html).
 
  * Syntax:
 
-        overlap-bins(interval_expression, time-bin-anchor, duration-bin-size)
+        overlap-bins(interval, time-bin-anchor, duration-bin-size)
 
- * Returns an ordered list of `interval` values representing each bin that is overlapping the `interval_expression`.
+ * Returns an ordered list of `interval` values representing each bin that is overlapping the `interval`.
  * Arguments:
-    * `interval_expression`: an `interval` value
+    * `interval`: an `interval` value
     * `time-bin-anchor`: a date/time/datetime value representing an anchor of a bin starts. The type of this argument should be the same as the first `time-to-bin` argument.
     * `duration-bin-size`: the duration value representing the size of the bin, in the type of year-month-duration or day-time-duration. The type of this duration should be compatible with the type of `time-to-bin`, so that the arithmetic operation between `time-to-bin` and `duration-bin-size` is well-defined. Currently AsterixDB supports the following arithmetic operations:
         * datetime +|- year-month-duration
@@ -2226,7 +2201,7 @@ See the [Allen's Relations](allens.html).
         * date +|- day-time-duration
         * time +|- day-time-duration
   * Return Value:
-    * A ordered list of `interval` values representing each bin that is overlapping the `interval_expression`. Note that the internal type as `time-to-bin` and `duration-bin-size`.
+    * A ordered list of `interval` values representing each bin that is overlapping the `interval`. Note that the internal type as `time-to-bin` and `duration-bin-size`.
 
   * Example:
 
@@ -2236,11 +2211,11 @@ See the [Allen's Relations](allens.html).
         return { "timebins": overlap-bins($itv1, time("00:00:00"), day-time-duration("PT30M")),
           "datebins": overlap-bins($itv2, date("1990-01-01"), year-month-duration("P20Y")),
           "datetimebins": overlap-bins($itv3, datetime("1900-01-01T00:00:00.000"), year-month-duration("P100Y")) }
-          
+
    * The expected result is:
 
-        { "timebins": [ interval-time("17:00:00.000Z, 17:30:00.000Z"), interval-time("17:30:00.000Z, 18:00:00.000Z"), interval-time("18:00:00.000Z, 18:30:00.000Z"), interval-time("18:30:00.000Z, 19:00:00.000Z") ], 
-          "datebins": [ interval-date("1970-01-01, 1990-01-01"), interval-date("1990-01-01, 2010-01-01"), interval-date("2010-01-01, 2030-01-01") ], 
+        { "timebins": [ interval-time("17:00:00.000Z, 17:30:00.000Z"), interval-time("17:30:00.000Z, 18:00:00.000Z"), interval-time("18:00:00.000Z, 18:30:00.000Z"), interval-time("18:30:00.000Z, 19:00:00.000Z") ],
+          "datebins": [ interval-date("1970-01-01, 1990-01-01"), interval-date("1990-01-01, 2010-01-01"), interval-date("2010-01-01, 2030-01-01") ],
           "datetimebins": [ interval-datetime("1800-01-01T00:00:00.000Z, 1900-01-01T00:00:00.000Z"), interval-datetime("1900-01-01T00:00:00.000Z, 2000-01-01T00:00:00.000Z"), interval-datetime("2000-01-01T00:00:00.000Z, 2100-01-01T00:00:00.000Z") ] }
 
 
@@ -2250,52 +2225,52 @@ See the [Allen's Relations](allens.html).
 ### get-record-fields ###
  * Syntax:
 
-        get-record-fields(record_expression)
+        get-record-fields(input_record)
 
  * Access the record field names, type and open status for a given record.
  * Arguments:
-    * `record_expression` : a record value.
+    * `input_record` : a record value.
  * Return Value:
-    * An order list of `record` values that include the field-name `string`, field-type `string`, is-open `boolean` and optional nested `orderedList` for the values of a nested record.
+    * An order list of `record` values that include the field-name `string`, field-type `string`, is-open `boolean` (used for debug purposes only: `true` if field is open and `false` otherwise), and optional nested `orderedList` for the values of a nested record.
 
  * Example:
 
-        let $r1 := {"id": 1, 
-            "project": "AsterixDB", 
-            "address": {"city": "Irvine", "state": "CA"}, 
+        let $r1 := {"id": 1,
+            "project": "AsterixDB",
+            "address": {"city": "Irvine", "state": "CA"},
             "related": ["Hivestrix", "Preglix", "Apache VXQuery"] }
         return get-record-fields($r1)
 
  * The expected result is:
 
-        [ { "field-name": "id", "field-type": "INT64", "is-open": false }, 
-          { "field-name": "project", "field-type": "STRING", "is-open": false }, 
-          { "field-name": "address", "field-type": "RECORD", "is-open": false, "nested": [ 
-            { "field-name": "city", "field-type": "STRING", "is-open": false }, 
-            { "field-name": "state", "field-type": "STRING", "is-open": false } ] }, 
-          { "field-name": "related", "field-type": "ORDEREDLIST", "is-open": false, "list": [ 
-            { "field-type": "STRING" }, 
-            { "field-type": "STRING" }, 
+        [ { "field-name": "id", "field-type": "INT64", "is-open": false },
+          { "field-name": "project", "field-type": "STRING", "is-open": false },
+          { "field-name": "address", "field-type": "RECORD", "is-open": false, "nested": [
+            { "field-name": "city", "field-type": "STRING", "is-open": false },
+            { "field-name": "state", "field-type": "STRING", "is-open": false } ] },
+          { "field-name": "related", "field-type": "ORDEREDLIST", "is-open": false, "list": [
+            { "field-type": "STRING" },
+            { "field-type": "STRING" },
             { "field-type": "STRING" } ] } ]
 
  ]
 ### get-record-field-value ###
  * Syntax:
 
-        get-record-field-value(record_expression, string_expression)
+        get-record-field-value(input_record, string)
 
  * Access the field name given in the `string_expression` from the `record_expression`.
  * Arguments:
-    * `record_expression` : A `record` value.
-    * `string_expression` : A `string` representing the top level field name.
+    * `input_record` : A `record` value.
+    * `string` : A `string` representing the top level field name.
  * Return Value:
     * An `any` value saved in the designated field of the record.
 
  * Example:
 
-        let $r1 := {"id": 1, 
-            "project": "AsterixDB", 
-            "address": {"city": "Irvine", "state": "CA"}, 
+        let $r1 := {"id": 1,
+            "project": "AsterixDB",
+            "address": {"city": "Irvine", "state": "CA"},
             "related": ["Hivestrix", "Preglix", "Apache VXQuery"] }
         return get-record-field-value($r1, "project")
 
@@ -2303,9 +2278,99 @@ See the [Allen's Relations](allens.html).
 
         "AsterixDB"
 
+### record-remove-fields ###
+ * Syntax:
 
-## <a id="OtherFunctions">Other Functions</a> <font size="4"><a href="#toc">[Back to TOC]</a></font> ##
+        record-remove-fields(input_record, field_names)
+
+ * Remove indicated fields from a record given a list of field names.
+ * Arguments:
+    * `input_record`:  a record value.
+    * `field_names`: an ordered list of strings and/or ordered list of ordered list of strings.
+
+ * Return Value:
+    * A new record value without the fields listed in the second argument.
+
+
+ * Example:
+
+        let $r1 := {"id":1,
+            "project":"AsterixDB",
+            "address":{"city":"Irvine", "state":"CA"},
+            "related":["Hivestrix", "Preglix", "Apache VXQuery"] }
+        return remove-fields($r1, [["address", "city"], "related"])
+
+ * The expected result is:
+
+        { "id":1,
+        "project":"AsterixDB",
+        "address":{"state":"CA"}}
+
+### record-add-fields ###
+ * Syntax:
+
+        record-add-fields(input_record, fields)
 
+ * Add fields from a record given a list of field names.
+ * Arguments:
+    * `input_record` : a record value.
+    * `fields`: an ordered list of field descriptor records where each record has field-name and  field-value.
+ * Return Value:
+    * A new record value with the new fields included.
+
+
+ * Example:
+
+        let $r1 := {"id":1,
+            "project":"AsterixDB",
+            "address":{"city":"Irvine", "state":"CA"},
+            "related":["Hivestrix", "Preglix", "Apache VXQuery"] }
+        return record-add-fields($r1, [{"field-name":"employment-location", "field-value":create-point(30.0,70.0)}])
+
+ * The expected result is:
+
+        {"id":1,
+           "project":"AsterixDB",
+           "address":{"city":"Irvine", "state":"CA"},
+           "related":["Hivestrix", "Preglix", "Apache VXQuery"]
+           "employment-location": point("30.0,70.0")}
+
+### record-merge ###
+ * Syntax:
+
+        record-merge(record1, record2)
+
+ * Merge two different records into a new record.
+ * Arguments:
+    * `record1` : a record value.
+    * `record2` : a record value.
+ * Return Value:
+    * A new record value with fields from both input records. If a field’s names in both records are the same, an exception is issued.
+
+
+ * Example:
+
+        let $r1 := {"id":1,
+            "project":"AsterixDB",
+            "address":{"city":"Irvine", "state":"CA"},
+            "related":["Hivestrix", "Preglix", "Apache VXQuery"] }
+
+        let $r2 := {"user_id": 22,
+           "employer": "UC Irvine",
+           "employment-type": "visitor" }
+        return  record-merge($r1, $r2)
+
+ * The expected result is:
+
+        {"id":1,
+         "project":"AsterixDB",
+         "address":{"city":"Irvine", "state":"CA"},
+         "related":["Hivestrix", "Preglix", "Apache VXQuery"]
+         "user-id": 22,
+         "employer": "UC Irvine",
+         "employment-type": "visitor"}
+
+## <a id="OtherFunctions">Other Functions</a> <font size="4"><a href="#toc">[Back to TOC]</a></font> ##
 
 ### create-uuid ###
  * Syntax:
@@ -2357,13 +2422,13 @@ See the [Allen's Relations](allens.html).
 ### len ###
  * Syntax:
 
-    len(list_expression)
+    len(list)
 
- * Returns the length of the list list_expression.
+ * Returns the length of the list list.
  * Arguments:
-    * `list_expression` : An `OrderedList`, `UnorderedList` or `null`, represents the list need to be checked.
+    * `list` : An `OrderedList`, `UnorderedList` or `null`, represents the list need to be checked.
  * Return Value:
-    * An `Int32` that represents the length of list_expression.
+    * An `Int32` that represents the length of list.
 
  * Example:
 
@@ -2403,13 +2468,13 @@ See the [Allen's Relations](allens.html).
 ### range ###
  * Syntax:
 
-        range(start_numeric_expression, end_numeric_expression)
+        range(start_numeric_value, end_numeric_value)
 
-* Generates a series of `int64` values based start the `start_numeric_expression` until the `end_numeric_expression`.
+* Generates a series of `int64` values based start the `start_numeric_value` until the `end_numeric_value`.
   The `range` fucntion must be used list argument of a `for` expression.
 * Arguments:
-   * `start_numeric_expression`: A `int8`/`int16`/`int32`/`int64` value representing the start value.
-   * `end_numeric_expression`: A `int8`/`int16`/`int32`/`int64` value representing the max final value.
+   * `start_numeric_value`: A `int8`/`int16`/`int32`/`int64` value representing the start value.
+   * `end_numeric_value`: A `int8`/`int16`/`int32`/`int64` value representing the max final value.
 * Return Value:
     * A generated `uuid`.
 * Example:
@@ -2420,8 +2485,8 @@ See the [Allen's Relations](allens.html).
  * The expected result is:
 
         [ 0
-        , 1 
-        , 2 
+        , 1
+        , 2
         , 3
         ]
 
@@ -2470,3 +2535,33 @@ See the [Allen's Relations](allens.html).
         3
 
 
+### deep-equal ###
+* Syntax:
+
+        deep-equal(var1, var2)
+
+
+ * Assess the equality between two variables of any type (e.g., records and lists). Two objects are deeply equal iff both their types and values are equal.
+ * Arguments:
+    * `var1` : a data value, such as record and list.
+    * `var2`: a data value, such as record and list.
+ * Return Value:
+    * `true` or `false` depending on the data equality.
+
+
+ * Example:
+
+        let $r1 := {"id":1,
+            "project":"AsterixDB",
+            "address":{"city":"Irvine", "state":"CA"},
+            "related":["Hivestrix", "Preglix", "Apache VXQuery"] }
+
+        let $r2 := {"id":1,
+                    "project":"AsterixDB",
+                    "address":{"city":"San Diego", "state":"CA"},
+                    "related":["Hivestrix", "Preglix", "Apache VXQuery"] }
+        return deep-equal($r1, $r2)
+
+ * The expected result is:
+
+        false
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-om/src/main/java/org/apache/asterix/builders/IARecordBuilder.java
----------------------------------------------------------------------
diff --git a/asterix-om/src/main/java/org/apache/asterix/builders/IARecordBuilder.java b/asterix-om/src/main/java/org/apache/asterix/builders/IARecordBuilder.java
index 4512920..ee15d5d 100644
--- a/asterix-om/src/main/java/org/apache/asterix/builders/IARecordBuilder.java
+++ b/asterix-om/src/main/java/org/apache/asterix/builders/IARecordBuilder.java
@@ -52,7 +52,7 @@ public interface IARecordBuilder {
     /**
      * @param name
      *            The field name.
-     * @param out
+     * @param value
      *            The field value.
      * @throws AsterixException
      *             if the field name conflicts with a closed field name

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-om/src/main/java/org/apache/asterix/formats/nontagged/AqlSerializerDeserializerProvider.java
----------------------------------------------------------------------
diff --git a/asterix-om/src/main/java/org/apache/asterix/formats/nontagged/AqlSerializerDeserializerProvider.java b/asterix-om/src/main/java/org/apache/asterix/formats/nontagged/AqlSerializerDeserializerProvider.java
index 9ca94f1..9be8cae 100644
--- a/asterix-om/src/main/java/org/apache/asterix/formats/nontagged/AqlSerializerDeserializerProvider.java
+++ b/asterix-om/src/main/java/org/apache/asterix/formats/nontagged/AqlSerializerDeserializerProvider.java
@@ -18,11 +18,6 @@
  */
 package org.apache.asterix.formats.nontagged;
 
-import java.io.DataInput;
-import java.io.DataOutput;
-import java.io.IOException;
-import java.io.Serializable;
-
 import org.apache.asterix.dataflow.data.nontagged.serde.ABinarySerializerDeserializer;
 import org.apache.asterix.dataflow.data.nontagged.serde.ABooleanSerializerDeserializer;
 import org.apache.asterix.dataflow.data.nontagged.serde.ACircleSerializerDeserializer;
@@ -66,6 +61,11 @@ import org.apache.hyracks.api.dataflow.value.ISerializerDeserializer;
 import org.apache.hyracks.api.exceptions.HyracksDataException;
 import org.apache.hyracks.dataflow.common.data.marshalling.ShortSerializerDeserializer;
 
+import java.io.DataInput;
+import java.io.DataOutput;
+import java.io.IOException;
+import java.io.Serializable;
+
 public class AqlSerializerDeserializerProvider implements ISerializerDeserializerProvider, Serializable {
 
     private static final long serialVersionUID = 1L;

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-om/src/main/java/org/apache/asterix/om/functions/AsterixBuiltinFunctions.java
----------------------------------------------------------------------
diff --git a/asterix-om/src/main/java/org/apache/asterix/om/functions/AsterixBuiltinFunctions.java b/asterix-om/src/main/java/org/apache/asterix/om/functions/AsterixBuiltinFunctions.java
index ad4831f..7b8a9fa 100644
--- a/asterix-om/src/main/java/org/apache/asterix/om/functions/AsterixBuiltinFunctions.java
+++ b/asterix-om/src/main/java/org/apache/asterix/om/functions/AsterixBuiltinFunctions.java
@@ -18,12 +18,6 @@
  */
 package org.apache.asterix.om.functions;
 
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.List;
-import java.util.Map;
-import java.util.Set;
-
 import org.apache.asterix.common.functions.FunctionConstants;
 import org.apache.asterix.common.functions.FunctionSignature;
 import org.apache.asterix.om.typecomputer.base.IResultTypeComputer;
@@ -97,7 +91,9 @@ import org.apache.asterix.om.typecomputer.impl.OrderedListOfAPointTypeComputer;
 import org.apache.asterix.om.typecomputer.impl.OrderedListOfAStringTypeComputer;
 import org.apache.asterix.om.typecomputer.impl.OrderedListOfAnyTypeComputer;
 import org.apache.asterix.om.typecomputer.impl.QuadStringStringOrNullTypeComputer;
+import org.apache.asterix.om.typecomputer.impl.RecordAddFieldsTypeComputer;
 import org.apache.asterix.om.typecomputer.impl.RecordMergeTypeComputer;
+import org.apache.asterix.om.typecomputer.impl.RecordRemoveFieldsTypeComputer;
 import org.apache.asterix.om.typecomputer.impl.ScalarVersionOfAggregateResultType;
 import org.apache.asterix.om.typecomputer.impl.SubsetCollectionTypeComputer;
 import org.apache.asterix.om.typecomputer.impl.Substring2TypeComputer;
@@ -117,6 +113,12 @@ import org.apache.hyracks.algebricks.core.algebra.functions.AlgebricksBuiltinFun
 import org.apache.hyracks.algebricks.core.algebra.functions.FunctionIdentifier;
 import org.apache.hyracks.algebricks.core.algebra.functions.IFunctionInfo;
 
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+
 public class AsterixBuiltinFunctions {
 
     public enum SpatialFilterKind {
@@ -173,9 +175,17 @@ public class AsterixBuiltinFunctions {
     public final static FunctionIdentifier UNORDERED_LIST_CONSTRUCTOR = new FunctionIdentifier(
             FunctionConstants.ASTERIX_NS, "unordered-list-constructor", FunctionIdentifier.VARARGS);
 
+    public final static FunctionIdentifier DEEP_EQUAL = new FunctionIdentifier(FunctionConstants.ASTERIX_NS,
+            "deep-equal", 2);
+
     // records
     public final static FunctionIdentifier RECORD_MERGE = new FunctionIdentifier(FunctionConstants.ASTERIX_NS,
-            "record-merge", 3);
+            "record-merge", 2);
+    public final static FunctionIdentifier REMOVE_FIELDS = new FunctionIdentifier(FunctionConstants.ASTERIX_NS,
+            "record-remove-fields", 2);
+    public final static FunctionIdentifier ADD_FIELDS = new FunctionIdentifier(FunctionConstants.ASTERIX_NS,
+            "record-add-fields", 2);
+
     public final static FunctionIdentifier CLOSED_RECORD_CONSTRUCTOR = new FunctionIdentifier(
             FunctionConstants.ASTERIX_NS, "closed-record-constructor", FunctionIdentifier.VARARGS);
     public final static FunctionIdentifier OPEN_RECORD_CONSTRUCTOR = new FunctionIdentifier(
@@ -741,6 +751,9 @@ public class AsterixBuiltinFunctions {
         addPrivateFunction(OR, BinaryBooleanOrNullFunctionTypeComputer.INSTANCE, true);
         addPrivateFunction(NUMERIC_ADD, NonTaggedNumericAddSubMulDivTypeComputer.INSTANCE, true);
 
+        // Deep equality
+        addFunction(DEEP_EQUAL, BinaryBooleanOrNullFunctionTypeComputer.INSTANCE, true);
+
         // and then, Asterix builtin functions
         addPrivateFunction(NOT_NULL, NotNullTypeComputer.INSTANCE, true);
         addPrivateFunction(ANY_COLLECTION_MEMBER, NonTaggedCollectionMemberResultType.INSTANCE, true);
@@ -933,7 +946,9 @@ public class AsterixBuiltinFunctions {
         addFunction(WORD_TOKENS, OrderedListOfAStringTypeComputer.INSTANCE, true);
 
         // records
-        addPrivateFunction(RECORD_MERGE, RecordMergeTypeComputer.INSTANCE, true);
+        addFunction(RECORD_MERGE, RecordMergeTypeComputer.INSTANCE, true);
+        addFunction(ADD_FIELDS, RecordAddFieldsTypeComputer.INSTANCE, true);
+        addFunction(REMOVE_FIELDS, RecordRemoveFieldsTypeComputer.INSTANCE, true);
         addPrivateFunction(CLOSED_RECORD_CONSTRUCTOR, ClosedRecordConstructorResultType.INSTANCE, true);
         addPrivateFunction(OPEN_RECORD_CONSTRUCTOR, OpenRecordConstructorResultType.INSTANCE, true);
         addPrivateFunction(FIELD_ACCESS_BY_INDEX, FieldAccessByIndexResultType.INSTANCE, true);

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-om/src/main/java/org/apache/asterix/om/pointables/ARecordVisitablePointable.java
----------------------------------------------------------------------
diff --git a/asterix-om/src/main/java/org/apache/asterix/om/pointables/ARecordVisitablePointable.java b/asterix-om/src/main/java/org/apache/asterix/om/pointables/ARecordVisitablePointable.java
index 823ea3e..03e3895 100644
--- a/asterix-om/src/main/java/org/apache/asterix/om/pointables/ARecordVisitablePointable.java
+++ b/asterix-om/src/main/java/org/apache/asterix/om/pointables/ARecordVisitablePointable.java
@@ -19,11 +19,6 @@
 
 package org.apache.asterix.om.pointables;
 
-import java.io.DataOutputStream;
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.List;
-
 import org.apache.asterix.common.exceptions.AsterixException;
 import org.apache.asterix.dataflow.data.nontagged.AqlNullWriterFactory;
 import org.apache.asterix.dataflow.data.nontagged.serde.AInt32SerializerDeserializer;
@@ -40,6 +35,11 @@ import org.apache.asterix.om.util.container.IObjectFactory;
 import org.apache.hyracks.api.dataflow.value.INullWriter;
 import org.apache.hyracks.util.string.UTF8StringWriter;
 
+import java.io.DataOutputStream;
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.List;
+
 /**
  * This class interprets the binary data representation of a record. One can
  * call getFieldNames, getFieldTypeTags and getFieldValues to get pointable

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-om/src/main/java/org/apache/asterix/om/pointables/cast/ARecordCaster.java
----------------------------------------------------------------------
diff --git a/asterix-om/src/main/java/org/apache/asterix/om/pointables/cast/ARecordCaster.java b/asterix-om/src/main/java/org/apache/asterix/om/pointables/cast/ARecordCaster.java
index 7e41f3b..d89ae6a 100644
--- a/asterix-om/src/main/java/org/apache/asterix/om/pointables/cast/ARecordCaster.java
+++ b/asterix-om/src/main/java/org/apache/asterix/om/pointables/cast/ARecordCaster.java
@@ -19,14 +19,6 @@
 
 package org.apache.asterix.om.pointables.cast;
 
-import java.io.ByteArrayOutputStream;
-import java.io.DataOutput;
-import java.io.DataOutputStream;
-import java.io.IOException;
-import java.io.PrintStream;
-import java.util.ArrayList;
-import java.util.List;
-
 import org.apache.asterix.builders.RecordBuilder;
 import org.apache.asterix.common.exceptions.AsterixException;
 import org.apache.asterix.common.exceptions.TypeException;
@@ -55,6 +47,14 @@ import org.apache.hyracks.data.std.primitive.UTF8StringPointable;
 import org.apache.hyracks.data.std.util.ByteArrayAccessibleOutputStream;
 import org.apache.hyracks.util.string.UTF8StringWriter;
 
+import java.io.ByteArrayOutputStream;
+import java.io.DataOutput;
+import java.io.DataOutputStream;
+import java.io.IOException;
+import java.io.PrintStream;
+import java.util.ArrayList;
+import java.util.List;
+
 /**
  * This class is to do the runtime type cast for a record. It is ONLY visible to
  * ACastVisitor.


[4/6] incubator-asterixdb git commit: ASTERIXDB-1187, ASTERIXDB-1162 and ASTERIXDB-1252 fixes, plus new internal functions

Posted by ti...@apache.org.
http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/results/records/record-merge/tiny-social-example/tiny-social-example.4.adm
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/results/records/record-merge/tiny-social-example/tiny-social-example.4.adm b/asterix-app/src/test/resources/runtimets/results/records/record-merge/tiny-social-example/tiny-social-example.4.adm
new file mode 100644
index 0000000..ea3c1f5
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/results/records/record-merge/tiny-social-example/tiny-social-example.4.adm
@@ -0,0 +1,180 @@
+{ "message-text": " like samsung the platform is good", "referred-topics": {{ "samsung", "platform" }}, "send-time": datetime("2011-08-25T10:10:00.000Z"), "sender-location": point("36.21,72.6"), "tweetid": "7", "user": { "screen-name": "ChangEwing_573", "lang": "en", "friends_count": 182, "statuses_count": 394, "name": "Chang Ewing", "followers_count": 32136 }, "fb-user": 9, "fb-message": " love at&t its 3G is good:)" }
+, { "message-text": " like motorola the speed is good:)", "referred-topics": {{ "motorola", "speed" }}, "send-time": datetime("2006-11-04T10:10:00.000Z"), "sender-location": point("29.72,75.8"), "tweetid": "3", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 9, "fb-message": " love at&t its 3G is good:)" }
+, { "message-text": " like samsung the platform is good", "referred-topics": {{ "samsung", "platform" }}, "send-time": datetime("2011-08-25T10:10:00.000Z"), "sender-location": point("36.21,72.6"), "tweetid": "7", "user": { "screen-name": "ChangEwing_573", "lang": "en", "friends_count": 182, "statuses_count": 394, "name": "Chang Ewing", "followers_count": 32136 }, "fb-user": 1, "fb-message": " like verizon the 3G is awesome:)" }
+, { "message-text": " like samsung the platform is good", "referred-topics": {{ "samsung", "platform" }}, "send-time": datetime("2011-08-25T10:10:00.000Z"), "sender-location": point("36.21,72.6"), "tweetid": "7", "user": { "screen-name": "ChangEwing_573", "lang": "en", "friends_count": 182, "statuses_count": 394, "name": "Chang Ewing", "followers_count": 32136 }, "fb-user": 2, "fb-message": " like samsung the plan is amazing" }
+, { "message-text": " like samsung the platform is good", "referred-topics": {{ "samsung", "platform" }}, "send-time": datetime("2011-08-25T10:10:00.000Z"), "sender-location": point("36.21,72.6"), "tweetid": "7", "user": { "screen-name": "ChangEwing_573", "lang": "en", "friends_count": 182, "statuses_count": 394, "name": "Chang Ewing", "followers_count": 32136 }, "fb-user": 3, "fb-message": " love verizon its wireless is good" }
+, { "message-text": " like motorola the speed is good:)", "referred-topics": {{ "motorola", "speed" }}, "send-time": datetime("2006-11-04T10:10:00.000Z"), "sender-location": point("29.72,75.8"), "tweetid": "3", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 1, "fb-message": " like verizon the 3G is awesome:)" }
+, { "message-text": " like motorola the speed is good:)", "referred-topics": {{ "motorola", "speed" }}, "send-time": datetime("2006-11-04T10:10:00.000Z"), "sender-location": point("29.72,75.8"), "tweetid": "3", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 2, "fb-message": " like samsung the plan is amazing" }
+, { "message-text": " like motorola the speed is good:)", "referred-topics": {{ "motorola", "speed" }}, "send-time": datetime("2006-11-04T10:10:00.000Z"), "sender-location": point("29.72,75.8"), "tweetid": "3", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 3, "fb-message": " love verizon its wireless is good" }
+, { "message-text": " like samsung the platform is good", "referred-topics": {{ "samsung", "platform" }}, "send-time": datetime("2011-08-25T10:10:00.000Z"), "sender-location": point("36.21,72.6"), "tweetid": "7", "user": { "screen-name": "ChangEwing_573", "lang": "en", "friends_count": 182, "statuses_count": 394, "name": "Chang Ewing", "followers_count": 32136 }, "fb-user": 5, "fb-message": " dislike sprint the speed is horrible" }
+, { "message-text": " like samsung the platform is good", "referred-topics": {{ "samsung", "platform" }}, "send-time": datetime("2011-08-25T10:10:00.000Z"), "sender-location": point("36.21,72.6"), "tweetid": "7", "user": { "screen-name": "ChangEwing_573", "lang": "en", "friends_count": 182, "statuses_count": 394, "name": "Chang Ewing", "followers_count": 32136 }, "fb-user": 1, "fb-message": " can't stand at&t its plan is terrible" }
+, { "message-text": " like iphone the voice-clarity is good:)", "referred-topics": {{ "iphone", "voice-clarity" }}, "send-time": datetime("2010-05-07T10:10:00.000Z"), "sender-location": point("47.51,83.99"), "tweetid": "6", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 9, "fb-message": " love at&t its 3G is good:)" }
+, { "message-text": " like motorola the speed is good:)", "referred-topics": {{ "motorola", "speed" }}, "send-time": datetime("2006-11-04T10:10:00.000Z"), "sender-location": point("29.72,75.8"), "tweetid": "3", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 5, "fb-message": " dislike sprint the speed is horrible" }
+, { "message-text": " like motorola the speed is good:)", "referred-topics": {{ "motorola", "speed" }}, "send-time": datetime("2006-11-04T10:10:00.000Z"), "sender-location": point("29.72,75.8"), "tweetid": "3", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 1, "fb-message": " can't stand at&t its plan is terrible" }
+, { "message-text": " can't stand motorola its speed is terrible:(", "referred-topics": {{ "motorola", "speed" }}, "send-time": datetime("2006-08-04T10:10:00.000Z"), "sender-location": point("40.09,92.69"), "tweetid": "5", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 9, "fb-message": " love at&t its 3G is good:)" }
+, { "message-text": " can't stand iphone its platform is terrible", "referred-topics": {{ "iphone", "platform" }}, "send-time": datetime("2008-03-09T10:10:00.000Z"), "sender-location": point("37.59,68.42"), "tweetid": "11", "user": { "screen-name": "NilaMilliron_tw", "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Nila Milliron", "followers_count": 22649 }, "fb-user": 9, "fb-message": " love at&t its 3G is good:)" }
+, { "message-text": " hate verizon its voice-clarity is OMG:(", "referred-topics": {{ "verizon", "voice-clarity" }}, "send-time": datetime("2008-01-26T10:10:00.000Z"), "sender-location": point("29.15,76.53"), "tweetid": "10", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 9, "fb-message": " love at&t its 3G is good:)" }
+, { "message-text": " like samsung the platform is good", "referred-topics": {{ "samsung", "platform" }}, "send-time": datetime("2011-08-25T10:10:00.000Z"), "sender-location": point("36.21,72.6"), "tweetid": "7", "user": { "screen-name": "ChangEwing_573", "lang": "en", "friends_count": 182, "statuses_count": 394, "name": "Chang Ewing", "followers_count": 32136 }, "fb-user": 10, "fb-message": " dislike iphone the voice-command is bad:(" }
+, { "message-text": " like samsung the platform is good", "referred-topics": {{ "samsung", "platform" }}, "send-time": datetime("2011-08-25T10:10:00.000Z"), "sender-location": point("36.21,72.6"), "tweetid": "7", "user": { "screen-name": "ChangEwing_573", "lang": "en", "friends_count": 182, "statuses_count": 394, "name": "Chang Ewing", "followers_count": 32136 }, "fb-user": 1, "fb-message": " can't stand at&t the network is horrible:(" }
+, { "message-text": " like samsung the platform is good", "referred-topics": {{ "samsung", "platform" }}, "send-time": datetime("2011-08-25T10:10:00.000Z"), "sender-location": point("36.21,72.6"), "tweetid": "7", "user": { "screen-name": "ChangEwing_573", "lang": "en", "friends_count": 182, "statuses_count": 394, "name": "Chang Ewing", "followers_count": 32136 }, "fb-user": 2, "fb-message": " like t-mobile its platform is mind-blowing" }
+, { "message-text": " like samsung the platform is good", "referred-topics": {{ "samsung", "platform" }}, "send-time": datetime("2011-08-25T10:10:00.000Z"), "sender-location": point("36.21,72.6"), "tweetid": "7", "user": { "screen-name": "ChangEwing_573", "lang": "en", "friends_count": 182, "statuses_count": 394, "name": "Chang Ewing", "followers_count": 32136 }, "fb-user": 3, "fb-message": " love sprint its shortcut-menu is awesome:)" }
+, { "message-text": " like verizon its shortcut-menu is awesome:)", "referred-topics": {{ "verizon", "shortcut-menu" }}, "send-time": datetime("2010-05-13T10:10:00.000Z"), "sender-location": point("32.84,67.14"), "tweetid": "2", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 9, "fb-message": " love at&t its 3G is good:)" }
+, { "message-text": " like samsung the voice-command is amazing:)", "referred-topics": {{ "samsung", "voice-command" }}, "send-time": datetime("2010-02-13T10:10:00.000Z"), "sender-location": point("24.82,94.63"), "tweetid": "12", "user": { "screen-name": "OliJackson_512", "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Oli Jackson", "followers_count": 22649 }, "fb-user": 9, "fb-message": " love at&t its 3G is good:)" }
+, { "message-text": " like samsung the platform is good", "referred-topics": {{ "samsung", "platform" }}, "send-time": datetime("2011-08-25T10:10:00.000Z"), "sender-location": point("36.21,72.6"), "tweetid": "7", "user": { "screen-name": "ChangEwing_573", "lang": "en", "friends_count": 182, "statuses_count": 394, "name": "Chang Ewing", "followers_count": 32136 }, "fb-user": 1, "fb-message": " dislike iphone its touch-screen is horrible" }
+, { "message-text": " like motorola the speed is good:)", "referred-topics": {{ "motorola", "speed" }}, "send-time": datetime("2006-11-04T10:10:00.000Z"), "sender-location": point("29.72,75.8"), "tweetid": "3", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 10, "fb-message": " dislike iphone the voice-command is bad:(" }
+, { "message-text": " like iphone the voice-clarity is good:)", "referred-topics": {{ "iphone", "voice-clarity" }}, "send-time": datetime("2010-05-07T10:10:00.000Z"), "sender-location": point("47.51,83.99"), "tweetid": "6", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 1, "fb-message": " like verizon the 3G is awesome:)" }
+, { "message-text": " like iphone the voice-clarity is good:)", "referred-topics": {{ "iphone", "voice-clarity" }}, "send-time": datetime("2010-05-07T10:10:00.000Z"), "sender-location": point("47.51,83.99"), "tweetid": "6", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 2, "fb-message": " like samsung the plan is amazing" }
+, { "message-text": " like samsung the platform is good", "referred-topics": {{ "samsung", "platform" }}, "send-time": datetime("2011-08-25T10:10:00.000Z"), "sender-location": point("36.21,72.6"), "tweetid": "7", "user": { "screen-name": "ChangEwing_573", "lang": "en", "friends_count": 182, "statuses_count": 394, "name": "Chang Ewing", "followers_count": 32136 }, "fb-user": 7, "fb-message": " like iphone the voicemail-service is awesome" }
+, { "message-text": " like motorola the speed is good:)", "referred-topics": {{ "motorola", "speed" }}, "send-time": datetime("2006-11-04T10:10:00.000Z"), "sender-location": point("29.72,75.8"), "tweetid": "3", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 1, "fb-message": " can't stand at&t the network is horrible:(" }
+, { "message-text": " like motorola the speed is good:)", "referred-topics": {{ "motorola", "speed" }}, "send-time": datetime("2006-11-04T10:10:00.000Z"), "sender-location": point("29.72,75.8"), "tweetid": "3", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 2, "fb-message": " like t-mobile its platform is mind-blowing" }
+, { "message-text": " like motorola the speed is good:)", "referred-topics": {{ "motorola", "speed" }}, "send-time": datetime("2006-11-04T10:10:00.000Z"), "sender-location": point("29.72,75.8"), "tweetid": "3", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 3, "fb-message": " love sprint its shortcut-menu is awesome:)" }
+, { "message-text": " like iphone the voice-clarity is good:)", "referred-topics": {{ "iphone", "voice-clarity" }}, "send-time": datetime("2010-05-07T10:10:00.000Z"), "sender-location": point("47.51,83.99"), "tweetid": "6", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 3, "fb-message": " love verizon its wireless is good" }
+, { "message-text": " love t-mobile its customization is good:)", "referred-topics": {{ "t-mobile", "customization" }}, "send-time": datetime("2008-04-26T10:10:00.000Z"), "sender-location": point("47.44,80.65"), "tweetid": "1", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 9, "fb-message": " love at&t its 3G is good:)" }
+, { "message-text": " like samsung the platform is good", "referred-topics": {{ "samsung", "platform" }}, "send-time": datetime("2011-08-25T10:10:00.000Z"), "sender-location": point("36.21,72.6"), "tweetid": "7", "user": { "screen-name": "ChangEwing_573", "lang": "en", "friends_count": 182, "statuses_count": 394, "name": "Chang Ewing", "followers_count": 32136 }, "fb-user": 6, "fb-message": " love sprint the customization is mind-blowing" }
+, { "message-text": " like motorola the speed is good:)", "referred-topics": {{ "motorola", "speed" }}, "send-time": datetime("2006-11-04T10:10:00.000Z"), "sender-location": point("29.72,75.8"), "tweetid": "3", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 1, "fb-message": " dislike iphone its touch-screen is horrible" }
+, { "message-text": " can't stand motorola its speed is terrible:(", "referred-topics": {{ "motorola", "speed" }}, "send-time": datetime("2006-08-04T10:10:00.000Z"), "sender-location": point("40.09,92.69"), "tweetid": "5", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 1, "fb-message": " like verizon the 3G is awesome:)" }
+, { "message-text": " can't stand motorola its speed is terrible:(", "referred-topics": {{ "motorola", "speed" }}, "send-time": datetime("2006-08-04T10:10:00.000Z"), "sender-location": point("40.09,92.69"), "tweetid": "5", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 2, "fb-message": " like samsung the plan is amazing" }
+, { "message-text": " can't stand iphone its platform is terrible", "referred-topics": {{ "iphone", "platform" }}, "send-time": datetime("2008-03-09T10:10:00.000Z"), "sender-location": point("37.59,68.42"), "tweetid": "11", "user": { "screen-name": "NilaMilliron_tw", "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Nila Milliron", "followers_count": 22649 }, "fb-user": 1, "fb-message": " like verizon the 3G is awesome:)" }
+, { "message-text": " can't stand iphone its platform is terrible", "referred-topics": {{ "iphone", "platform" }}, "send-time": datetime("2008-03-09T10:10:00.000Z"), "sender-location": point("37.59,68.42"), "tweetid": "11", "user": { "screen-name": "NilaMilliron_tw", "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Nila Milliron", "followers_count": 22649 }, "fb-user": 2, "fb-message": " like samsung the plan is amazing" }
+, { "message-text": " hate verizon its voice-clarity is OMG:(", "referred-topics": {{ "verizon", "voice-clarity" }}, "send-time": datetime("2008-01-26T10:10:00.000Z"), "sender-location": point("29.15,76.53"), "tweetid": "10", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 1, "fb-message": " like verizon the 3G is awesome:)" }
+, { "message-text": " hate verizon its voice-clarity is OMG:(", "referred-topics": {{ "verizon", "voice-clarity" }}, "send-time": datetime("2008-01-26T10:10:00.000Z"), "sender-location": point("29.15,76.53"), "tweetid": "10", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 2, "fb-message": " like samsung the plan is amazing" }
+, { "message-text": " like motorola the speed is good:)", "referred-topics": {{ "motorola", "speed" }}, "send-time": datetime("2006-11-04T10:10:00.000Z"), "sender-location": point("29.72,75.8"), "tweetid": "3", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 7, "fb-message": " like iphone the voicemail-service is awesome" }
+, { "message-text": " can't stand motorola its speed is terrible:(", "referred-topics": {{ "motorola", "speed" }}, "send-time": datetime("2006-08-04T10:10:00.000Z"), "sender-location": point("40.09,92.69"), "tweetid": "5", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 3, "fb-message": " love verizon its wireless is good" }
+, { "message-text": " can't stand iphone its platform is terrible", "referred-topics": {{ "iphone", "platform" }}, "send-time": datetime("2008-03-09T10:10:00.000Z"), "sender-location": point("37.59,68.42"), "tweetid": "11", "user": { "screen-name": "NilaMilliron_tw", "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Nila Milliron", "followers_count": 22649 }, "fb-user": 3, "fb-message": " love verizon its wireless is good" }
+, { "message-text": " hate verizon its voice-clarity is OMG:(", "referred-topics": {{ "verizon", "voice-clarity" }}, "send-time": datetime("2008-01-26T10:10:00.000Z"), "sender-location": point("29.15,76.53"), "tweetid": "10", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 3, "fb-message": " love verizon its wireless is good" }
+, { "message-text": " like motorola the speed is good:)", "referred-topics": {{ "motorola", "speed" }}, "send-time": datetime("2006-11-04T10:10:00.000Z"), "sender-location": point("29.72,75.8"), "tweetid": "3", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 6, "fb-message": " love sprint the customization is mind-blowing" }
+, { "message-text": " like iphone the voice-clarity is good:)", "referred-topics": {{ "iphone", "voice-clarity" }}, "send-time": datetime("2010-05-07T10:10:00.000Z"), "sender-location": point("47.51,83.99"), "tweetid": "6", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 5, "fb-message": " dislike sprint the speed is horrible" }
+, { "message-text": " like t-mobile the shortcut-menu is awesome:)", "referred-topics": {{ "t-mobile", "shortcut-menu" }}, "send-time": datetime("2005-10-14T10:10:00.000Z"), "sender-location": point("46.05,93.34"), "tweetid": "8", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 9, "fb-message": " love at&t its 3G is good:)" }
+, { "message-text": " like iphone the voice-clarity is good:)", "referred-topics": {{ "iphone", "voice-clarity" }}, "send-time": datetime("2010-05-07T10:10:00.000Z"), "sender-location": point("47.51,83.99"), "tweetid": "6", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 1, "fb-message": " can't stand at&t its plan is terrible" }
+, { "message-text": " like verizon its shortcut-menu is awesome:)", "referred-topics": {{ "verizon", "shortcut-menu" }}, "send-time": datetime("2010-05-13T10:10:00.000Z"), "sender-location": point("32.84,67.14"), "tweetid": "2", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 1, "fb-message": " like verizon the 3G is awesome:)" }
+, { "message-text": " like verizon its shortcut-menu is awesome:)", "referred-topics": {{ "verizon", "shortcut-menu" }}, "send-time": datetime("2010-05-13T10:10:00.000Z"), "sender-location": point("32.84,67.14"), "tweetid": "2", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 2, "fb-message": " like samsung the plan is amazing" }
+, { "message-text": " like samsung the voice-command is amazing:)", "referred-topics": {{ "samsung", "voice-command" }}, "send-time": datetime("2010-02-13T10:10:00.000Z"), "sender-location": point("24.82,94.63"), "tweetid": "12", "user": { "screen-name": "OliJackson_512", "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Oli Jackson", "followers_count": 22649 }, "fb-user": 1, "fb-message": " like verizon the 3G is awesome:)" }
+, { "message-text": " like samsung the voice-command is amazing:)", "referred-topics": {{ "samsung", "voice-command" }}, "send-time": datetime("2010-02-13T10:10:00.000Z"), "sender-location": point("24.82,94.63"), "tweetid": "12", "user": { "screen-name": "OliJackson_512", "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Oli Jackson", "followers_count": 22649 }, "fb-user": 2, "fb-message": " like samsung the plan is amazing" }
+, { "message-text": " like sprint the voice-command is mind-blowing:)", "referred-topics": {{ "sprint", "voice-command" }}, "send-time": datetime("2011-12-26T10:10:00.000Z"), "sender-location": point("39.28,70.48"), "tweetid": "4", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 9, "fb-message": " love at&t its 3G is good:)" }
+, { "message-text": " like samsung the platform is good", "referred-topics": {{ "samsung", "platform" }}, "send-time": datetime("2011-08-25T10:10:00.000Z"), "sender-location": point("36.21,72.6"), "tweetid": "7", "user": { "screen-name": "ChangEwing_573", "lang": "en", "friends_count": 182, "statuses_count": 394, "name": "Chang Ewing", "followers_count": 32136 }, "fb-user": 1, "fb-message": " can't stand motorola the touch-screen is terrible" }
+, { "message-text": " can't stand motorola its speed is terrible:(", "referred-topics": {{ "motorola", "speed" }}, "send-time": datetime("2006-08-04T10:10:00.000Z"), "sender-location": point("40.09,92.69"), "tweetid": "5", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 5, "fb-message": " dislike sprint the speed is horrible" }
+, { "message-text": " can't stand iphone its platform is terrible", "referred-topics": {{ "iphone", "platform" }}, "send-time": datetime("2008-03-09T10:10:00.000Z"), "sender-location": point("37.59,68.42"), "tweetid": "11", "user": { "screen-name": "NilaMilliron_tw", "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Nila Milliron", "followers_count": 22649 }, "fb-user": 5, "fb-message": " dislike sprint the speed is horrible" }
+, { "message-text": " like verizon its shortcut-menu is awesome:)", "referred-topics": {{ "verizon", "shortcut-menu" }}, "send-time": datetime("2010-05-13T10:10:00.000Z"), "sender-location": point("32.84,67.14"), "tweetid": "2", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 3, "fb-message": " love verizon its wireless is good" }
+, { "message-text": " like samsung the voice-command is amazing:)", "referred-topics": {{ "samsung", "voice-command" }}, "send-time": datetime("2010-02-13T10:10:00.000Z"), "sender-location": point("24.82,94.63"), "tweetid": "12", "user": { "screen-name": "OliJackson_512", "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Oli Jackson", "followers_count": 22649 }, "fb-user": 3, "fb-message": " love verizon its wireless is good" }
+, { "message-text": " hate verizon its voice-clarity is OMG:(", "referred-topics": {{ "verizon", "voice-clarity" }}, "send-time": datetime("2008-01-26T10:10:00.000Z"), "sender-location": point("29.15,76.53"), "tweetid": "10", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 5, "fb-message": " dislike sprint the speed is horrible" }
+, { "message-text": " can't stand motorola its speed is terrible:(", "referred-topics": {{ "motorola", "speed" }}, "send-time": datetime("2006-08-04T10:10:00.000Z"), "sender-location": point("40.09,92.69"), "tweetid": "5", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 1, "fb-message": " can't stand at&t its plan is terrible" }
+, { "message-text": " can't stand iphone its platform is terrible", "referred-topics": {{ "iphone", "platform" }}, "send-time": datetime("2008-03-09T10:10:00.000Z"), "sender-location": point("37.59,68.42"), "tweetid": "11", "user": { "screen-name": "NilaMilliron_tw", "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Nila Milliron", "followers_count": 22649 }, "fb-user": 1, "fb-message": " can't stand at&t its plan is terrible" }
+, { "message-text": " hate verizon its voice-clarity is OMG:(", "referred-topics": {{ "verizon", "voice-clarity" }}, "send-time": datetime("2008-01-26T10:10:00.000Z"), "sender-location": point("29.15,76.53"), "tweetid": "10", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 1, "fb-message": " can't stand at&t its plan is terrible" }
+, { "message-text": " love t-mobile its customization is good:)", "referred-topics": {{ "t-mobile", "customization" }}, "send-time": datetime("2008-04-26T10:10:00.000Z"), "sender-location": point("47.44,80.65"), "tweetid": "1", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 1, "fb-message": " like verizon the 3G is awesome:)" }
+, { "message-text": " love t-mobile its customization is good:)", "referred-topics": {{ "t-mobile", "customization" }}, "send-time": datetime("2008-04-26T10:10:00.000Z"), "sender-location": point("47.44,80.65"), "tweetid": "1", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 2, "fb-message": " like samsung the plan is amazing" }
+, { "message-text": " like samsung the platform is good", "referred-topics": {{ "samsung", "platform" }}, "send-time": datetime("2011-08-25T10:10:00.000Z"), "sender-location": point("36.21,72.6"), "tweetid": "7", "user": { "screen-name": "ChangEwing_573", "lang": "en", "friends_count": 182, "statuses_count": 394, "name": "Chang Ewing", "followers_count": 32136 }, "fb-user": 10, "fb-message": " can't stand t-mobile its voicemail-service is OMG:(" }
+, { "message-text": " like motorola the speed is good:)", "referred-topics": {{ "motorola", "speed" }}, "send-time": datetime("2006-11-04T10:10:00.000Z"), "sender-location": point("29.72,75.8"), "tweetid": "3", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 1, "fb-message": " can't stand motorola the touch-screen is terrible" }
+, { "message-text": " love t-mobile its customization is good:)", "referred-topics": {{ "t-mobile", "customization" }}, "send-time": datetime("2008-04-26T10:10:00.000Z"), "sender-location": point("47.44,80.65"), "tweetid": "1", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 3, "fb-message": " love verizon its wireless is good" }
+, { "message-text": " love verizon its voicemail-service is awesome", "referred-topics": {{ "verizon", "voicemail-service" }}, "send-time": datetime("2012-07-21T10:10:00.000Z"), "sender-location": point("36.86,74.62"), "tweetid": "9", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 9, "fb-message": " love at&t its 3G is good:)" }
+, { "message-text": " like iphone the voice-clarity is good:)", "referred-topics": {{ "iphone", "voice-clarity" }}, "send-time": datetime("2010-05-07T10:10:00.000Z"), "sender-location": point("47.51,83.99"), "tweetid": "6", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 10, "fb-message": " dislike iphone the voice-command is bad:(" }
+, { "message-text": " like verizon its shortcut-menu is awesome:)", "referred-topics": {{ "verizon", "shortcut-menu" }}, "send-time": datetime("2010-05-13T10:10:00.000Z"), "sender-location": point("32.84,67.14"), "tweetid": "2", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 5, "fb-message": " dislike sprint the speed is horrible" }
+, { "message-text": " like samsung the voice-command is amazing:)", "referred-topics": {{ "samsung", "voice-command" }}, "send-time": datetime("2010-02-13T10:10:00.000Z"), "sender-location": point("24.82,94.63"), "tweetid": "12", "user": { "screen-name": "OliJackson_512", "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Oli Jackson", "followers_count": 22649 }, "fb-user": 5, "fb-message": " dislike sprint the speed is horrible" }
+, { "message-text": " like motorola the speed is good:)", "referred-topics": {{ "motorola", "speed" }}, "send-time": datetime("2006-11-04T10:10:00.000Z"), "sender-location": point("29.72,75.8"), "tweetid": "3", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 10, "fb-message": " can't stand t-mobile its voicemail-service is OMG:(" }
+, { "message-text": " like iphone the voice-clarity is good:)", "referred-topics": {{ "iphone", "voice-clarity" }}, "send-time": datetime("2010-05-07T10:10:00.000Z"), "sender-location": point("47.51,83.99"), "tweetid": "6", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 1, "fb-message": " can't stand at&t the network is horrible:(" }
+, { "message-text": " like iphone the voice-clarity is good:)", "referred-topics": {{ "iphone", "voice-clarity" }}, "send-time": datetime("2010-05-07T10:10:00.000Z"), "sender-location": point("47.51,83.99"), "tweetid": "6", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 2, "fb-message": " like t-mobile its platform is mind-blowing" }
+, { "message-text": " like iphone the voice-clarity is good:)", "referred-topics": {{ "iphone", "voice-clarity" }}, "send-time": datetime("2010-05-07T10:10:00.000Z"), "sender-location": point("47.51,83.99"), "tweetid": "6", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 3, "fb-message": " love sprint its shortcut-menu is awesome:)" }
+, { "message-text": " like verizon its shortcut-menu is awesome:)", "referred-topics": {{ "verizon", "shortcut-menu" }}, "send-time": datetime("2010-05-13T10:10:00.000Z"), "sender-location": point("32.84,67.14"), "tweetid": "2", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 1, "fb-message": " can't stand at&t its plan is terrible" }
+, { "message-text": " like samsung the voice-command is amazing:)", "referred-topics": {{ "samsung", "voice-command" }}, "send-time": datetime("2010-02-13T10:10:00.000Z"), "sender-location": point("24.82,94.63"), "tweetid": "12", "user": { "screen-name": "OliJackson_512", "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Oli Jackson", "followers_count": 22649 }, "fb-user": 1, "fb-message": " can't stand at&t its plan is terrible" }
+, { "message-text": " like t-mobile the shortcut-menu is awesome:)", "referred-topics": {{ "t-mobile", "shortcut-menu" }}, "send-time": datetime("2005-10-14T10:10:00.000Z"), "sender-location": point("46.05,93.34"), "tweetid": "8", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 1, "fb-message": " like verizon the 3G is awesome:)" }
+, { "message-text": " like t-mobile the shortcut-menu is awesome:)", "referred-topics": {{ "t-mobile", "shortcut-menu" }}, "send-time": datetime("2005-10-14T10:10:00.000Z"), "sender-location": point("46.05,93.34"), "tweetid": "8", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 2, "fb-message": " like samsung the plan is amazing" }
+, { "message-text": " can't stand motorola its speed is terrible:(", "referred-topics": {{ "motorola", "speed" }}, "send-time": datetime("2006-08-04T10:10:00.000Z"), "sender-location": point("40.09,92.69"), "tweetid": "5", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 10, "fb-message": " dislike iphone the voice-command is bad:(" }
+, { "message-text": " can't stand iphone its platform is terrible", "referred-topics": {{ "iphone", "platform" }}, "send-time": datetime("2008-03-09T10:10:00.000Z"), "sender-location": point("37.59,68.42"), "tweetid": "11", "user": { "screen-name": "NilaMilliron_tw", "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Nila Milliron", "followers_count": 22649 }, "fb-user": 10, "fb-message": " dislike iphone the voice-command is bad:(" }
+, { "message-text": " like iphone the voice-clarity is good:)", "referred-topics": {{ "iphone", "voice-clarity" }}, "send-time": datetime("2010-05-07T10:10:00.000Z"), "sender-location": point("47.51,83.99"), "tweetid": "6", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 1, "fb-message": " dislike iphone its touch-screen is horrible" }
+, { "message-text": " hate verizon its voice-clarity is OMG:(", "referred-topics": {{ "verizon", "voice-clarity" }}, "send-time": datetime("2008-01-26T10:10:00.000Z"), "sender-location": point("29.15,76.53"), "tweetid": "10", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 10, "fb-message": " dislike iphone the voice-command is bad:(" }
+, { "message-text": " like sprint the voice-command is mind-blowing:)", "referred-topics": {{ "sprint", "voice-command" }}, "send-time": datetime("2011-12-26T10:10:00.000Z"), "sender-location": point("39.28,70.48"), "tweetid": "4", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 1, "fb-message": " like verizon the 3G is awesome:)" }
+, { "message-text": " like sprint the voice-command is mind-blowing:)", "referred-topics": {{ "sprint", "voice-command" }}, "send-time": datetime("2011-12-26T10:10:00.000Z"), "sender-location": point("39.28,70.48"), "tweetid": "4", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 2, "fb-message": " like samsung the plan is amazing" }
+, { "message-text": " love t-mobile its customization is good:)", "referred-topics": {{ "t-mobile", "customization" }}, "send-time": datetime("2008-04-26T10:10:00.000Z"), "sender-location": point("47.44,80.65"), "tweetid": "1", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 5, "fb-message": " dislike sprint the speed is horrible" }
+, { "message-text": " like t-mobile the shortcut-menu is awesome:)", "referred-topics": {{ "t-mobile", "shortcut-menu" }}, "send-time": datetime("2005-10-14T10:10:00.000Z"), "sender-location": point("46.05,93.34"), "tweetid": "8", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 3, "fb-message": " love verizon its wireless is good" }
+, { "message-text": " can't stand motorola its speed is terrible:(", "referred-topics": {{ "motorola", "speed" }}, "send-time": datetime("2006-08-04T10:10:00.000Z"), "sender-location": point("40.09,92.69"), "tweetid": "5", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 1, "fb-message": " can't stand at&t the network is horrible:(" }
+, { "message-text": " can't stand motorola its speed is terrible:(", "referred-topics": {{ "motorola", "speed" }}, "send-time": datetime("2006-08-04T10:10:00.000Z"), "sender-location": point("40.09,92.69"), "tweetid": "5", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 2, "fb-message": " like t-mobile its platform is mind-blowing" }
+, { "message-text": " can't stand motorola its speed is terrible:(", "referred-topics": {{ "motorola", "speed" }}, "send-time": datetime("2006-08-04T10:10:00.000Z"), "sender-location": point("40.09,92.69"), "tweetid": "5", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 3, "fb-message": " love sprint its shortcut-menu is awesome:)" }
+, { "message-text": " can't stand iphone its platform is terrible", "referred-topics": {{ "iphone", "platform" }}, "send-time": datetime("2008-03-09T10:10:00.000Z"), "sender-location": point("37.59,68.42"), "tweetid": "11", "user": { "screen-name": "NilaMilliron_tw", "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Nila Milliron", "followers_count": 22649 }, "fb-user": 1, "fb-message": " can't stand at&t the network is horrible:(" }
+, { "message-text": " can't stand iphone its platform is terrible", "referred-topics": {{ "iphone", "platform" }}, "send-time": datetime("2008-03-09T10:10:00.000Z"), "sender-location": point("37.59,68.42"), "tweetid": "11", "user": { "screen-name": "NilaMilliron_tw", "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Nila Milliron", "followers_count": 22649 }, "fb-user": 2, "fb-message": " like t-mobile its platform is mind-blowing" }
+, { "message-text": " can't stand iphone its platform is terrible", "referred-topics": {{ "iphone", "platform" }}, "send-time": datetime("2008-03-09T10:10:00.000Z"), "sender-location": point("37.59,68.42"), "tweetid": "11", "user": { "screen-name": "NilaMilliron_tw", "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Nila Milliron", "followers_count": 22649 }, "fb-user": 3, "fb-message": " love sprint its shortcut-menu is awesome:)" }
+, { "message-text": " like iphone the voice-clarity is good:)", "referred-topics": {{ "iphone", "voice-clarity" }}, "send-time": datetime("2010-05-07T10:10:00.000Z"), "sender-location": point("47.51,83.99"), "tweetid": "6", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 7, "fb-message": " like iphone the voicemail-service is awesome" }
+, { "message-text": " hate verizon its voice-clarity is OMG:(", "referred-topics": {{ "verizon", "voice-clarity" }}, "send-time": datetime("2008-01-26T10:10:00.000Z"), "sender-location": point("29.15,76.53"), "tweetid": "10", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 1, "fb-message": " can't stand at&t the network is horrible:(" }
+, { "message-text": " hate verizon its voice-clarity is OMG:(", "referred-topics": {{ "verizon", "voice-clarity" }}, "send-time": datetime("2008-01-26T10:10:00.000Z"), "sender-location": point("29.15,76.53"), "tweetid": "10", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 2, "fb-message": " like t-mobile its platform is mind-blowing" }
+, { "message-text": " hate verizon its voice-clarity is OMG:(", "referred-topics": {{ "verizon", "voice-clarity" }}, "send-time": datetime("2008-01-26T10:10:00.000Z"), "sender-location": point("29.15,76.53"), "tweetid": "10", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 3, "fb-message": " love sprint its shortcut-menu is awesome:)" }
+, { "message-text": " like sprint the voice-command is mind-blowing:)", "referred-topics": {{ "sprint", "voice-command" }}, "send-time": datetime("2011-12-26T10:10:00.000Z"), "sender-location": point("39.28,70.48"), "tweetid": "4", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 3, "fb-message": " love verizon its wireless is good" }
+, { "message-text": " love t-mobile its customization is good:)", "referred-topics": {{ "t-mobile", "customization" }}, "send-time": datetime("2008-04-26T10:10:00.000Z"), "sender-location": point("47.44,80.65"), "tweetid": "1", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 1, "fb-message": " can't stand at&t its plan is terrible" }
+, { "message-text": " can't stand motorola its speed is terrible:(", "referred-topics": {{ "motorola", "speed" }}, "send-time": datetime("2006-08-04T10:10:00.000Z"), "sender-location": point("40.09,92.69"), "tweetid": "5", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 1, "fb-message": " dislike iphone its touch-screen is horrible" }
+, { "message-text": " can't stand iphone its platform is terrible", "referred-topics": {{ "iphone", "platform" }}, "send-time": datetime("2008-03-09T10:10:00.000Z"), "sender-location": point("37.59,68.42"), "tweetid": "11", "user": { "screen-name": "NilaMilliron_tw", "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Nila Milliron", "followers_count": 22649 }, "fb-user": 1, "fb-message": " dislike iphone its touch-screen is horrible" }
+, { "message-text": " like iphone the voice-clarity is good:)", "referred-topics": {{ "iphone", "voice-clarity" }}, "send-time": datetime("2010-05-07T10:10:00.000Z"), "sender-location": point("47.51,83.99"), "tweetid": "6", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 6, "fb-message": " love sprint the customization is mind-blowing" }
+, { "message-text": " hate verizon its voice-clarity is OMG:(", "referred-topics": {{ "verizon", "voice-clarity" }}, "send-time": datetime("2008-01-26T10:10:00.000Z"), "sender-location": point("29.15,76.53"), "tweetid": "10", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 1, "fb-message": " dislike iphone its touch-screen is horrible" }
+, { "message-text": " can't stand motorola its speed is terrible:(", "referred-topics": {{ "motorola", "speed" }}, "send-time": datetime("2006-08-04T10:10:00.000Z"), "sender-location": point("40.09,92.69"), "tweetid": "5", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 7, "fb-message": " like iphone the voicemail-service is awesome" }
+, { "message-text": " can't stand iphone its platform is terrible", "referred-topics": {{ "iphone", "platform" }}, "send-time": datetime("2008-03-09T10:10:00.000Z"), "sender-location": point("37.59,68.42"), "tweetid": "11", "user": { "screen-name": "NilaMilliron_tw", "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Nila Milliron", "followers_count": 22649 }, "fb-user": 7, "fb-message": " like iphone the voicemail-service is awesome" }
+, { "message-text": " like verizon its shortcut-menu is awesome:)", "referred-topics": {{ "verizon", "shortcut-menu" }}, "send-time": datetime("2010-05-13T10:10:00.000Z"), "sender-location": point("32.84,67.14"), "tweetid": "2", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 10, "fb-message": " dislike iphone the voice-command is bad:(" }
+, { "message-text": " like samsung the voice-command is amazing:)", "referred-topics": {{ "samsung", "voice-command" }}, "send-time": datetime("2010-02-13T10:10:00.000Z"), "sender-location": point("24.82,94.63"), "tweetid": "12", "user": { "screen-name": "OliJackson_512", "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Oli Jackson", "followers_count": 22649 }, "fb-user": 10, "fb-message": " dislike iphone the voice-command is bad:(" }
+, { "message-text": " hate verizon its voice-clarity is OMG:(", "referred-topics": {{ "verizon", "voice-clarity" }}, "send-time": datetime("2008-01-26T10:10:00.000Z"), "sender-location": point("29.15,76.53"), "tweetid": "10", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 7, "fb-message": " like iphone the voicemail-service is awesome" }
+, { "message-text": " like t-mobile the shortcut-menu is awesome:)", "referred-topics": {{ "t-mobile", "shortcut-menu" }}, "send-time": datetime("2005-10-14T10:10:00.000Z"), "sender-location": point("46.05,93.34"), "tweetid": "8", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 5, "fb-message": " dislike sprint the speed is horrible" }
+, { "message-text": " love verizon its voicemail-service is awesome", "referred-topics": {{ "verizon", "voicemail-service" }}, "send-time": datetime("2012-07-21T10:10:00.000Z"), "sender-location": point("36.86,74.62"), "tweetid": "9", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 1, "fb-message": " like verizon the 3G is awesome:)" }
+, { "message-text": " love verizon its voicemail-service is awesome", "referred-topics": {{ "verizon", "voicemail-service" }}, "send-time": datetime("2012-07-21T10:10:00.000Z"), "sender-location": point("36.86,74.62"), "tweetid": "9", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 2, "fb-message": " like samsung the plan is amazing" }
+, { "message-text": " can't stand motorola its speed is terrible:(", "referred-topics": {{ "motorola", "speed" }}, "send-time": datetime("2006-08-04T10:10:00.000Z"), "sender-location": point("40.09,92.69"), "tweetid": "5", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 6, "fb-message": " love sprint the customization is mind-blowing" }
+, { "message-text": " can't stand iphone its platform is terrible", "referred-topics": {{ "iphone", "platform" }}, "send-time": datetime("2008-03-09T10:10:00.000Z"), "sender-location": point("37.59,68.42"), "tweetid": "11", "user": { "screen-name": "NilaMilliron_tw", "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Nila Milliron", "followers_count": 22649 }, "fb-user": 6, "fb-message": " love sprint the customization is mind-blowing" }
+, { "message-text": " like verizon its shortcut-menu is awesome:)", "referred-topics": {{ "verizon", "shortcut-menu" }}, "send-time": datetime("2010-05-13T10:10:00.000Z"), "sender-location": point("32.84,67.14"), "tweetid": "2", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 1, "fb-message": " can't stand at&t the network is horrible:(" }
+, { "message-text": " like verizon its shortcut-menu is awesome:)", "referred-topics": {{ "verizon", "shortcut-menu" }}, "send-time": datetime("2010-05-13T10:10:00.000Z"), "sender-location": point("32.84,67.14"), "tweetid": "2", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 2, "fb-message": " like t-mobile its platform is mind-blowing" }
+, { "message-text": " like verizon its shortcut-menu is awesome:)", "referred-topics": {{ "verizon", "shortcut-menu" }}, "send-time": datetime("2010-05-13T10:10:00.000Z"), "sender-location": point("32.84,67.14"), "tweetid": "2", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 3, "fb-message": " love sprint its shortcut-menu is awesome:)" }
+, { "message-text": " like samsung the voice-command is amazing:)", "referred-topics": {{ "samsung", "voice-command" }}, "send-time": datetime("2010-02-13T10:10:00.000Z"), "sender-location": point("24.82,94.63"), "tweetid": "12", "user": { "screen-name": "OliJackson_512", "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Oli Jackson", "followers_count": 22649 }, "fb-user": 1, "fb-message": " can't stand at&t the network is horrible:(" }
+, { "message-text": " like samsung the voice-command is amazing:)", "referred-topics": {{ "samsung", "voice-command" }}, "send-time": datetime("2010-02-13T10:10:00.000Z"), "sender-location": point("24.82,94.63"), "tweetid": "12", "user": { "screen-name": "OliJackson_512", "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Oli Jackson", "followers_count": 22649 }, "fb-user": 2, "fb-message": " like t-mobile its platform is mind-blowing" }
+, { "message-text": " like samsung the voice-command is amazing:)", "referred-topics": {{ "samsung", "voice-command" }}, "send-time": datetime("2010-02-13T10:10:00.000Z"), "sender-location": point("24.82,94.63"), "tweetid": "12", "user": { "screen-name": "OliJackson_512", "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Oli Jackson", "followers_count": 22649 }, "fb-user": 3, "fb-message": " love sprint its shortcut-menu is awesome:)" }
+, { "message-text": " hate verizon its voice-clarity is OMG:(", "referred-topics": {{ "verizon", "voice-clarity" }}, "send-time": datetime("2008-01-26T10:10:00.000Z"), "sender-location": point("29.15,76.53"), "tweetid": "10", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 6, "fb-message": " love sprint the customization is mind-blowing" }
+, { "message-text": " like sprint the voice-command is mind-blowing:)", "referred-topics": {{ "sprint", "voice-command" }}, "send-time": datetime("2011-12-26T10:10:00.000Z"), "sender-location": point("39.28,70.48"), "tweetid": "4", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 5, "fb-message": " dislike sprint the speed is horrible" }
+, { "message-text": " like t-mobile the shortcut-menu is awesome:)", "referred-topics": {{ "t-mobile", "shortcut-menu" }}, "send-time": datetime("2005-10-14T10:10:00.000Z"), "sender-location": point("46.05,93.34"), "tweetid": "8", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 1, "fb-message": " can't stand at&t its plan is terrible" }
+, { "message-text": " love verizon its voicemail-service is awesome", "referred-topics": {{ "verizon", "voicemail-service" }}, "send-time": datetime("2012-07-21T10:10:00.000Z"), "sender-location": point("36.86,74.62"), "tweetid": "9", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 3, "fb-message": " love verizon its wireless is good" }
+, { "message-text": " like verizon its shortcut-menu is awesome:)", "referred-topics": {{ "verizon", "shortcut-menu" }}, "send-time": datetime("2010-05-13T10:10:00.000Z"), "sender-location": point("32.84,67.14"), "tweetid": "2", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 1, "fb-message": " dislike iphone its touch-screen is horrible" }
+, { "message-text": " like samsung the voice-command is amazing:)", "referred-topics": {{ "samsung", "voice-command" }}, "send-time": datetime("2010-02-13T10:10:00.000Z"), "sender-location": point("24.82,94.63"), "tweetid": "12", "user": { "screen-name": "OliJackson_512", "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Oli Jackson", "followers_count": 22649 }, "fb-user": 1, "fb-message": " dislike iphone its touch-screen is horrible" }
+, { "message-text": " like sprint the voice-command is mind-blowing:)", "referred-topics": {{ "sprint", "voice-command" }}, "send-time": datetime("2011-12-26T10:10:00.000Z"), "sender-location": point("39.28,70.48"), "tweetid": "4", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 1, "fb-message": " can't stand at&t its plan is terrible" }
+, { "message-text": " love t-mobile its customization is good:)", "referred-topics": {{ "t-mobile", "customization" }}, "send-time": datetime("2008-04-26T10:10:00.000Z"), "sender-location": point("47.44,80.65"), "tweetid": "1", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 10, "fb-message": " dislike iphone the voice-command is bad:(" }
+, { "message-text": " like iphone the voice-clarity is good:)", "referred-topics": {{ "iphone", "voice-clarity" }}, "send-time": datetime("2010-05-07T10:10:00.000Z"), "sender-location": point("47.51,83.99"), "tweetid": "6", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 1, "fb-message": " can't stand motorola the touch-screen is terrible" }
+, { "message-text": " like verizon its shortcut-menu is awesome:)", "referred-topics": {{ "verizon", "shortcut-menu" }}, "send-time": datetime("2010-05-13T10:10:00.000Z"), "sender-location": point("32.84,67.14"), "tweetid": "2", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 7, "fb-message": " like iphone the voicemail-service is awesome" }
+, { "message-text": " like samsung the voice-command is amazing:)", "referred-topics": {{ "samsung", "voice-command" }}, "send-time": datetime("2010-02-13T10:10:00.000Z"), "sender-location": point("24.82,94.63"), "tweetid": "12", "user": { "screen-name": "OliJackson_512", "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Oli Jackson", "followers_count": 22649 }, "fb-user": 7, "fb-message": " like iphone the voicemail-service is awesome" }
+, { "message-text": " love t-mobile its customization is good:)", "referred-topics": {{ "t-mobile", "customization" }}, "send-time": datetime("2008-04-26T10:10:00.000Z"), "sender-location": point("47.44,80.65"), "tweetid": "1", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 1, "fb-message": " can't stand at&t the network is horrible:(" }
+, { "message-text": " love t-mobile its customization is good:)", "referred-topics": {{ "t-mobile", "customization" }}, "send-time": datetime("2008-04-26T10:10:00.000Z"), "sender-location": point("47.44,80.65"), "tweetid": "1", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 2, "fb-message": " like t-mobile its platform is mind-blowing" }
+, { "message-text": " love t-mobile its customization is good:)", "referred-topics": {{ "t-mobile", "customization" }}, "send-time": datetime("2008-04-26T10:10:00.000Z"), "sender-location": point("47.44,80.65"), "tweetid": "1", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 3, "fb-message": " love sprint its shortcut-menu is awesome:)" }
+, { "message-text": " like verizon its shortcut-menu is awesome:)", "referred-topics": {{ "verizon", "shortcut-menu" }}, "send-time": datetime("2010-05-13T10:10:00.000Z"), "sender-location": point("32.84,67.14"), "tweetid": "2", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 6, "fb-message": " love sprint the customization is mind-blowing" }
+, { "message-text": " like samsung the voice-command is amazing:)", "referred-topics": {{ "samsung", "voice-command" }}, "send-time": datetime("2010-02-13T10:10:00.000Z"), "sender-location": point("24.82,94.63"), "tweetid": "12", "user": { "screen-name": "OliJackson_512", "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Oli Jackson", "followers_count": 22649 }, "fb-user": 6, "fb-message": " love sprint the customization is mind-blowing" }
+, { "message-text": " love t-mobile its customization is good:)", "referred-topics": {{ "t-mobile", "customization" }}, "send-time": datetime("2008-04-26T10:10:00.000Z"), "sender-location": point("47.44,80.65"), "tweetid": "1", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 1, "fb-message": " dislike iphone its touch-screen is horrible" }
+, { "message-text": " love verizon its voicemail-service is awesome", "referred-topics": {{ "verizon", "voicemail-service" }}, "send-time": datetime("2012-07-21T10:10:00.000Z"), "sender-location": point("36.86,74.62"), "tweetid": "9", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 5, "fb-message": " dislike sprint the speed is horrible" }
+, { "message-text": " can't stand motorola its speed is terrible:(", "referred-topics": {{ "motorola", "speed" }}, "send-time": datetime("2006-08-04T10:10:00.000Z"), "sender-location": point("40.09,92.69"), "tweetid": "5", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 1, "fb-message": " can't stand motorola the touch-screen is terrible" }
+, { "message-text": " can't stand iphone its platform is terrible", "referred-topics": {{ "iphone", "platform" }}, "send-time": datetime("2008-03-09T10:10:00.000Z"), "sender-location": point("37.59,68.42"), "tweetid": "11", "user": { "screen-name": "NilaMilliron_tw", "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Nila Milliron", "followers_count": 22649 }, "fb-user": 1, "fb-message": " can't stand motorola the touch-screen is terrible" }
+, { "message-text": " like iphone the voice-clarity is good:)", "referred-topics": {{ "iphone", "voice-clarity" }}, "send-time": datetime("2010-05-07T10:10:00.000Z"), "sender-location": point("47.51,83.99"), "tweetid": "6", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 10, "fb-message": " can't stand t-mobile its voicemail-service is OMG:(" }
+, { "message-text": " hate verizon its voice-clarity is OMG:(", "referred-topics": {{ "verizon", "voice-clarity" }}, "send-time": datetime("2008-01-26T10:10:00.000Z"), "sender-location": point("29.15,76.53"), "tweetid": "10", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 1, "fb-message": " can't stand motorola the touch-screen is terrible" }
+, { "message-text": " love t-mobile its customization is good:)", "referred-topics": {{ "t-mobile", "customization" }}, "send-time": datetime("2008-04-26T10:10:00.000Z"), "sender-location": point("47.44,80.65"), "tweetid": "1", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 7, "fb-message": " like iphone the voicemail-service is awesome" }
+, { "message-text": " like t-mobile the shortcut-menu is awesome:)", "referred-topics": {{ "t-mobile", "shortcut-menu" }}, "send-time": datetime("2005-10-14T10:10:00.000Z"), "sender-location": point("46.05,93.34"), "tweetid": "8", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 10, "fb-message": " dislike iphone the voice-command is bad:(" }
+, { "message-text": " love verizon its voicemail-service is awesome", "referred-topics": {{ "verizon", "voicemail-service" }}, "send-time": datetime("2012-07-21T10:10:00.000Z"), "sender-location": point("36.86,74.62"), "tweetid": "9", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 1, "fb-message": " can't stand at&t its plan is terrible" }
+, { "message-text": " like sprint the voice-command is mind-blowing:)", "referred-topics": {{ "sprint", "voice-command" }}, "send-time": datetime("2011-12-26T10:10:00.000Z"), "sender-location": point("39.28,70.48"), "tweetid": "4", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 10, "fb-message": " dislike iphone the voice-command is bad:(" }
+, { "message-text": " love t-mobile its customization is good:)", "referred-topics": {{ "t-mobile", "customization" }}, "send-time": datetime("2008-04-26T10:10:00.000Z"), "sender-location": point("47.44,80.65"), "tweetid": "1", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 6, "fb-message": " love sprint the customization is mind-blowing" }
+, { "message-text": " like t-mobile the shortcut-menu is awesome:)", "referred-topics": {{ "t-mobile", "shortcut-menu" }}, "send-time": datetime("2005-10-14T10:10:00.000Z"), "sender-location": point("46.05,93.34"), "tweetid": "8", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 1, "fb-message": " can't stand at&t the network is horrible:(" }
+, { "message-text": " like t-mobile the shortcut-menu is awesome:)", "referred-topics": {{ "t-mobile", "shortcut-menu" }}, "send-time": datetime("2005-10-14T10:10:00.000Z"), "sender-location": point("46.05,93.34"), "tweetid": "8", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 2, "fb-message": " like t-mobile its platform is mind-blowing" }
+, { "message-text": " like t-mobile the shortcut-menu is awesome:)", "referred-topics": {{ "t-mobile", "shortcut-menu" }}, "send-time": datetime("2005-10-14T10:10:00.000Z"), "sender-location": point("46.05,93.34"), "tweetid": "8", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 3, "fb-message": " love sprint its shortcut-menu is awesome:)" }
+, { "message-text": " can't stand motorola its speed is terrible:(", "referred-topics": {{ "motorola", "speed" }}, "send-time": datetime("2006-08-04T10:10:00.000Z"), "sender-location": point("40.09,92.69"), "tweetid": "5", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 10, "fb-message": " can't stand t-mobile its voicemail-service is OMG:(" }
+, { "message-text": " can't stand iphone its platform is terrible", "referred-topics": {{ "iphone", "platform" }}, "send-time": datetime("2008-03-09T10:10:00.000Z"), "sender-location": point("37.59,68.42"), "tweetid": "11", "user": { "screen-name": "NilaMilliron_tw", "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Nila Milliron", "followers_count": 22649 }, "fb-user": 10, "fb-message": " can't stand t-mobile its voicemail-service is OMG:(" }
+, { "message-text": " hate verizon its voice-clarity is OMG:(", "referred-topics": {{ "verizon", "voice-clarity" }}, "send-time": datetime("2008-01-26T10:10:00.000Z"), "sender-location": point("29.15,76.53"), "tweetid": "10", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 10, "fb-message": " can't stand t-mobile its voicemail-service is OMG:(" }
+, { "message-text": " like sprint the voice-command is mind-blowing:)", "referred-topics": {{ "sprint", "voice-command" }}, "send-time": datetime("2011-12-26T10:10:00.000Z"), "sender-location": point("39.28,70.48"), "tweetid": "4", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 1, "fb-message": " can't stand at&t the network is horrible:(" }
+, { "message-text": " like sprint the voice-command is mind-blowing:)", "referred-topics": {{ "sprint", "voice-command" }}, "send-time": datetime("2011-12-26T10:10:00.000Z"), "sender-location": point("39.28,70.48"), "tweetid": "4", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 2, "fb-message": " like t-mobile its platform is mind-blowing" }
+, { "message-text": " like sprint the voice-command is mind-blowing:)", "referred-topics": {{ "sprint", "voice-command" }}, "send-time": datetime("2011-12-26T10:10:00.000Z"), "sender-location": point("39.28,70.48"), "tweetid": "4", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 3, "fb-message": " love sprint its shortcut-menu is awesome:)" }
+, { "message-text": " like t-mobile the shortcut-menu is awesome:)", "referred-topics": {{ "t-mobile", "shortcut-menu" }}, "send-time": datetime("2005-10-14T10:10:00.000Z"), "sender-location": point("46.05,93.34"), "tweetid": "8", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 1, "fb-message": " dislike iphone its touch-screen is horrible" }
+, { "message-text": " like verizon its shortcut-menu is awesome:)", "referred-topics": {{ "verizon", "shortcut-menu" }}, "send-time": datetime("2010-05-13T10:10:00.000Z"), "sender-location": point("32.84,67.14"), "tweetid": "2", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 1, "fb-message": " can't stand motorola the touch-screen is terrible" }
+, { "message-text": " like samsung the voice-command is amazing:)", "referred-topics": {{ "samsung", "voice-command" }}, "send-time": datetime("2010-02-13T10:10:00.000Z"), "sender-location": point("24.82,94.63"), "tweetid": "12", "user": { "screen-name": "OliJackson_512", "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Oli Jackson", "followers_count": 22649 }, "fb-user": 1, "fb-message": " can't stand motorola the touch-screen is terrible" }
+, { "message-text": " like sprint the voice-command is mind-blowing:)", "referred-topics": {{ "sprint", "voice-command" }}, "send-time": datetime("2011-12-26T10:10:00.000Z"), "sender-location": point("39.28,70.48"), "tweetid": "4", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 1, "fb-message": " dislike iphone its touch-screen is horrible" }
+, { "message-text": " like t-mobile the shortcut-menu is awesome:)", "referred-topics": {{ "t-mobile", "shortcut-menu" }}, "send-time": datetime("2005-10-14T10:10:00.000Z"), "sender-location": point("46.05,93.34"), "tweetid": "8", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 7, "fb-message": " like iphone the voicemail-service is awesome" }
+, { "message-text": " like sprint the voice-command is mind-blowing:)", "referred-topics": {{ "sprint", "voice-command" }}, "send-time": datetime("2011-12-26T10:10:00.000Z"), "sender-location": point("39.28,70.48"), "tweetid": "4", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 7, "fb-message": " like iphone the voicemail-service is awesome" }
+, { "message-text": " like t-mobile the shortcut-menu is awesome:)", "referred-topics": {{ "t-mobile", "shortcut-menu" }}, "send-time": datetime("2005-10-14T10:10:00.000Z"), "sender-location": point("46.05,93.34"), "tweetid": "8", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 6, "fb-message": " love sprint the customization is mind-blowing" }
+, { "message-text": " love verizon its voicemail-service is awesome", "referred-topics": {{ "verizon", "voicemail-service" }}, "send-time": datetime("2012-07-21T10:10:00.000Z"), "sender-location": point("36.86,74.62"), "tweetid": "9", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 10, "fb-message": " dislike iphone the voice-command is bad:(" }
+, { "message-text": " like verizon its shortcut-menu is awesome:)", "referred-topics": {{ "verizon", "shortcut-menu" }}, "send-time": datetime("2010-05-13T10:10:00.000Z"), "sender-location": point("32.84,67.14"), "tweetid": "2", "user": { "screen-name": "ColineGeyer@63", "lang": "en", "friends_count": 121, "statuses_count": 362, "name": "Coline Geyer", "followers_count": 17159 }, "fb-user": 10, "fb-message": " can't stand t-mobile its voicemail-service is OMG:(" }
+, { "message-text": " like samsung the voice-command is amazing:)", "referred-topics": {{ "samsung", "voice-command" }}, "send-time": datetime("2010-02-13T10:10:00.000Z"), "sender-location": point("24.82,94.63"), "tweetid": "12", "user": { "screen-name": "OliJackson_512", "lang": "en", "friends_count": 445, "statuses_count": 164, "name": "Oli Jackson", "followers_count": 22649 }, "fb-user": 10, "fb-message": " can't stand t-mobile its voicemail-service is OMG:(" }
+, { "message-text": " like sprint the voice-command is mind-blowing:)", "referred-topics": {{ "sprint", "voice-command" }}, "send-time": datetime("2011-12-26T10:10:00.000Z"), "sender-location": point("39.28,70.48"), "tweetid": "4", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 6, "fb-message": " love sprint the customization is mind-blowing" }
+, { "message-text": " love t-mobile its customization is good:)", "referred-topics": {{ "t-mobile", "customization" }}, "send-time": datetime("2008-04-26T10:10:00.000Z"), "sender-location": point("47.44,80.65"), "tweetid": "1", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 1, "fb-message": " can't stand motorola the touch-screen is terrible" }
+, { "message-text": " love verizon its voicemail-service is awesome", "referred-topics": {{ "verizon", "voicemail-service" }}, "send-time": datetime("2012-07-21T10:10:00.000Z"), "sender-location": point("36.86,74.62"), "tweetid": "9", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 1, "fb-message": " can't stand at&t the network is horrible:(" }
+, { "message-text": " love verizon its voicemail-service is awesome", "referred-topics": {{ "verizon", "voicemail-service" }}, "send-time": datetime("2012-07-21T10:10:00.000Z"), "sender-location": point("36.86,74.62"), "tweetid": "9", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 2, "fb-message": " like t-mobile its platform is mind-blowing" }
+, { "message-text": " love verizon its voicemail-service is awesome", "referred-topics": {{ "verizon", "voicemail-service" }}, "send-time": datetime("2012-07-21T10:10:00.000Z"), "sender-location": point("36.86,74.62"), "tweetid": "9", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 3, "fb-message": " love sprint its shortcut-menu is awesome:)" }
+, { "message-text": " love verizon its voicemail-service is awesome", "referred-topics": {{ "verizon", "voicemail-service" }}, "send-time": datetime("2012-07-21T10:10:00.000Z"), "sender-location": point("36.86,74.62"), "tweetid": "9", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 1, "fb-message": " dislike iphone its touch-screen is horrible" }
+, { "message-text": " love t-mobile its customization is good:)", "referred-topics": {{ "t-mobile", "customization" }}, "send-time": datetime("2008-04-26T10:10:00.000Z"), "sender-location": point("47.44,80.65"), "tweetid": "1", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 10, "fb-message": " can't stand t-mobile its voicemail-service is OMG:(" }
+, { "message-text": " love verizon its voicemail-service is awesome", "referred-topics": {{ "verizon", "voicemail-service" }}, "send-time": datetime("2012-07-21T10:10:00.000Z"), "sender-location": point("36.86,74.62"), "tweetid": "9", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 7, "fb-message": " like iphone the voicemail-service is awesome" }
+, { "message-text": " like t-mobile the shortcut-menu is awesome:)", "referred-topics": {{ "t-mobile", "shortcut-menu" }}, "send-time": datetime("2005-10-14T10:10:00.000Z"), "sender-location": point("46.05,93.34"), "tweetid": "8", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 1, "fb-message": " can't stand motorola the touch-screen is terrible" }
+, { "message-text": " love verizon its voicemail-service is awesome", "referred-topics": {{ "verizon", "voicemail-service" }}, "send-time": datetime("2012-07-21T10:10:00.000Z"), "sender-location": point("36.86,74.62"), "tweetid": "9", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 6, "fb-message": " love sprint the customization is mind-blowing" }
+, { "message-text": " like sprint the voice-command is mind-blowing:)", "referred-topics": {{ "sprint", "voice-command" }}, "send-time": datetime("2011-12-26T10:10:00.000Z"), "sender-location": point("39.28,70.48"), "tweetid": "4", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 1, "fb-message": " can't stand motorola the touch-screen is terrible" }
+, { "message-text": " like t-mobile the shortcut-menu is awesome:)", "referred-topics": {{ "t-mobile", "shortcut-menu" }}, "send-time": datetime("2005-10-14T10:10:00.000Z"), "sender-location": point("46.05,93.34"), "tweetid": "8", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 10, "fb-message": " can't stand t-mobile its voicemail-service is OMG:(" }
+, { "message-text": " like sprint the voice-command is mind-blowing:)", "referred-topics": {{ "sprint", "voice-command" }}, "send-time": datetime("2011-12-26T10:10:00.000Z"), "sender-location": point("39.28,70.48"), "tweetid": "4", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 10, "fb-message": " can't stand t-mobile its voicemail-service is OMG:(" }
+, { "message-text": " love verizon its voicemail-service is awesome", "referred-topics": {{ "verizon", "voicemail-service" }}, "send-time": datetime("2012-07-21T10:10:00.000Z"), "sender-location": point("36.86,74.62"), "tweetid": "9", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 1, "fb-message": " can't stand motorola the touch-screen is terrible" }
+, { "message-text": " love verizon its voicemail-service is awesome", "referred-topics": {{ "verizon", "voicemail-service" }}, "send-time": datetime("2012-07-21T10:10:00.000Z"), "sender-location": point("36.86,74.62"), "tweetid": "9", "user": { "screen-name": "NathanGiesen@211", "lang": "en", "friends_count": 39339, "statuses_count": 473, "name": "Nathan Giesen", "followers_count": 49416 }, "fb-user": 10, "fb-message": " can't stand t-mobile its voicemail-service is OMG:(" }
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/results/records/record-remove-fields/documentation-example/documentation-example.1.adm
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/results/records/record-remove-fields/documentation-example/documentation-example.1.adm b/asterix-app/src/test/resources/runtimets/results/records/record-remove-fields/documentation-example/documentation-example.1.adm
new file mode 100644
index 0000000..8dd39e5
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/results/records/record-remove-fields/documentation-example/documentation-example.1.adm
@@ -0,0 +1 @@
+{ "id": 1, "address": { "city": "Irvine", "state": "CA" }, "related": [ "Hivestrix", "Preglix", "Apache VXQuery" ] }

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/results/records/record-remove-fields/documentation-example/documentation-example.2.adm
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/results/records/record-remove-fields/documentation-example/documentation-example.2.adm b/asterix-app/src/test/resources/runtimets/results/records/record-remove-fields/documentation-example/documentation-example.2.adm
new file mode 100644
index 0000000..3654f8c
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/results/records/record-remove-fields/documentation-example/documentation-example.2.adm
@@ -0,0 +1 @@
+{ "id": 1, "project": "AsterixDB", "address": { "state": "CA" }, "related": [ "Hivestrix", "Preglix", "Apache VXQuery" ] }
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/results/records/record-remove-fields/documentation-example/documentation-example.3.adm
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/results/records/record-remove-fields/documentation-example/documentation-example.3.adm b/asterix-app/src/test/resources/runtimets/results/records/record-remove-fields/documentation-example/documentation-example.3.adm
new file mode 100644
index 0000000..d177cad
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/results/records/record-remove-fields/documentation-example/documentation-example.3.adm
@@ -0,0 +1 @@
+{ "id": 1, "project": "AsterixDB", "related": [ "Hivestrix", "Preglix", "Apache VXQuery" ], "address": {  } }
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/4053f390/asterix-app/src/test/resources/runtimets/results/records/record-remove-fields/highly-nested-open/highly-nested-open.3.adm
----------------------------------------------------------------------
diff --git a/asterix-app/src/test/resources/runtimets/results/records/record-remove-fields/highly-nested-open/highly-nested-open.3.adm b/asterix-app/src/test/resources/runtimets/results/records/record-remove-fields/highly-nested-open/highly-nested-open.3.adm
new file mode 100644
index 0000000..78194ce
--- /dev/null
+++ b/asterix-app/src/test/resources/runtimets/results/records/record-remove-fields/highly-nested-open/highly-nested-open.3.adm
@@ -0,0 +1,4 @@
+{ "id": 1, "class": { "id": 1 } }
+{ "id": 2, "class": { "id": 2 } }
+{ "id": 3, "class": { "id": 3 } }
+{ "id": 4, "class": { "id": 4 } }
\ No newline at end of file