This is an automated email from the ASF dual-hosted git repository. mblow pushed a commit to branch master in repository https://gitbox.apache.org/repos/asf/asterixdb.git
commit 265e3ce136970640709242658e234a77e7d1b06b Author: Dmitry Lychagin <[email protected]> AuthorDate: Tue Mar 2 12:22:38 2021 -0800 [NO ISSUE][COMP] CREATE FUNCTION IF NOT EXISTS improvements - user model changes: no - storage format changes: no - interface changes: no Details: - Move IF NOT EXISTS modifier after function parameter list in CREATE FUNCTION - Parser now prohibits IF NOT EXISTS with OR REPLACE in CREATE FUNCTION. Remove this check from QueryTranslator - Add testcases and update documentation Change-Id: Iddaab4f829574de47cb9baf42cc7def92429f2c8 Reviewed-on: https://asterix-gerrit.ics.uci.edu/c/asterixdb/+/10323 Integration-Tests: Jenkins <[email protected]> Tested-by: Jenkins <[email protected]> Reviewed-by: Dmitry Lychagin <[email protected]> Reviewed-by: Till Westmann <[email protected]> --- .../apache/asterix/app/translator/QueryTranslator.java | 8 ++------ .../bad-ext-function-ddl-1.4.ddl.sqlpp} | 12 ++++++------ .../external-library/mysum/mysum.2.ddl.sqlpp | 2 +- .../bad-function-ddl-11/bad-function-ddl-11.4.ddl.sqlpp} | 15 ++++++++++----- .../src/test/resources/runtimets/testsuite_it_sqlpp.xml | 1 + .../src/test/resources/runtimets/testsuite_sqlpp.xml | 1 + asterixdb/asterix-doc/src/main/grammar/sqlpp.ebnf | 2 +- asterixdb/asterix-lang-sqlpp/src/main/javacc/SQLPP.jj | 16 +++++++++------- 8 files changed, 31 insertions(+), 26 deletions(-) diff --git a/asterixdb/asterix-app/src/main/java/org/apache/asterix/app/translator/QueryTranslator.java b/asterixdb/asterix-app/src/main/java/org/apache/asterix/app/translator/QueryTranslator.java index 0a34559..233a678 100644 --- a/asterixdb/asterix-app/src/main/java/org/apache/asterix/app/translator/QueryTranslator.java +++ b/asterixdb/asterix-app/src/main/java/org/apache/asterix/app/translator/QueryTranslator.java @@ -2040,14 +2040,10 @@ public class QueryTranslator extends AbstractLangTranslator implements IStatemen List<TypeSignature> existingInlineTypes; Function existingFunction = MetadataManager.INSTANCE.getFunction(mdTxnCtx, functionSignature); if (existingFunction != null) { - if (cfs.getReplaceIfExists()) { - if (cfs.getIfNotExists()) { - throw new CompilationException(ErrorCode.PARSE_ERROR, cfs.getSourceLocation(), "IF NOT EXISTS"); - } - } else if (cfs.getIfNotExists()) { + if (cfs.getIfNotExists()) { MetadataManager.INSTANCE.commitTransaction(mdTxnCtx); return; - } else { + } else if (!cfs.getReplaceIfExists()) { throw new CompilationException(ErrorCode.FUNCTION_EXISTS, cfs.getSourceLocation(), functionSignature.toString(false)); } diff --git a/asterixdb/asterix-app/src/test/resources/runtimets/queries_sqlpp/external-library/mysum/mysum.2.ddl.sqlpp b/asterixdb/asterix-app/src/test/resources/runtimets/queries_sqlpp/external-library/bad-ext-function-ddl-1/bad-ext-function-ddl-1.4.ddl.sqlpp similarity index 69% copy from asterixdb/asterix-app/src/test/resources/runtimets/queries_sqlpp/external-library/mysum/mysum.2.ddl.sqlpp copy to asterixdb/asterix-app/src/test/resources/runtimets/queries_sqlpp/external-library/bad-ext-function-ddl-1/bad-ext-function-ddl-1.4.ddl.sqlpp index 9f325a3..3aa6169 100644 --- a/asterixdb/asterix-app/src/test/resources/runtimets/queries_sqlpp/external-library/mysum/mysum.2.ddl.sqlpp +++ b/asterixdb/asterix-app/src/test/resources/runtimets/queries_sqlpp/external-library/bad-ext-function-ddl-1/bad-ext-function-ddl-1.4.ddl.sqlpp @@ -17,10 +17,10 @@ * under the License. */ -create function externallibtest.mysum(a: int32, b: int32) returns int32 - as "org.apache.asterix.external.library.MySumFactory" at externallibtest.testlib; - -/* test if not exists */ -create function externallibtest.mysum if not exists (a: int32, b: int32) returns int32 - as "org.apache.asterix.external.library.MySumFactory" at externallibtest.testlib; +/* + * Description : IF NOT EXISTS is not allowed if OR REPLACE is present + * Expected Res : Error + */ +create or replace function externallibtest.f4(a) if not exists + as "org.apache.asterix.external.library.OpenCapitalFinderFactory" at testlib; \ No newline at end of file diff --git a/asterixdb/asterix-app/src/test/resources/runtimets/queries_sqlpp/external-library/mysum/mysum.2.ddl.sqlpp b/asterixdb/asterix-app/src/test/resources/runtimets/queries_sqlpp/external-library/mysum/mysum.2.ddl.sqlpp index 9f325a3..3acb768 100644 --- a/asterixdb/asterix-app/src/test/resources/runtimets/queries_sqlpp/external-library/mysum/mysum.2.ddl.sqlpp +++ b/asterixdb/asterix-app/src/test/resources/runtimets/queries_sqlpp/external-library/mysum/mysum.2.ddl.sqlpp @@ -21,6 +21,6 @@ create function externallibtest.mysum(a: int32, b: int32) returns int32 as "org.apache.asterix.external.library.MySumFactory" at externallibtest.testlib; /* test if not exists */ -create function externallibtest.mysum if not exists (a: int32, b: int32) returns int32 +create function externallibtest.mysum(a: int32, b: int32) if not exists returns int32 as "org.apache.asterix.external.library.MySumFactory" at externallibtest.testlib; diff --git a/asterixdb/asterix-app/src/test/resources/runtimets/queries_sqlpp/external-library/mysum/mysum.2.ddl.sqlpp b/asterixdb/asterix-app/src/test/resources/runtimets/queries_sqlpp/user-defined-functions/bad-function-ddl-11/bad-function-ddl-11.4.ddl.sqlpp similarity index 69% copy from asterixdb/asterix-app/src/test/resources/runtimets/queries_sqlpp/external-library/mysum/mysum.2.ddl.sqlpp copy to asterixdb/asterix-app/src/test/resources/runtimets/queries_sqlpp/user-defined-functions/bad-function-ddl-11/bad-function-ddl-11.4.ddl.sqlpp index 9f325a3..73cad66 100644 --- a/asterixdb/asterix-app/src/test/resources/runtimets/queries_sqlpp/external-library/mysum/mysum.2.ddl.sqlpp +++ b/asterixdb/asterix-app/src/test/resources/runtimets/queries_sqlpp/user-defined-functions/bad-function-ddl-11/bad-function-ddl-11.4.ddl.sqlpp @@ -17,10 +17,15 @@ * under the License. */ -create function externallibtest.mysum(a: int32, b: int32) returns int32 - as "org.apache.asterix.external.library.MySumFactory" at externallibtest.testlib; +/* + * Description : IF NOT EXISTS is not allowed if OR REPLACE is present + * Expected Res : Error + */ -/* test if not exists */ -create function externallibtest.mysum if not exists (a: int32, b: int32) returns int32 - as "org.apache.asterix.external.library.MySumFactory" at externallibtest.testlib; +drop dataverse experiments4 if exists; +create dataverse experiments4; +use experiments4; +create or replace function myfn004() if not exists { + 1 +}; \ No newline at end of file diff --git a/asterixdb/asterix-app/src/test/resources/runtimets/testsuite_it_sqlpp.xml b/asterixdb/asterix-app/src/test/resources/runtimets/testsuite_it_sqlpp.xml index 1ebc78c..a9f52b4 100644 --- a/asterixdb/asterix-app/src/test/resources/runtimets/testsuite_it_sqlpp.xml +++ b/asterixdb/asterix-app/src/test/resources/runtimets/testsuite_it_sqlpp.xml @@ -27,6 +27,7 @@ <compilation-unit name="bad-ext-function-ddl-1"> <output-dir compare="Text">none</output-dir> <expected-error>ASX1079: Compilation error: Variable number of parameters is not supported for external functions</expected-error> + <expected-error>ASX1001: Syntax error: Unexpected IF NOT EXISTS (in line 25, at column 1)</expected-error> </compilation-unit> </test-case> <test-case FilePath="external-library"> diff --git a/asterixdb/asterix-app/src/test/resources/runtimets/testsuite_sqlpp.xml b/asterixdb/asterix-app/src/test/resources/runtimets/testsuite_sqlpp.xml index d2135df..8963f49 100644 --- a/asterixdb/asterix-app/src/test/resources/runtimets/testsuite_sqlpp.xml +++ b/asterixdb/asterix-app/src/test/resources/runtimets/testsuite_sqlpp.xml @@ -12012,6 +12012,7 @@ <expected-error>ASX1001: Syntax error: Unexpected type declaration for parameter a in function myfn001</expected-error> <expected-error>ASX1001: Syntax error: Unexpected return type declaration for function myfn002</expected-error> <expected-error>ASX1001: Syntax error: Unexpected return type declaration for function myfn003</expected-error> + <expected-error>ASX1001: Syntax error: Unexpected IF NOT EXISTS (in line 29, at column 1)</expected-error> </compilation-unit> </test-case> <test-case FilePath="user-defined-functions"> diff --git a/asterixdb/asterix-doc/src/main/grammar/sqlpp.ebnf b/asterixdb/asterix-doc/src/main/grammar/sqlpp.ebnf index aae81ec..cf7d4a5 100644 --- a/asterixdb/asterix-doc/src/main/grammar/sqlpp.ebnf +++ b/asterixdb/asterix-doc/src/main/grammar/sqlpp.ebnf @@ -226,7 +226,7 @@ CreateSynonym ::= "CREATE" "SYNONYM" QualifiedName "FOR" QualifiedName ("IF" "NO FunctionDeclaration ::= "DECLARE" "FUNCTION" Identifier "(" ( (Identifier ("," Identifier)*) | "..." )? ")" "{" Expr "}" -CreateFunction ::= "CREATE" ("OR" "REPLACE")? "FUNCTION" QualifiedName ("IF" "NOT" "EXISTS")? "(" FunctionParameters? ")" +CreateFunction ::= "CREATE" ("OR" "REPLACE")? "FUNCTION" QualifiedName "(" FunctionParameters? ")" ("IF" "NOT" "EXISTS")? ( ("{" Expr "}") | ExternalFunctionDef ) FunctionParameters ::= ( Identifier ((":")? TypeExpr)? ("," Identifier ((":")? TypeExpr)? )* ) | "..." diff --git a/asterixdb/asterix-lang-sqlpp/src/main/javacc/SQLPP.jj b/asterixdb/asterix-lang-sqlpp/src/main/javacc/SQLPP.jj index 687920a..77765b1 100644 --- a/asterixdb/asterix-lang-sqlpp/src/main/javacc/SQLPP.jj +++ b/asterixdb/asterix-lang-sqlpp/src/main/javacc/SQLPP.jj @@ -1259,12 +1259,13 @@ CreateFunctionStatement FunctionSpecification(Token startStmtToken, boolean orRe { defaultDataverse = fctName.dataverse; } - ifNotExists = IfNotExists() paramsWithArity = FunctionParameters() { arity = paramsWithArity.first; params = paramsWithArity.second; + signature = new FunctionSignature(fctName.dataverse, fctName.function, arity); } + ifNotExists = IfNotExists() returnType = FunctionReturnType() ( ( @@ -1279,13 +1280,10 @@ CreateFunctionStatement FunctionSpecification(Token startStmtToken, boolean orRe endPos = token; String functionBody = extractFragment(beginPos.beginLine, beginPos.beginColumn, endPos.beginLine, endPos.beginColumn); - signature = new FunctionSignature(fctName.dataverse, fctName.function, arity); getCurrentScope().addFunctionDescriptor(signature, false); removeCurrentScope(); - defaultDataverse = currentDataverse; ensureNoTypeDeclsInFunction(fctName.function, params, returnType, startStmtToken); stmt = new CreateFunctionStatement(signature, params, functionBody, functionBodyExpr, orReplace, ifNotExists); - return addSourceLocation(stmt, startStmtToken); } ) | @@ -1294,18 +1292,22 @@ CreateFunctionStatement FunctionSpecification(Token startStmtToken, boolean orRe <AT> libraryName = QualifiedName() (<WITH> withOptions = RecordConstructor())? { - signature = new FunctionSignature(fctName.dataverse, fctName.function, arity); - defaultDataverse = currentDataverse; try { stmt = new CreateFunctionStatement(signature, params, returnType, libraryName.first, libraryName.second.getValue(), externalIdentifier, withOptions, orReplace, ifNotExists); } catch (AlgebricksException e) { throw new SqlppParseException(getSourceLocation(startStmtToken), e.getMessage()); } - return addSourceLocation(stmt, startStmtToken); } ) ) + { + if (orReplace && ifNotExists) { + throw new SqlppParseException(getSourceLocation(startStmtToken), "Unexpected IF NOT EXISTS"); + } + defaultDataverse = currentDataverse; + return addSourceLocation(stmt, startStmtToken); + } } Pair<Integer, List<Pair<VarIdentifier, TypeExpression>>> FunctionParameters() :
