From notifications-return-147891-archive-asf-public=cust-asf.ponee.io@asterixdb.apache.org Mon May 13 12:10:04 2019 Return-Path: X-Original-To: archive-asf-public@cust-asf.ponee.io Delivered-To: archive-asf-public@cust-asf.ponee.io Received: from mail.apache.org (hermes.apache.org [207.244.88.153]) by mx-eu-01.ponee.io (Postfix) with SMTP id 07CC3180671 for ; Mon, 13 May 2019 14:10:03 +0200 (CEST) Received: (qmail 88183 invoked by uid 500); 13 May 2019 12:10:03 -0000 Mailing-List: contact notifications-help@asterixdb.apache.org; run by ezmlm Precedence: bulk List-Help: List-Unsubscribe: List-Post: List-Id: Reply-To: dev@asterixdb.apache.org Delivered-To: mailing list notifications@asterixdb.apache.org Received: (qmail 88174 invoked by uid 99); 13 May 2019 12:10:03 -0000 Received: from pnap-us-west-generic-nat.apache.org (HELO spamd1-us-west.apache.org) (209.188.14.142) by apache.org (qpsmtpd/0.29) with ESMTP; Mon, 13 May 2019 12:10:03 +0000 Received: from localhost (localhost [127.0.0.1]) by spamd1-us-west.apache.org (ASF Mail Server at spamd1-us-west.apache.org) with ESMTP id B3391C020C for ; Mon, 13 May 2019 12:10:02 +0000 (UTC) X-Virus-Scanned: Debian amavisd-new at spamd1-us-west.apache.org X-Spam-Flag: NO X-Spam-Score: 4.127 X-Spam-Level: **** X-Spam-Status: No, score=4.127 tagged_above=-999 required=6.31 tests=[HTML_MESSAGE=2, MISSING_HEADERS=1.207, SPF_FAIL=0.919, URIBL_BLOCKED=0.001] autolearn=disabled Received: from mx1-lw-eu.apache.org ([10.40.0.8]) by localhost (spamd1-us-west.apache.org [10.40.0.7]) (amavisd-new, port 10024) with ESMTP id L0_gncY158FG for ; Mon, 13 May 2019 12:09:58 +0000 (UTC) Received: from adrian-monk-v3.ics.uci.edu (adrian-monk-v3.ics.uci.edu [128.195.1.133]) by mx1-lw-eu.apache.org (ASF Mail Server at mx1-lw-eu.apache.org) with ESMTPS id 750155F4EB for ; Mon, 13 May 2019 12:09:57 +0000 (UTC) Received: from 5bb8be5df840 (vitalstatistix.ics.uci.edu [128.195.52.38]) by adrian-monk-v3.ics.uci.edu (8.14.7/8.14.7) with ESMTP id x4DC8F40017605; Mon, 13 May 2019 05:08:15 -0700 X-Gerrit-PatchSet: 1 Date: Mon, 13 May 2019 12:08:14 +0000 From: "Hussain Towaileb (Code Review)" CC: Hussain Towaileb Message-ID: X-Gerrit-MessageType: newchange Subject: Change in asterixdb[master]: [NO ISSUE][TEST] Convert type computer tests to parameterized X-Gerrit-Change-Id: I4426efcc9e825ebb00e04e3783d18bb1cbb63a90 X-Gerrit-Change-Number: 3393 X-Gerrit-ChangeURL: X-Gerrit-Commit: f5c84cfe78933c762c476dfd21ec8f920a6ca857 Reply-To: hussainht@gmail.com, HussainHT@Gmail.com, notifications@asterixdb.incubator.apache.org, lwhaywhu@gmail.com MIME-Version: 1.0 Content-Transfer-Encoding: 8bit Content-Disposition: inline User-Agent: Gerrit/2.14.19 Content-Type: multipart/alternative; boundary="v1R3RmNVOJw="; charset=UTF-8 X-ICS-MailScanner-Information: Please send mail to helpdesk@ics.uci.edu or more information X-ICS-MailScanner-ID: x4DC8F40017605 X-ICS-MailScanner: Found to be clean X-ICS-MailScanner-SpamCheck: not spam, SpamAssassin (not cached, score=-1.877, required 5, ALL_TRUSTED -1.00, BAYES_00 -1.90, FSL_HELO_NON_FQDN_1 0.00, HTML_MESSAGE 0.00, MISSING_HEADERS 1.02) X-ICS-MailScanner-From: dev@asterixdb.apache.org --v1R3RmNVOJw= Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: quoted-printable Hussain Towaileb has uploaded this change for review=2E ( https://asterix-g= errit=2Eics=2Euci=2Eedu/3393 Change subject: [NO ISSUE][TEST] Convert typ= e computer tests to parameterized =2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E= =2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E= =2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E=2E= =2E=2E=2E=2E=2E=2E=2E [NO ISSUE][TEST] Convert type computer tests to para= meterized Change-Id: I4426efcc9e825ebb00e04e3783d18bb1cbb63a90 --- D aster= ixdb/asterix-om/src/test/java/org/apache/asterix/om/typecomputer/TypeComput= erTest=2Ejava R asterixdb/asterix-om/src/test/java/org/apache/asterix/test/= om/typecomputer/ExceptionTest=2Ejava A asterixdb/asterix-om/src/test/java/o= rg/apache/asterix/test/om/typecomputer/TypeComputerTest=2Ejava R asterixdb/= asterix-om/src/test/java/org/apache/asterix/test/om/util/JSONDeserializerFo= rTypesTest=2Ejava 4 files changed, 293 insertions(+), 168 deletions(-) = git pull ssh://asterix-gerrit=2Eics=2Euci=2Eedu:29418/asterixdb refs/chang= es/93/3393/1 diff --git a/asterixdb/asterix-om/src/test/java/org/apache/as= terix/om/typecomputer/TypeComputerTest=2Ejava b/asterixdb/asterix-om/src/te= st/java/org/apache/asterix/om/typecomputer/TypeComputerTest=2Ejava deleted = file mode 100644 index bd77580=2E=2E0000000 --- a/asterixdb/asterix-om/src/= test/java/org/apache/asterix/om/typecomputer/TypeComputerTest=2Ejava +++ /d= ev/null @@ -1,166 +0,0 @@ -/* - * Licensed to the Apache Software Foundatio= n (ASF) under one - * or more contributor license agreements=2E See the NO= TICE file - * distributed with this work for additional information - * reg= arding copyright ownership=2E The ASF licenses this file - * to you under = the Apache License, Version 2=2E0 (the - * "License"); you may not use this= file except in compliance - * with the License=2E You may obtain a copy o= f the License at - * - * http://www=2Eapache=2Eorg/licenses/LICENSE-2=2E0= - * - * Unless required by applicable law or agreed to in writing, - * sof= tware distributed under the License is distributed on an - * "AS IS" BASIS,= WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implie= d=2E See the License for the - * specific language governing permissions a= nd limitations - * under the License=2E - */ - -package org=2Eapache=2Easte= rix=2Eom=2Etypecomputer; - -import static org=2Emockito=2EMockito=2Emock; -= import static org=2Emockito=2EMockito=2Ewhen; - -import java=2Elang=2Erefle= ct=2EField; -import java=2Elang=2Ereflect=2EModifier; -import java=2Eutil= =2EArrayList; -import java=2Eutil=2EHashMap; -import java=2Eutil=2EHashSet;= -import java=2Eutil=2EList; -import java=2Eutil=2ESet; - -import org=2Eapa= che=2Easterix=2Eom=2Etypecomputer=2Ebase=2EIResultTypeComputer; -import org= =2Eapache=2Easterix=2Eom=2Etypes=2EATypeTag; -import org=2Eapache=2Easterix= =2Eom=2Etypes=2EAUnionType; -import org=2Eapache=2Easterix=2Eom=2Etypes=2EB= uiltinType; -import org=2Eapache=2Easterix=2Eom=2Etypes=2EIAType; -import o= rg=2Eapache=2Ecommons=2Elang3=2Emutable=2EMutable; -import org=2Eapache=2Ec= ommons=2Elang3=2Emutable=2EMutableObject; -import org=2Eapache=2Ehyracks=2E= algebricks=2Ecore=2Ealgebra=2Ebase=2EILogicalExpression; -import org=2Eapac= he=2Ehyracks=2Ealgebricks=2Ecore=2Ealgebra=2Eexpressions=2EAbstractFunction= CallExpression; -import org=2Eapache=2Ehyracks=2Ealgebricks=2Ecore=2Ealgebr= a=2Eexpressions=2EIVariableTypeEnvironment; -import org=2Eapache=2Ehyracks= =2Ealgebricks=2Ecore=2Ealgebra=2Efunctions=2EFunctionIdentifier; -import or= g=2Eapache=2Ehyracks=2Ealgebricks=2Ecore=2Ealgebra=2Emetadata=2EIMetadataPr= ovider; -import org=2Ejunit=2EAssert; -import org=2Ejunit=2ETest; -import o= rg=2Ereflections=2EReflections; -import org=2Ereflections=2Escanners=2ESubT= ypesScanner; - -// Tests if all type computers can handle input type ANY pr= operly=2E -// TODO: this test should be fixed/updated/modified/enhanced -pu= blic class TypeComputerTest { - - @Test - public void test() throws E= xception { - // Mocks the type environment=2E - IVariableType= Environment mockTypeEnv =3D mock(IVariableTypeEnvironment=2Eclass); - - = // Mocks the metadata provider=2E - IMetadataProvider mock= MetadataProvider =3D mock(IMetadataProvider=2Eclass); - - // Mocks f= unction expression=2E - AbstractFunctionCallExpression mockExpr =3D = mock(AbstractFunctionCallExpression=2Eclass); - FunctionIdentifier f= id =3D mock(FunctionIdentifier=2Eclass); - when(mockExpr=2EgetFuncti= onIdentifier())=2EthenReturn(fid); - when(fid=2EgetName())=2EthenRet= urn("testFunction"); - - // A function at most has six argument=2E -= List> sixArgs =3D createArgs(6, mockTyp= eEnv); - - // Sets up arguments for the mocked expression=2E - = when(mockExpr=2EgetArguments())=2EthenReturn(sixArgs); - - // Sets= up required/actual types of the mocked expression=2E - Object[] opa= queParameters =3D new Object[2]; - opaqueParameters[0] =3D BuiltinTy= pe=2EANY; - opaqueParameters[1] =3D BuiltinType=2EANY; - when= (mockExpr=2EgetOpaqueParameters())=2EthenReturn(opaqueParameters); - - = // functions that check the number of args inside the type computer - = List> replaceArgs =3D createArgs(4, mockTy= peEnv); - List> sliceArgs =3D createArgs= (3, mockTypeEnv); - List> rangeArgs =3D = createArgs(3, mockTypeEnv); - HashMap>> map =3D new HashMap<>(); - map=2Eput("INSTANCE_REPLACE"= , replaceArgs); - map=2Eput("INSTANCE_SLICE", sliceArgs); - m= ap=2Eput("ArrayRangeTypeComputer", rangeArgs); - - // Several except= ional type computers=2E - Set exceptionalTypeComputers =3D n= ew HashSet<>(); - exceptionalTypeComputers=2Eadd("InjectFailureTypeC= omputer"); - exceptionalTypeComputers=2Eadd("RecordAddFieldsTypeComp= uter"); - exceptionalTypeComputers=2Eadd("OpenRecordConstructorResul= tType"); - exceptionalTypeComputers=2Eadd("RecordRemoveFieldsTypeCom= puter"); - exceptionalTypeComputers=2Eadd("ClosedRecordConstructorRe= sultType"); - exceptionalTypeComputers=2Eadd("LocalAvgTypeComputer")= ; - exceptionalTypeComputers=2Eadd("BooleanOnlyTypeComputer"); - = exceptionalTypeComputers=2Eadd("AMissingTypeComputer"); - except= ionalTypeComputers=2Eadd("NullableDoubleTypeComputer"); - exceptiona= lTypeComputers=2Eadd("RecordMergeTypeComputer"); - exceptionalTypeCo= mputers=2Eadd("BooleanOrMissingTypeComputer"); - exceptionalTypeComp= uters=2Eadd("LocalSingleVarStatisticsTypeComputer"); - - // Tests al= l usual type computers=2E - Reflections reflections =3D new Reflecti= ons("org=2Eapache=2Easterix=2Eom=2Etypecomputer", new SubTypesScanner(false= )); - Set> classes =3D reflecti= ons=2EgetSubTypesOf(IResultTypeComputer=2Eclass); - for (Class c : classes) { - if (exceptionalTypeCo= mputers=2Econtains(c=2EgetSimpleName()) || Modifier=2EisAbstract(c=2EgetMod= ifiers())) { - continue; - } - System= =2Eout=2Eprintln("Test type computer: " + c=2EgetName()); - Asse= rt=2EassertTrue(testTypeComputer(c, mockTypeEnv, mockMetadataProvider, mock= Expr, map, sixArgs)); - } - } - - private boolean testTypeComp= uter(Class c, IVariableTypeEnvironment mockT= ypeEnv, - IMetadataProvider mockMetadataProvider, Abstract= FunctionCallExpression mockExpr, - HashMap>> map, List> sixArgs) - = throws Exception { - // Tests the return type=2E It should b= e either ANY or NULLABLE/MISSABLE=2E - IResultTypeComputer instance;= - IAType resultType; - Field[] fields =3D c=2EgetFields(); -= List> args; - for (Field field := fields) { - if (field=2EgetName()=2EstartsWith("INSTANCE")) { -= System=2Eout=2Eprintln("Test type computer INSTANCE: " + fi= eld=2EgetName()); - args =3D getArgs(field=2EgetName(), c, m= ap); - if (args !=3D null) { - when(mockE= xpr=2EgetArguments())=2EthenReturn(args); - } else { - = when(mockExpr=2EgetArguments())=2EthenReturn(sixArgs); - = } - instance =3D (IResultTypeComputer) field=2Ege= t(null); - resultType =3D instance=2EcomputeType(mockExpr, m= ockTypeEnv, mockMetadataProvider); - ATypeTag typeTag =3D re= sultType=2EgetTypeTag(); - if (typeTag !=3D ATypeTag=2EANY &= & !(typeTag =3D=3D ATypeTag=2EUNION && ((AUnionType) resultType)=2EisNullab= leType() - && ((AUnionType) resultType)=2EisMissable= Type())) { - return false; - } - = } - } - return true; - } - - private List> createArgs(int numArgs, IVariableTypeEnvironment mockTyp= eEnv) - throws Exception { - List> argRefs =3D new ArrayList<>(); - for (int argIndex =3D 0; argI= ndex < numArgs; ++argIndex) { - ILogicalExpression mockArg =3D m= ock(ILogicalExpression=2Eclass); - argRefs=2Eadd(new MutableObje= ct<>(mockArg)); - when(mockTypeEnv=2EgetType(mockArg))=2EthenRet= urn(BuiltinType=2EANY); - } - - return argRefs; - } - - = private List> getArgs(String instanceName, Cla= ss c, - HashMap>> map) { - if (instanceName=2Eequals("INSTAN= CE")) { - return map=2Eget(c=2EgetSimpleName()); - } else= { - return map=2Eget(instanceName); - } - } -} diff -= -git a/asterixdb/asterix-om/src/test/java/org/apache/asterix/om/typecompute= r/ExceptionTest=2Ejava b/asterixdb/asterix-om/src/test/java/org/apache/aste= rix/test/om/typecomputer/ExceptionTest=2Ejava similarity index 98% rename f= rom asterixdb/asterix-om/src/test/java/org/apache/asterix/om/typecomputer/E= xceptionTest=2Ejava rename to asterixdb/asterix-om/src/test/java/org/apache= /asterix/test/om/typecomputer/ExceptionTest=2Ejava index 29cb9a7=2E=2E3d8c6= 90 100644 --- a/asterixdb/asterix-om/src/test/java/org/apache/asterix/om/ty= pecomputer/ExceptionTest=2Ejava +++ b/asterixdb/asterix-om/src/test/java/or= g/apache/asterix/test/om/typecomputer/ExceptionTest=2Ejava @@ -17,7 +17,7 @= @ * under the License=2E */ -package org=2Eapache=2Easterix=2Eom=2Et= ypecomputer; +package org=2Eapache=2Easterix=2Etest=2Eom=2Etypecomputer; = import static org=2Emockito=2EMockito=2Emock; import static org=2Emockito= =2EMockito=2Ewhen; diff --git a/asterixdb/asterix-om/src/test/java/org/apac= he/asterix/test/om/typecomputer/TypeComputerTest=2Ejava b/asterixdb/asterix= -om/src/test/java/org/apache/asterix/test/om/typecomputer/TypeComputerTest= =2Ejava new file mode 100644 index 0000000=2E=2Eb65c15e --- /dev/null +++ b= /asterixdb/asterix-om/src/test/java/org/apache/asterix/test/om/typecomputer= /TypeComputerTest=2Ejava @@ -0,0 +1,291 @@ +/* + * Licensed to the Apache S= oftware Foundation (ASF) under one + * or more contributor license agreemen= ts=2E See the NOTICE file + * distributed with this work for additional in= formation + * regarding copyright ownership=2E The ASF licenses this file = + * to you under the Apache License, Version 2=2E0 (the + * "License"); you= may not use this file except in compliance + * with the License=2E You ma= y obtain a copy of the License at + * + * http://www=2Eapache=2Eorg/licen= ses/LICENSE-2=2E0 + * + * 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=2E See the License for the + * specific language govern= ing permissions and limitations + * under the License=2E + */ + +package or= g=2Eapache=2Easterix=2Etest=2Eom=2Etypecomputer; + +import static org=2Emoc= kito=2EMockito=2Emock; +import static org=2Emockito=2EMockito=2Ewhen; + +im= port java=2Elang=2Ereflect=2EField; +import java=2Elang=2Ereflect=2EModifie= r; +import java=2Eutil=2EArrayList; +import java=2Eutil=2ECollection; +impo= rt java=2Eutil=2EHashMap; +import java=2Eutil=2EHashSet; +import java=2Euti= l=2EList; +import java=2Eutil=2ESet; + +import org=2Eapache=2Easterix=2Eom= =2Etypecomputer=2Ebase=2EIResultTypeComputer; +import org=2Eapache=2Easteri= x=2Eom=2Etypes=2EATypeTag; +import org=2Eapache=2Easterix=2Eom=2Etypes=2EAU= nionType; +import org=2Eapache=2Easterix=2Eom=2Etypes=2EBuiltinType; +impor= t org=2Eapache=2Easterix=2Eom=2Etypes=2EIAType; +import org=2Eapache=2Ecomm= ons=2Elang3=2Emutable=2EMutable; +import org=2Eapache=2Ecommons=2Elang3=2Em= utable=2EMutableObject; +import org=2Eapache=2Ehyracks=2Ealgebricks=2Ecore= =2Ealgebra=2Ebase=2EILogicalExpression; +import org=2Eapache=2Ehyracks=2Eal= gebricks=2Ecore=2Ealgebra=2Eexpressions=2EAbstractFunctionCallExpression; += import org=2Eapache=2Ehyracks=2Ealgebricks=2Ecore=2Ealgebra=2Eexpressions= =2EIVariableTypeEnvironment; +import org=2Eapache=2Ehyracks=2Ealgebricks=2E= core=2Ealgebra=2Efunctions=2EFunctionIdentifier; +import org=2Eapache=2Ehyr= acks=2Ealgebricks=2Ecore=2Ealgebra=2Emetadata=2EIMetadataProvider; +import = org=2Eapache=2Elogging=2Elog4j=2ELevel; +import org=2Eapache=2Elogging=2Elo= g4j=2ELogManager; +import org=2Eapache=2Elogging=2Elog4j=2ELogger; +import = org=2Ejunit=2EAssert; +import org=2Ejunit=2ETest; +import org=2Ejunit=2Erun= ner=2ERunWith; +import org=2Ejunit=2Erunners=2EParameterized; +import org= =2Ejunit=2Erunners=2EParameterized=2EParameter; +import org=2Ejunit=2Erunne= rs=2EParameterized=2EParameters; +import org=2Ereflections=2EReflections; += import org=2Ereflections=2Escanners=2ESubTypesScanner; + +/** + * This test= passes a number of arguments to the type computers, all arguments of type = "any", and ensures that + * each computer handles the "any" type properly= =2E The expected behavior for each type computer is to return "any", + * "n= ullable" or "missable" type result=2E + * + * Things to note: + * - The fun= ction passes 6 "any" arguments because, as of now, no function that we have= has more than 6 arguments=2E + * two other lists are made (3 args and 4 ar= gs), those are needed by specific type computers for now, those should be += * changed and then the lists can be removed from the test=2E + * - Some fu= nctions have a different behavior with "any" value, those will be added to = an exception list=2E + * - Some functions check their arguments count, this= will make passing 6 arguments fail, + * those are added to exception list= =2E + */ + +@RunWith(Parameterized=2Eclass) +public class TypeComputerTest = { + + private static final Logger LOGGER =3D LogManager=2EgetLogger(); += + // type computers that have a different behavior when handling "any" = type + private static Set differentBehaviorFunctions =3D new Has= hSet<>(); + + // type computers that check the number of arguments + = private static HashMap>> checkArgsC= ountFunctions =3D new HashMap<>(); + + // Members + private static IV= ariableTypeEnvironment env; + private static IMetadataProvider metadataP= rovider; + private static AbstractFunctionCallExpression functionCallExp= ression; + + // Arguments all of type "any", different combination is pr= ovided because it's needed by other functions (for now) + private static= List> threeArgs; + private static List> fourArgs; + private static List> sixArgs; + + @Parameter + public String testName; + + = @Parameter(1) + public Class clazz; + += @Parameters(name =3D "TypeComputerTest {index}: {0}") + public stati= c Collection tests() throws Exception { + + System=2Eout= =2Eprintln("\n-------------------------------------------------------------= -------------------------"); + + // Prepare the test environment fir= st + setup(); + + // Prepare tests + List te= sts =3D new ArrayList<>(); + + // Tests all usual type computers=2E = + Reflections reflections =3D new Reflections("org=2Eapache=2Easteri= x=2Eom=2Etypecomputer", new SubTypesScanner(false)); + Set> classes =3D reflections=2EgetSubTypesOf(IResul= tTypeComputer=2Eclass); + + for (Class clazz : classes) { + if (Modifier=2EisAbstract(clazz=2EgetModi= fiers())) { + LOGGER=2Elog(Level=2EINFO, "Excluding " + claz= z=2EgetSimpleName() + " (Abstract class)"); + continue; + = } + + if (differentBehaviorFunctions=2Econtains(clazz= =2EgetSimpleName())) { + LOGGER=2Elog(Level=2EINFO, "Excludi= ng " + clazz=2EgetSimpleName() + " (Special behavior)"); + c= ontinue; + } + + tests=2Eadd(new Object[] { clazz=2Eg= etSimpleName(), clazz }); + } + + System=2Eout=2Eprintln("---= ---------------------------------------------------------------------------= --------\n"); + + return tests; + } + + /** + * Test retur= n types should be either "any", "missable" or "nullable" + * + * @t= hrows Exception Exception + */ + @Test + public void test() throw= s Exception { + + // Tests the return type=2E It should be either AN= Y or NULLABLE/MISSABLE=2E + IResultTypeComputer instance; + I= AType resultType; + List> args; + = Field[] fields =3D clazz=2EgetFields(); + + // The type computer fi= elds are only the ones that start with "INSTANCE" + for (Field field= : fields) { + + if (field=2EgetName()=2EstartsWith("INSTANCE"))= { + LOGGER=2Elog(Level=2EINFO, "Testing " + clazz=2EgetSimp= leName() + ": " + field=2EgetName()); + + // Need to check i= f this is a special type computer that counts number of arguments + = args =3D checkArgsCountFunctions=2Eget(field); + + /= / Yes, pass its specified arguments in the map + if (args != =3D null) { + when(functionCallExpression=2EgetArguments= ())=2EthenReturn(args); + } + // No, pass six= arguments + else { + when(functionCallEx= pression=2EgetArguments())=2EthenReturn(sixArgs); + } + + = instance =3D (IResultTypeComputer) field=2Eget(null); + = resultType =3D instance=2EcomputeType(functionCallExpression, env,= metadataProvider); + ATypeTag typeTag =3D resultType=2EgetT= ypeTag(); + + // Result should be ANY, Missable or Nullable = + Assert=2EassertTrue(typeTag =3D=3D ATypeTag=2EANY + = || (typeTag =3D=3D ATypeTag=2EUNION && ((AUnionType) resul= tType)=2EisNullableType() + || ((AUnionType)= resultType)=2EisMissableType())); + } + } + } + + = public static void setup() throws Exception { + + // Mocks the type = environment=2E + env =3D mock(IVariableTypeEnvironment=2Eclass); + += // Mocks the metadata provider=2E + metadataProvider =3D moc= k(IMetadataProvider=2Eclass); + + // Prepare the function arguments = + threeArgs =3D createArgs(3); + fourArgs =3D createArgs(4); = + sixArgs =3D createArgs(6); + + // Mocks function identifier= + FunctionIdentifier functionIdentifier =3D mock(FunctionIdentifier= =2Eclass); + when(functionIdentifier=2EgetName())=2EthenReturn("test= Function"); + + // Mocks function expression=2E + functionCal= lExpression =3D mock(AbstractFunctionCallExpression=2Eclass); + when= (functionCallExpression=2EgetFunctionIdentifier())=2EthenReturn(functionIde= ntifier); + when(functionCallExpression=2EgetArguments())=2EthenRetu= rn(sixArgs); + + // Sets up required/actual types of the mocked expr= ession=2E + Object[] opaqueParameters =3D new Object[2]; + op= aqueParameters[0] =3D BuiltinType=2EANY; + opaqueParameters[1] =3D B= uiltinType=2EANY; + when(functionCallExpression=2EgetOpaqueParameter= s())=2EthenReturn(opaqueParameters); + + // Add to exception list fo= r computers checking their arguments count + addComputersCheckingArg= sCount(); + + // Add to exception list for computers having a differ= ent behavior for "any" type + addComputersBehavingDifferently(); + = } + + // TODO This is not a good practice, if the class name is change= d, the test will fail and this needs to be updated + // Consider using a= nnotation to avoid modifying the test and have a generic behavior + /** = + * Adds the type computers that have a different behavior for "any" ty= pe=2E + */ + private static void addComputersBehavingDifferently() {= + differentBehaviorFunctions=2Eadd("InjectFailureTypeComputer"); + = differentBehaviorFunctions=2Eadd("RecordAddFieldsTypeComputer"); + = differentBehaviorFunctions=2Eadd("OpenRecordConstructorResultType"); = + differentBehaviorFunctions=2Eadd("RecordRemoveFieldsTypeComputer")= ; + differentBehaviorFunctions=2Eadd("ClosedRecordConstructorResultT= ype"); + differentBehaviorFunctions=2Eadd("LocalAvgTypeComputer"); += differentBehaviorFunctions=2Eadd("BooleanOnlyTypeComputer"); + = differentBehaviorFunctions=2Eadd("AMissingTypeComputer"); + diffe= rentBehaviorFunctions=2Eadd("NullableDoubleTypeComputer"); + differe= ntBehaviorFunctions=2Eadd("RecordMergeTypeComputer"); + differentBeh= aviorFunctions=2Eadd("BooleanOrMissingTypeComputer"); + differentBeh= aviorFunctions=2Eadd("LocalSingleVarStatisticsTypeComputer"); + } + + = // TODO Type computers should not be checking the arguments count, if the = argument count is variable but knowable, + // then multiple INSTANCES ne= ed to be created, each indicating the number of incoming arguments, and bas= ed on that + // applying the appropriate behavior in the compute method = body + /** + * Adds the type computers that check the args count in = their method body=2E If 6 arguments are passed to those + * computers, = they're gonna throw an exception, so we manually specify how many arguments= they should get=2E + * + * @throws Exception Exception + */ + = private static void addComputersCheckingArgsCount() throws Exception { += + // AListTypeComputer + Class clazz =3D Class=2EforName(= "org=2Eapache=2Easterix=2Eom=2Etypecomputer=2Eimpl=2EAListTypeComputer"); += Field[] fields =3D clazz=2EgetFields(); + + for (Field field= : fields) { + if (field=2EgetName()=2EequalsIgnoreCase("INSTANC= E_SLICE")) { + LOGGER=2Elog(Level=2EINFO, field=2EgetName() = + " will use only 3 arguments"); + checkArgsCountFunctions= =2Eput(field, threeArgs); + } + + if (field=2EgetName= ()=2EequalsIgnoreCase("INSTANCE_REPLACE")) { + LOGGER=2Elog(= Level=2EINFO, field=2EgetName() + " will use only 4 arguments"); + = checkArgsCountFunctions=2Eput(field, fourArgs); + } + = } + + // ArrayRangeTypeComputer + clazz =3D Class=2EforNa= me("org=2Eapache=2Easterix=2Eom=2Etypecomputer=2Eimpl=2EArrayRangeTypeCompu= ter"); + fields =3D clazz=2EgetFields(); + + for (Field field= : fields) { + if (field=2EgetName()=2EequalsIgnoreCase("INSTANC= E")) { + LOGGER=2Elog(Level=2EINFO, field=2EgetName() + " wi= ll use only 3 arguments"); + checkArgsCountFunctions=2Eput(f= ield, threeArgs); + } + } + } + + /** + * Creat= es expressions matching the number passed as an argument=2E Variable type e= nvironment is set for all those + * expressions to be of type "any"=2E = + * + * @param numArgs number of arguments to create + * @retur= n a list holding the created expressions + * @throws Exception Exceptio= n + */ + private static List> createArgs= (int numArgs) throws Exception { + + List> arguments =3D new ArrayList<>(); + + for (int i =3D 0; i < numArg= s; ++i) { + ILogicalExpression argument =3D mock(ILogicalExpress= ion=2Eclass); + arguments=2Eadd(new MutableObject<>(argument)); = + when(env=2EgetType(argument))=2EthenReturn(BuiltinType=2EANY);= + } + + return arguments; + } +} diff --git a/asterixdb/a= sterix-om/src/test/java/org/apache/asterix/om/util/JSONDeserializerForTypes= Test=2Ejava b/asterixdb/asterix-om/src/test/java/org/apache/asterix/test/om= /util/JSONDeserializerForTypesTest=2Ejava similarity index 98% rename from = asterixdb/asterix-om/src/test/java/org/apache/asterix/om/util/JSONDeseriali= zerForTypesTest=2Ejava rename to asterixdb/asterix-om/src/test/java/org/apa= che/asterix/test/om/util/JSONDeserializerForTypesTest=2Ejava index 32ec75a= =2E=2E35e4d35 100644 --- a/asterixdb/asterix-om/src/test/java/org/apache/as= terix/om/util/JSONDeserializerForTypesTest=2Ejava +++ b/asterixdb/asterix-o= m/src/test/java/org/apache/asterix/test/om/util/JSONDeserializerForTypesTes= t=2Ejava @@ -17,7 +17,7 @@ * under the License=2E */ -package org=2Ea= pache=2Easterix=2Eom=2Eutil; +package org=2Eapache=2Easterix=2Etest=2Eom=2E= util; import java=2Eutil=2EArrayList; import java=2Eutil=2EList; -- T= o view, visit https://asterix-gerrit=2Eics=2Euci=2Eedu/3393 To unsubscribe,= visit https://asterix-gerrit=2Eics=2Euci=2Eedu/settings Gerrit-Project: a= sterixdb Gerrit-Branch: master Gerrit-MessageType: newchange Gerrit-Change-= Id: I4426efcc9e825ebb00e04e3783d18bb1cbb63a90 Gerrit-Change-Number: 3393 Ge= rrit-PatchSet: 1 Gerrit-Owner: Hussain Towaileb Ger= rit-Reviewer: Hussain Towaileb --v1R3RmNVOJw= Content-Type: text/html; charset=UTF-8 Content-Transfer-Encoding: quoted-printable

Hussain Towaileb has uploaded this change for review=2E=

View Chang= e

[NO ISSUE][TEST] Convert type computer tests to parameterized

= Change-Id: I4426efcc9e825ebb00e04e3783d18bb1cbb63a90
---
D asterixdb/= asterix-om/src/test/java/org/apache/asterix/om/typecomputer/TypeComputerTes= t=2Ejava
R asterixdb/asterix-om/src/test/java/org/apache/asterix/test/om= /typecomputer/ExceptionTest=2Ejava
A asterixdb/asterix-om/src/test/java/= org/apache/asterix/test/om/typecomputer/TypeComputerTest=2Ejava
R asteri= xdb/asterix-om/src/test/java/org/apache/asterix/test/om/util/JSONDeserializ= erForTypesTest=2Ejava
4 files changed, 293 insertions(+), 168 deletions(= -)

git pull ssh://asterix-gerrit=2Eics=2Euci=2Eedu:29418/asterixd=
b refs/changes/93/3393/1
diff --git a/asterixdb/asterix-om/src/test/java/=
org/apache/asterix/om/typecomputer/TypeComputerTest=2Ejava b/asterixdb/aste=
rix-om/src/test/java/org/apache/asterix/om/typecomputer/TypeComputerTest=2E=
java
deleted file mode 100644
index bd77580=2E=2E0000000
--- a/ast= erixdb/asterix-om/src/test/java/org/apache/asterix/om/typecomputer/TypeComp= uterTest=2Ejava
+++ /dev/null
@@ -1,166 +0,0 @@
-/*
- * License= d to the Apache Software Foundation (ASF) under one
- * or more contribu= tor license agreements=2E See the NOTICE file
- * distributed with this= work for additional information
- * regarding copyright ownership=2E T= he ASF licenses this file
- * to you under the Apache License, Version 2= =2E0 (the
- * "License"); you may not use this file except in = compliance
- * with the License=2E You may obtain a copy of the License= at
- *
- * http://www=2Eapache=2Eorg/licenses/LICENSE-2=2E0
- *=
- * Unless required by applicable law or agreed to in writing,
- * s= oftware distributed under the License is distributed on an
- * "AS = IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- * KIND, either= express or implied=2E See the License for the
- * specific language go= verning permissions and limitations
- * under the License=2E
- */
= -
-package org=2Eapache=2Easterix=2Eom=2Etypecomputer;
-
-import s= tatic org=2Emockito=2EMockito=2Emock;
-import static org=2Emockito=2EMoc= kito=2Ewhen;
-
-import java=2Elang=2Ereflect=2EField;
-import java= =2Elang=2Ereflect=2EModifier;
-import java=2Eutil=2EArrayList;
-impor= t java=2Eutil=2EHashMap;
-import java=2Eutil=2EHashSet;
-import java= =2Eutil=2EList;
-import java=2Eutil=2ESet;
-
-import org=2Eapache= =2Easterix=2Eom=2Etypecomputer=2Ebase=2EIResultTypeComputer;
-import org= =2Eapache=2Easterix=2Eom=2Etypes=2EATypeTag;
-import org=2Eapache=2Easte= rix=2Eom=2Etypes=2EAUnionType;
-import org=2Eapache=2Easterix=2Eom=2Etyp= es=2EBuiltinType;
-import org=2Eapache=2Easterix=2Eom=2Etypes=2EIAType;<= br>-import org=2Eapache=2Ecommons=2Elang3=2Emutable=2EMutable;
-import o= rg=2Eapache=2Ecommons=2Elang3=2Emutable=2EMutableObject;
-import org=2Ea= pache=2Ehyracks=2Ealgebricks=2Ecore=2Ealgebra=2Ebase=2EILogicalExpression;<= br>-import org=2Eapache=2Ehyracks=2Ealgebricks=2Ecore=2Ealgebra=2Eexpressio= ns=2EAbstractFunctionCallExpression;
-import org=2Eapache=2Ehyracks=2Eal= gebricks=2Ecore=2Ealgebra=2Eexpressions=2EIVariableTypeEnvironment;
-imp= ort org=2Eapache=2Ehyracks=2Ealgebricks=2Ecore=2Ealgebra=2Efunctions=2EFunc= tionIdentifier;
-import org=2Eapache=2Ehyracks=2Ealgebricks=2Ecore=2Ealg= ebra=2Emetadata=2EIMetadataProvider;
-import org=2Ejunit=2EAssert;
-i= mport org=2Ejunit=2ETest;
-import org=2Ereflections=2EReflections;
-i= mport org=2Ereflections=2Escanners=2ESubTypesScanner;
-
-// Tests if = all type computers can handle input type ANY properly=2E
-// TODO: this = test should be fixed/updated/modified/enhanced
-public class TypeCompute= rTest {
-
- @Test
- public void test() throws Exception {- // Mocks the type environment=2E
- IVariableTypeEnviron= ment mockTypeEnv =3D mock(IVariableTypeEnvironment=2Eclass);
-
- = // Mocks the metadata provider=2E
- IMetadataProvider<?, ?&= gt; mockMetadataProvider =3D mock(IMetadataProvider=2Eclass);
-
- = // Mocks function expression=2E
- AbstractFunctionCallExpress= ion mockExpr =3D mock(AbstractFunctionCallExpression=2Eclass);
- = FunctionIdentifier fid =3D mock(FunctionIdentifier=2Eclass);
- wh= en(mockExpr=2EgetFunctionIdentifier())=2EthenReturn(fid);
- when(= fid=2EgetName())=2EthenReturn("testFunction");
-
- /= / A function at most has six argument=2E
- List<Mutable<ILo= gicalExpression>> sixArgs =3D createArgs(6, mockTypeEnv);
-
- = // Sets up arguments for the mocked expression=2E
- when(mo= ckExpr=2EgetArguments())=2EthenReturn(sixArgs);
-
- // Sets up= required/actual types of the mocked expression=2E
- Object[] opa= queParameters =3D new Object[2];
- opaqueParameters[0] =3D Builti= nType=2EANY;
- opaqueParameters[1] =3D BuiltinType=2EANY;
- = when(mockExpr=2EgetOpaqueParameters())=2EthenReturn(opaqueParameters);=
-
- // functions that check the number of args inside the typ= e computer
- List<Mutable<ILogicalExpression>> replac= eArgs =3D createArgs(4, mockTypeEnv);
- List<Mutable<ILogic= alExpression>> sliceArgs =3D createArgs(3, mockTypeEnv);
- = List<Mutable<ILogicalExpression>> rangeArgs =3D createArgs(3, m= ockTypeEnv);
- HashMap<String, List<Mutable<ILogicalExpr= ession>>> map =3D new HashMap<>();
- map=2Eput(&qu= ot;INSTANCE_REPLACE", replaceArgs);
- map=2Eput("INSTAN= CE_SLICE", sliceArgs);
- map=2Eput("ArrayRangeTypeCompu= ter", rangeArgs);
-
- // Several exceptional type compute= rs=2E
- Set<String> exceptionalTypeComputers =3D new HashSe= t<>();
- exceptionalTypeComputers=2Eadd("InjectFailure= TypeComputer");
- exceptionalTypeComputers=2Eadd("Recor= dAddFieldsTypeComputer");
- exceptionalTypeComputers=2Eadd(&= quot;OpenRecordConstructorResultType");
- exceptionalTypeCom= puters=2Eadd("RecordRemoveFieldsTypeComputer");
- excep= tionalTypeComputers=2Eadd("ClosedRecordConstructorResultType");- exceptionalTypeComputers=2Eadd("LocalAvgTypeComputer")= ;
- exceptionalTypeComputers=2Eadd("BooleanOnlyTypeComputer&= quot;);
- exceptionalTypeComputers=2Eadd("AMissingTypeComput= er");
- exceptionalTypeComputers=2Eadd("NullableDoubleT= ypeComputer");
- exceptionalTypeComputers=2Eadd("Record= MergeTypeComputer");
- exceptionalTypeComputers=2Eadd("= BooleanOrMissingTypeComputer");
- exceptionalTypeComputers= =2Eadd("LocalSingleVarStatisticsTypeComputer");
-
- = // Tests all usual type computers=2E
- Reflections reflections = =3D new Reflections("org=2Eapache=2Easterix=2Eom=2Etypecomputer",= new SubTypesScanner(false));
- Set<Class<? extends IResult= TypeComputer>> classes =3D reflections=2EgetSubTypesOf(IResultTypeCom= puter=2Eclass);
- for (Class<? extends IResultTypeComputer>= c : classes) {
- if (exceptionalTypeComputers=2Econtains(c= =2EgetSimpleName()) || Modifier=2EisAbstract(c=2EgetModifiers())) {
- = continue;
- }
- System=2Eout=2Epri= ntln("Test type computer: " + c=2EgetName());
- Ass= ert=2EassertTrue(testTypeComputer(c, mockTypeEnv, mockMetadataProvider, moc= kExpr, map, sixArgs));
- }
- }
-
- private boolean= testTypeComputer(Class<? extends IResultTypeComputer> c, IVariableTy= peEnvironment mockTypeEnv,
- IMetadataProvider<?, ?> mo= ckMetadataProvider, AbstractFunctionCallExpression mockExpr,
- = HashMap<String, List<Mutable<ILogicalExpression>>> map,= List<Mutable<ILogicalExpression>> sixArgs)
- thr= ows Exception {
- // Tests the return type=2E It should be either= ANY or NULLABLE/MISSABLE=2E
- IResultTypeComputer instance;
-= IAType resultType;
- Field[] fields =3D c=2EgetFields();<= br>- List<Mutable<ILogicalExpression>> args;
- = for (Field field : fields) {
- if (field=2EgetName()=2Estart= sWith("INSTANCE")) {
- System=2Eout=2Eprintln(&= quot;Test type computer INSTANCE: " + field=2EgetName());
- = args =3D getArgs(field=2EgetName(), c, map);
- if= (args !=3D null) {
- when(mockExpr=2EgetArguments())= =2EthenReturn(args);
- } else {
- w= hen(mockExpr=2EgetArguments())=2EthenReturn(sixArgs);
- }=
- instance =3D (IResultTypeComputer) field=2Eget(null);<= br>- resultType =3D instance=2EcomputeType(mockExpr, mockTyp= eEnv, mockMetadataProvider);
- ATypeTag typeTag =3D resul= tType=2EgetTypeTag();
- if (typeTag !=3D ATypeTag=2EANY &= amp;& !(typeTag =3D=3D ATypeTag=2EUNION && ((AUnionType) result= Type)=2EisNullableType()
- && ((AUnionTyp= e) resultType)=2EisMissableType())) {
- return false;=
- }
- }
- }
- return t= rue;
- }
-
- private List<Mutable<ILogicalExpression&g= t;> createArgs(int numArgs, IVariableTypeEnvironment mockTypeEnv)
- = throws Exception {
- List<Mutable<ILogicalExpress= ion>> argRefs =3D new ArrayList<>();
- for (int argIn= dex =3D 0; argIndex < numArgs; ++argIndex) {
- ILogicalExp= ression mockArg =3D mock(ILogicalExpression=2Eclass);
- argRe= fs=2Eadd(new MutableObject<>(mockArg));
- when(mockType= Env=2EgetType(mockArg))=2EthenReturn(BuiltinType=2EANY);
- }
-=
- return argRefs;
- }
-
- private List<Mutable= <ILogicalExpression>> getArgs(String instanceName, Class<? exte= nds IResultTypeComputer> c,
- HashMap<String, List<M= utable<ILogicalExpression>>> map) {
- if (instanceNam= e=2Eequals("INSTANCE")) {
- return map=2Eget(c=2Ege= tSimpleName());
- } else {
- return map=2Eget(insta= nceName);
- }
- }
-}
diff --git a/asterixdb/asterix-o= m/src/test/java/org/apache/asterix/om/typecomputer/ExceptionTest=2Ejava b/a= sterixdb/asterix-om/src/test/java/org/apache/asterix/test/om/typecomputer/E= xceptionTest=2Ejava
similarity index 98%
rename from asterixdb/asteri= x-om/src/test/java/org/apache/asterix/om/typecomputer/ExceptionTest=2Ejava<= br>rename to asterixdb/asterix-om/src/test/java/org/apache/asterix/test/om/= typecomputer/ExceptionTest=2Ejava
index 29cb9a7=2E=2E3d8c690 100644
-= -- a/asterixdb/asterix-om/src/test/java/org/apache/asterix/om/typecomputer/= ExceptionTest=2Ejava
+++ b/asterixdb/asterix-om/src/test/java/org/apache= /asterix/test/om/typecomputer/ExceptionTest=2Ejava
@@ -17,7 +17,7 @@
= * under the License=2E
*/

-package org=2Eapache=2Easterix= =2Eom=2Etypecomputer;
+package org=2Eapache=2Easterix=2Etest=2Eom=2Etype= computer;

import static org=2Emockito=2EMockito=2Emock;
import= static org=2Emockito=2EMockito=2Ewhen;
diff --git a/asterixdb/asterix-o= m/src/test/java/org/apache/asterix/test/om/typecomputer/TypeComputerTest=2E= java b/asterixdb/asterix-om/src/test/java/org/apache/asterix/test/om/typeco= mputer/TypeComputerTest=2Ejava
new file mode 100644
index 0000000=2E= =2Eb65c15e
--- /dev/null
+++ b/asterixdb/asterix-om/src/test/java/org= /apache/asterix/test/om/typecomputer/TypeComputerTest=2Ejava
@@ -0,0 +1,= 291 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under= one
+ * or more contributor license agreements=2E See the NOTICE file<= br>+ * distributed with this work for additional information
+ * regardi= ng copyright ownership=2E The ASF licenses this file
+ * to you under t= he Apache License, Version 2=2E0 (the
+ * "License"); you may = not use this file except in compliance
+ * with the License=2E You may = obtain a copy of the License at
+ *
+ * http://www=2Eapache=2Eorg/l= icenses/LICENSE-2=2E0
+ *
+ * Unless required by applicable law or ag= reed to in writing,
+ * software distributed under the License is distri= buted on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITION= S OF ANY
+ * KIND, either express or implied=2E See the License for the=
+ * specific language governing permissions and limitations
+ * unde= r the License=2E
+ */
+
+package org=2Eapache=2Easterix=2Etest=2Eo= m=2Etypecomputer;
+
+import static org=2Emockito=2EMockito=2Emock;+import static org=2Emockito=2EMockito=2Ewhen;
+
+import java=2Elang= =2Ereflect=2EField;
+import java=2Elang=2Ereflect=2EModifier;
+import= java=2Eutil=2EArrayList;
+import java=2Eutil=2ECollection;
+import j= ava=2Eutil=2EHashMap;
+import java=2Eutil=2EHashSet;
+import java=2Eu= til=2EList;
+import java=2Eutil=2ESet;
+
+import org=2Eapache=2Eas= terix=2Eom=2Etypecomputer=2Ebase=2EIResultTypeComputer;
+import org=2Eap= ache=2Easterix=2Eom=2Etypes=2EATypeTag;
+import org=2Eapache=2Easterix= =2Eom=2Etypes=2EAUnionType;
+import org=2Eapache=2Easterix=2Eom=2Etypes= =2EBuiltinType;
+import org=2Eapache=2Easterix=2Eom=2Etypes=2EIAType;+import org=2Eapache=2Ecommons=2Elang3=2Emutable=2EMutable;
+import org= =2Eapache=2Ecommons=2Elang3=2Emutable=2EMutableObject;
+import org=2Eapa= che=2Ehyracks=2Ealgebricks=2Ecore=2Ealgebra=2Ebase=2EILogicalExpression;+import org=2Eapache=2Ehyracks=2Ealgebricks=2Ecore=2Ealgebra=2Eexpressions= =2EAbstractFunctionCallExpression;
+import org=2Eapache=2Ehyracks=2Ealge= bricks=2Ecore=2Ealgebra=2Eexpressions=2EIVariableTypeEnvironment;
+impor= t org=2Eapache=2Ehyracks=2Ealgebricks=2Ecore=2Ealgebra=2Efunctions=2EFuncti= onIdentifier;
+import org=2Eapache=2Ehyracks=2Ealgebricks=2Ecore=2Ealgeb= ra=2Emetadata=2EIMetadataProvider;
+import org=2Eapache=2Elogging=2Elog4= j=2ELevel;
+import org=2Eapache=2Elogging=2Elog4j=2ELogManager;
+impo= rt org=2Eapache=2Elogging=2Elog4j=2ELogger;
+import org=2Ejunit=2EAssert= ;
+import org=2Ejunit=2ETest;
+import org=2Ejunit=2Erunner=2ERunWith;=
+import org=2Ejunit=2Erunners=2EParameterized;
+import org=2Ejunit= =2Erunners=2EParameterized=2EParameter;
+import org=2Ejunit=2Erunners=2E= Parameterized=2EParameters;
+import org=2Ereflections=2EReflections;
= +import org=2Ereflections=2Escanners=2ESubTypesScanner;
+
+/**
+ *= This test passes a number of arguments to the type computers, all argument= s of type "any", and ensures that
+ * each computer handles th= e "any" type properly=2E The expected behavior for each type comp= uter is to return "any",
+ * "nullable" or "mis= sable" type result=2E
+ *
+ * Things to note:
+ * - The funct= ion passes 6 "any" arguments because, as of now, no function that= we have has more than 6 arguments=2E
+ * two other lists are made (3 ar= gs and 4 args), those are needed by specific type computers for now, those = should be
+ * changed and then the lists can be removed from the test=2E=
+ * - Some functions have a different behavior with "any" val= ue, those will be added to an exception list=2E
+ * - Some functions che= ck their arguments count, this will make passing 6 arguments fail,
+ * t= hose are added to exception list=2E
+ */
+
+@RunWith(Parameterized= =2Eclass)
+public class TypeComputerTest {
+
+ private static f= inal Logger LOGGER =3D LogManager=2EgetLogger();
+
+ // type compu= ters that have a different behavior when handling "any" type
+= private static Set<String> differentBehaviorFunctions =3D new Has= hSet<>();
+
+ // type computers that check the number of arg= uments
+ private static HashMap<Field, List<Mutable<ILogical= Expression>>> checkArgsCountFunctions =3D new HashMap<>();+
+ // Members
+ private static IVariableTypeEnvironment env;=
+ private static IMetadataProvider metadataProvider;
+ private= static AbstractFunctionCallExpression functionCallExpression;
+
+ = // Arguments all of type "any", different combination is provide= d because it's needed by other functions (for now)
+ private stat= ic List<Mutable<ILogicalExpression>> threeArgs;
+ private= static List<Mutable<ILogicalExpression>> fourArgs;
+ pri= vate static List<Mutable<ILogicalExpression>> sixArgs;
+
= + @Parameter
+ public String testName;
+
+ @Parameter(1)<= br>+ public Class<? extends IResultTypeComputer> clazz;
+
+ = @Parameters(name =3D "TypeComputerTest {index}: {0}")
+ = public static Collection<Object[]> tests() throws Exception {
++ System=2Eout=2Eprintln("\n----------------------------------= ----------------------------------------------------");
+
+ = // Prepare the test environment first
+ setup();
+
+ = // Prepare tests
+ List<Object[]> tests =3D new ArrayLi= st<>();
+
+ // Tests all usual type computers=2E
+ = Reflections reflections =3D new Reflections("org=2Eapache=2Easter= ix=2Eom=2Etypecomputer", new SubTypesScanner(false));
+ Set&= lt;Class<? extends IResultTypeComputer>> classes =3D reflections= =2EgetSubTypesOf(IResultTypeComputer=2Eclass);
+
+ for (Class&= lt;? extends IResultTypeComputer> clazz : classes) {
+ if = (Modifier=2EisAbstract(clazz=2EgetModifiers())) {
+ LOGGE= R=2Elog(Level=2EINFO, "Excluding " + clazz=2EgetSimpleName() + &q= uot; (Abstract class)");
+ continue;
+ = }
+
+ if (differentBehaviorFunctions=2Econtains(clazz=2Eg= etSimpleName())) {
+ LOGGER=2Elog(Level=2EINFO, "Exc= luding " + clazz=2EgetSimpleName() + " (Special behavior)");=
+ continue;
+ }
+
+ tests= =2Eadd(new Object[] { clazz=2EgetSimpleName(), clazz });
+ }
+=
+ System=2Eout=2Eprintln("---------------------------------= -----------------------------------------------------\n");
+
+ = return tests;
+ }
+
+ /**
+ * Test return types= should be either "any", "missable" or "nullable&q= uot;
+ *
+ * @throws Exception Exception
+ */
+ = @Test
+ public void test() throws Exception {
+
+ // Tes= ts the return type=2E It should be either ANY or NULLABLE/MISSABLE=2E
+ = IResultTypeComputer instance;
+ IAType resultType;
+ = List<Mutable<ILogicalExpression>> args;
+ Field[= ] fields =3D clazz=2EgetFields();
+
+ // The type computer fie= lds are only the ones that start with "INSTANCE"
+ for = (Field field : fields) {
+
+ if (field=2EgetName()=2Estart= sWith("INSTANCE")) {
+ LOGGER=2Elog(Level=2EINF= O, "Testing " + clazz=2EgetSimpleName() + ": " + field= =2EgetName());
+
+ // Need to check if this is a speci= al type computer that counts number of arguments
+ args = =3D checkArgsCountFunctions=2Eget(field);
+
+ // Yes, = pass its specified arguments in the map
+ if (args !=3D n= ull) {
+ when(functionCallExpression=2EgetArguments()= )=2EthenReturn(args);
+ }
+ // No, pass= six arguments
+ else {
+ when(func= tionCallExpression=2EgetArguments())=2EthenReturn(sixArgs);
+ = }
+
+ instance =3D (IResultTypeComputer) field=2E= get(null);
+ resultType =3D instance=2EcomputeType(functi= onCallExpression, env, metadataProvider);
+ ATypeTag type= Tag =3D resultType=2EgetTypeTag();
+
+ // Result shoul= d be ANY, Missable or Nullable
+ Assert=2EassertTrue(type= Tag =3D=3D ATypeTag=2EANY
+ || (typeTag =3D=3D AT= ypeTag=2EUNION && ((AUnionType) resultType)=2EisNullableType()
+= || ((AUnionType) resultType)=2EisMissableTy= pe()));
+ }
+ }
+ }
+
+ public stati= c void setup() throws Exception {
+
+ // Mocks the type enviro= nment=2E
+ env =3D mock(IVariableTypeEnvironment=2Eclass);
++ // Mocks the metadata provider=2E
+ metadataProvider = =3D mock(IMetadataProvider=2Eclass);
+
+ // Prepare the functi= on arguments
+ threeArgs =3D createArgs(3);
+ fourArgs = =3D createArgs(4);
+ sixArgs =3D createArgs(6);
+
+ = // Mocks function identifier
+ FunctionIdentifier functionIdentif= ier =3D mock(FunctionIdentifier=2Eclass);
+ when(functionIdentifi= er=2EgetName())=2EthenReturn("testFunction");
+
+ //= Mocks function expression=2E
+ functionCallExpression =3D mock(A= bstractFunctionCallExpression=2Eclass);
+ when(functionCallExpres= sion=2EgetFunctionIdentifier())=2EthenReturn(functionIdentifier);
+ = when(functionCallExpression=2EgetArguments())=2EthenReturn(sixArgs);
= +
+ // Sets up required/actual types of the mocked expression=2E<= br>+ Object[] opaqueParameters =3D new Object[2];
+ opaque= Parameters[0] =3D BuiltinType=2EANY;
+ opaqueParameters[1] =3D Bu= iltinType=2EANY;
+ when(functionCallExpression=2EgetOpaqueParamet= ers())=2EthenReturn(opaqueParameters);
+
+ // Add to exception= list for computers checking their arguments count
+ addComputers= CheckingArgsCount();
+
+ // Add to exception list for computer= s having a different behavior for "any" type
+ addCompu= tersBehavingDifferently();
+ }
+
+ // TODO This is not a goo= d practice, if the class name is changed, the test will fail and this needs= to be updated
+ // Consider using annotation to avoid modifying the = test and have a generic behavior
+ /**
+ * Adds the type compu= ters that have a different behavior for "any" type=2E
+ */=
+ private static void addComputersBehavingDifferently() {
+ = differentBehaviorFunctions=2Eadd("InjectFailureTypeComputer");<= br>+ differentBehaviorFunctions=2Eadd("RecordAddFieldsTypeCompu= ter");
+ differentBehaviorFunctions=2Eadd("OpenRecordCo= nstructorResultType");
+ differentBehaviorFunctions=2Eadd(&q= uot;RecordRemoveFieldsTypeComputer");
+ differentBehaviorFun= ctions=2Eadd("ClosedRecordConstructorResultType");
+ di= fferentBehaviorFunctions=2Eadd("LocalAvgTypeComputer");
+ = differentBehaviorFunctions=2Eadd("BooleanOnlyTypeComputer");+ differentBehaviorFunctions=2Eadd("AMissingTypeComputer"= ;);
+ differentBehaviorFunctions=2Eadd("NullableDoubleTypeCo= mputer");
+ differentBehaviorFunctions=2Eadd("RecordMer= geTypeComputer");
+ differentBehaviorFunctions=2Eadd("B= ooleanOrMissingTypeComputer");
+ differentBehaviorFunctions= =2Eadd("LocalSingleVarStatisticsTypeComputer");
+ }
++ // TODO Type computers should not be checking the arguments count, if= the argument count is variable but knowable,
+ // then multiple INST= ANCES need to be created, each indicating the number of incoming arguments,= and based on that
+ // applying the appropriate behavior in the comp= ute method body
+ /**
+ * Adds the type computers that check t= he args count in their method body=2E If 6 arguments are passed to those+ * computers, they're gonna throw an exception, so we manually sp= ecify how many arguments they should get=2E
+ *
+ * @throws E= xception Exception
+ */
+ private static void addComputersChec= kingArgsCount() throws Exception {
+
+ // AListTypeComputer+ Class<?> clazz =3D Class=2EforName("org=2Eapache=2East= erix=2Eom=2Etypecomputer=2Eimpl=2EAListTypeComputer");
+ Fie= ld[] fields =3D clazz=2EgetFields();
+
+ for (Field field : fi= elds) {
+ if (field=2EgetName()=2EequalsIgnoreCase("INST= ANCE_SLICE")) {
+ LOGGER=2Elog(Level=2EINFO, field= =2EgetName() + " will use only 3 arguments");
+ = checkArgsCountFunctions=2Eput(field, threeArgs);
+ }
++ if (field=2EgetName()=2EequalsIgnoreCase("INSTANCE_REPLA= CE")) {
+ LOGGER=2Elog(Level=2EINFO, field=2EgetName= () + " will use only 4 arguments");
+ checkArgs= CountFunctions=2Eput(field, fourArgs);
+ }
+ }
+=
+ // ArrayRangeTypeComputer
+ clazz =3D Class=2EforNam= e("org=2Eapache=2Easterix=2Eom=2Etypecomputer=2Eimpl=2EArrayRangeTypeC= omputer");
+ fields =3D clazz=2EgetFields();
+
+ = for (Field field : fields) {
+ if (field=2EgetName()=2Eequa= lsIgnoreCase("INSTANCE")) {
+ LOGGER=2Elog(Leve= l=2EINFO, field=2EgetName() + " will use only 3 arguments");
+= checkArgsCountFunctions=2Eput(field, threeArgs);
+ = }
+ }
+ }
+
+ /**
+ * Creates express= ions matching the number passed as an argument=2E Variable type environment= is set for all those
+ * expressions to be of type "any"= =2E
+ *
+ * @param numArgs number of arguments to create
+= * @return a list holding the created expressions
+ * @throws Ex= ception Exception
+ */
+ private static List<Mutable<ILo= gicalExpression>> createArgs(int numArgs) throws Exception {
+
= + List<Mutable<ILogicalExpression>> arguments =3D new Ar= rayList<>();
+
+ for (int i =3D 0; i < numArgs; ++i) = {
+ ILogicalExpression argument =3D mock(ILogicalExpression= =2Eclass);
+ arguments=2Eadd(new MutableObject<>(argume= nt));
+ when(env=2EgetType(argument))=2EthenReturn(BuiltinTyp= e=2EANY);
+ }
+
+ return arguments;
+ }
+}<= br>diff --git a/asterixdb/asterix-om/src/test/java/org/apache/asterix/om/ut= il/JSONDeserializerForTypesTest=2Ejava b/asterixdb/asterix-om/src/test/java= /org/apache/asterix/test/om/util/JSONDeserializerForTypesTest=2Ejava
sim= ilarity index 98%
rename from asterixdb/asterix-om/src/test/java/org/apa= che/asterix/om/util/JSONDeserializerForTypesTest=2Ejava
rename to asteri= xdb/asterix-om/src/test/java/org/apache/asterix/test/om/util/JSONDeserializ= erForTypesTest=2Ejava
index 32ec75a=2E=2E35e4d35 100644
--- a/asterix= db/asterix-om/src/test/java/org/apache/asterix/om/util/JSONDeserializerForT= ypesTest=2Ejava
+++ b/asterixdb/asterix-om/src/test/java/org/apache/aste= rix/test/om/util/JSONDeserializerForTypesTest=2Ejava
@@ -17,7 +17,7 @@ * under the License=2E
*/

-package org=2Eapache=2Easterix= =2Eom=2Eutil;
+package org=2Eapache=2Easterix=2Etest=2Eom=2Eutil;
import java=2Eutil=2EArrayList;
import java=2Eutil=2EList;
=

To view, visit change 3393=2E To unsubscribe, visit settings=2E

Gerrit-Project= : asterixdb
Gerrit-Branch: master
Gerrit-MessageType: newchange
Gerrit-Change-Id: I4426efcc9e825ebb00e04e3783d18bb1cb= b63a90
Gerrit-Change-Number: 3393
Gerrit-PatchSet: 1
Gerrit-Owner: Hussain Towaileb <hussainht@gmail=2Ecom>
Gerrit-Reviewer: Hussain Towaileb <Huss= ainHT@Gmail=2Ecom>
--v1R3RmNVOJw=--