Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

HIVE-27490: HPL/SQL says it support default value for parameters but not considering them when no value is passed #5084

Merged

Conversation

mdayakar
Copy link
Contributor

HIVE-27490: HPL/SQL says it support default value for parameters but not considering them when no value is passed

What changes were proposed in this pull request?

The changes support considering default values specified for that parameter when value is not passed for the param of a HPLSQL procedure.

Why are the changes needed?

The change is required to support considering default values specified for that parameter when value is not passed for the param of a HPLSQL procedure.

Does this PR introduce any user-facing change?

No

Is the change a dependency upgrade?

No

How was this patch tested?

Tests are added.
mvn test -Dtest=TestHplSqlViaBeeLine -pl itests/hive-unit -Pitests

…not considering them when no value is passed
Comment on lines 154 to 157
actualCnt = actualCnt + defaultParamNamesVsIndexes.size();
if (actualCnt < formalCnt) {
throw new ArityException(ruleContext, procName, formalCnt, passedParamCnt);
}
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

actualCnt can be higher then formalCnt. Let's say we have a function with 2 formal parameters both has default values. When calling the function we pass only one actual parameter. The result is actualCnt = 1 + 2 = 3 which is incorrect.

What is the purpose of this check here? if (actualCnt < formalCnt)

The check in the end of the method should catch such cases too
if ((passedParamCnt + defaultParamNamesVsIndexes.size()) < formalCnt) {

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

actualCnt can be higher then formalCnt. Let's say we have a function with 2 formal parameters both has default values. When calling the function we pass only one actual parameter. The result is actualCnt = 1 + 2 = 3 which is incorrect.

Here actualCnt contains the actual parameters passed + all default parameters of the procedure. Which can be greater than formalCnt as user can pass values for some default params along with non-default params. For the same example a function with 2 formal parameters both has default values. When calling the function we pass only one actual parameter then actualCnt = 1 + 2 = 3 is correct why because user passed one parameter and for other parameter we take default value and execute the procedure. Thats why here we are checking only actualCnt < formalCnt.

What is the purpose of this check here? if (actualCnt < formalCnt)

As explained above if user passes lesser parameters than the required parameters then we should throw exception. For example if a function has 5 total params, in that lets say 2 default params, so here user has to pass minimum 3 param values but if user passes only 2 then 2+2=4 which is lesser than formal count so need to throw exception.

The check in the end of the method should catch such cases too
if ((passedParamCnt + defaultParamNamesVsIndexes.size()) < formalCnt) {

This check is done after processing the values. This is useful if user passes param values in named parameter binding. For example if a function takes 3 params in that 1 param is default one. Here user passes the values for one non-default param and default param using named parameter binding then we should throw exception as one non-default param value is not passed.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Isn't this last check enough for all scenarios?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Using last check now.

if (formalCnt != actualCnt) {
throw new ArityException(actual.getParent(), procName, formalCnt, actualCnt);
int actualCnt = (actualValues == null) ? 0 : actualValues.size();
int passedParamCnt = actualCnt;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What is the difference between passedParamCnt and actualCnt? Can we remove one of them?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

passedParamCnt is the actual params count which user passed while calling the function. actualCnt is actual params passed + default param count(updating actualCnt value later in the flow (actualCnt = actualCnt + defaultParamNamesVsIndexes.size();)

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think the sum of number of params passed by the user and the number of parameters with default values doesn't makes sense because there can be overlaps.
Please remove one of the variables.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done

Comment on lines 185 to 187
private static void populateDefaultParamDetails(List<HplsqlParser.Create_routine_param_itemContext> routineParamItem, int formalCnt,
Map<String, Integer> defaultParamNamesVsIndexes) {
for (int i = 0; i < formalCnt; i++) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

how about

for (int i = 0; i < routineParamItem.size(); i++)

and formalCnt can be removed from param list.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed

Copy link

sonarcloud bot commented Mar 1, 2024

Quality Gate Passed Quality Gate passed

Issues
2 New issues
0 Accepted issues

Measures
0 Security Hotspots
No data about Coverage
No data about Duplication

See analysis details on SonarCloud

@kasakrisz kasakrisz merged commit ff057c2 into apache:master Mar 1, 2024
5 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
3 participants