ASTERIXDB-1630: fix ATypeHierarchy to handle ANY.

Change-Id: Ic22421d12b1a6a17f15283e1e1403961e7fe17d0
Reviewed-on: https://asterix-gerrit.ics.uci.edu/1168
Sonar-Qube: Jenkins <jenkins@fulliautomatix.ics.uci.edu>
Tested-by: Jenkins <jenkins@fulliautomatix.ics.uci.edu>
Reviewed-by: Taewoo Kim <wangsaeu@yahoo.com>
Integration-Tests: Jenkins <jenkins@fulliautomatix.ics.uci.edu>
diff --git a/asterixdb/asterix-om/src/main/java/org/apache/asterix/om/typecomputer/base/TypeCastUtils.java b/asterixdb/asterix-om/src/main/java/org/apache/asterix/om/typecomputer/base/TypeCastUtils.java
index 4bdcbba..91990f2 100644
--- a/asterixdb/asterix-om/src/main/java/org/apache/asterix/om/typecomputer/base/TypeCastUtils.java
+++ b/asterixdb/asterix-om/src/main/java/org/apache/asterix/om/typecomputer/base/TypeCastUtils.java
@@ -39,9 +39,7 @@
             opaqueParameters = new Object[2];
             opaqueParameters[0] = requiredType;
             opaqueParameters[1] = inputType;
-            if (TypeComputeUtils.getActualType(inputType).getTypeTag() != ATypeTag.ANY
-                    && TypeComputeUtils.getActualType(requiredType).getTypeTag() != ATypeTag.ANY
-                    && !ATypeHierarchy.isCompatible(requiredType.getTypeTag(),
+            if (!ATypeHierarchy.isCompatible(requiredType.getTypeTag(),
                             TypeComputeUtils.getActualType(inputType).getTypeTag())) {
                 throw new AlgebricksException(inputType + " can't be casted to " + requiredType);
             }
diff --git a/asterixdb/asterix-om/src/main/java/org/apache/asterix/om/types/hierachy/ATypeHierarchy.java b/asterixdb/asterix-om/src/main/java/org/apache/asterix/om/types/hierachy/ATypeHierarchy.java
index f85aa50..af4d2a2 100644
--- a/asterixdb/asterix-om/src/main/java/org/apache/asterix/om/types/hierachy/ATypeHierarchy.java
+++ b/asterixdb/asterix-om/src/main/java/org/apache/asterix/om/types/hierachy/ATypeHierarchy.java
@@ -169,11 +169,11 @@
     }
 
     public static boolean isCompatible(ATypeTag type1, ATypeTag type2) {
-        return canPromote(type1, type2) | canPromote(type2, type1);
-    }
-
-    public static boolean isDemoteCompatible(ATypeTag type1, ATypeTag type2) {
-        return canDemote(type1, type2) | canDemote(type2, type1);
+        // The type tag ANY is only used at compile time to represent all possibilities.
+        // There is no runtime data model instance that has a type tag ANY.
+        // If we encounter type tag ANY, we should let it pass at compile time and defer erring to the runtime.
+        // Therefore, "type1 == ATypeTag.ANY || type2 == ATypeTag.ANY" works for both compiler and runtime.
+        return type1 == ATypeTag.ANY || type2 == ATypeTag.ANY || canPromote(type1, type2) || canPromote(type2, type1);
     }
 
     // Get an AsterixConstantValue from a source Object