Skip to content

Commit

Permalink
[incubator-kie-issues#1325] In functions with a scale parameter, th…
Browse files Browse the repository at this point in the history
…at must be in the range [−6111..6176] (apache#5993)

* Fix Round functions scale parameter range.

* Adding Ceiling, Decimal and Floor functions

* Tests

* Tests

* Tests

* Tests
  • Loading branch information
yesamer authored and rgdoliveira committed Jul 8, 2024
1 parent 888a596 commit 0d89fa1
Show file tree
Hide file tree
Showing 16 changed files with 412 additions and 4 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -35,9 +35,21 @@ public CeilingFunction() {
}

public FEELFnResult<BigDecimal> invoke(@ParameterName( "n" ) BigDecimal n) {
return invoke(n, BigDecimal.ZERO);
}

public FEELFnResult<BigDecimal> invoke(@ParameterName( "n" ) BigDecimal n, @ParameterName( "scale" ) BigDecimal scale) {
if ( n == null ) {
return FEELFnResult.ofError(new InvalidParametersEvent(Severity.ERROR, "n", "cannot be null"));
}
return FEELFnResult.ofResult( n.setScale( 0, RoundingMode.CEILING ) );
if ( scale == null ) {
return FEELFnResult.ofError(new InvalidParametersEvent(Severity.ERROR, "scale", "cannot be null"));
}
// Based on Table 76: Semantics of numeric functions, the scale is in range −6111 .. 6176
if (scale.compareTo(BigDecimal.valueOf(-6111)) < 0 || scale.compareTo(BigDecimal.valueOf(6176)) > 0) {
return FEELFnResult.ofError(new InvalidParametersEvent(Severity.ERROR, "scale", "must be in range between -6111 to 6176."));
}

return FEELFnResult.ofResult( n.setScale( scale.intValue(), RoundingMode.CEILING ) );
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,10 @@ public FEELFnResult<BigDecimal> invoke(@ParameterName( "n" ) BigDecimal n, @Para
if ( scale == null ) {
return FEELFnResult.ofError(new InvalidParametersEvent(Severity.ERROR, "scale", "cannot be null"));
}
// Based on Table 76: Semantics of numeric functions, the scale is in range −6111 .. 6176
if (scale.compareTo(BigDecimal.valueOf(-6111)) < 0 || scale.compareTo(BigDecimal.valueOf(6176)) > 0) {
return FEELFnResult.ofError(new InvalidParametersEvent(Severity.ERROR, "scale", "must be in range between -6111 to 6176."));
}

return FEELFnResult.ofResult( n.setScale( scale.intValue(), RoundingMode.HALF_EVEN ) );
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -34,9 +34,21 @@ public FloorFunction() {
}

public FEELFnResult<BigDecimal> invoke(@ParameterName( "n" ) BigDecimal n) {
return invoke(n, BigDecimal.ZERO);
}

public FEELFnResult<BigDecimal> invoke(@ParameterName( "n" ) BigDecimal n, @ParameterName( "scale" ) BigDecimal scale) {
if ( n == null ) {
return FEELFnResult.ofError(new InvalidParametersEvent(Severity.ERROR, "n", "cannot be null"));
}
return FEELFnResult.ofResult( n.setScale( 0, RoundingMode.FLOOR ) );
if ( scale == null ) {
return FEELFnResult.ofError(new InvalidParametersEvent(Severity.ERROR, "scale", "cannot be null"));
}
// Based on Table 76: Semantics of numeric functions, the scale is in range −6111 .. 6176
if (scale.compareTo(BigDecimal.valueOf(-6111)) < 0 || scale.compareTo(BigDecimal.valueOf(6176)) > 0) {
return FEELFnResult.ofError(new InvalidParametersEvent(Severity.ERROR, "scale", "must be in range between -6111 to 6176."));
}

return FEELFnResult.ofResult( n.setScale( scale.intValue(), RoundingMode.FLOOR ) );
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,10 @@ public FEELFnResult<BigDecimal> invoke(@ParameterName( "n" ) BigDecimal n, @Para
if ( scale == null ) {
return FEELFnResult.ofError(new InvalidParametersEvent(Severity.ERROR, "scale", "cannot be null"));
}
// Based on Table 76: Semantics of numeric functions, the scale is in range −6111 .. 6176
if (scale.compareTo(BigDecimal.valueOf(-6111)) < 0 || scale.compareTo(BigDecimal.valueOf(6176)) > 0) {
return FEELFnResult.ofError(new InvalidParametersEvent(Severity.ERROR, "scale", "must be in range between -6111 to 6176."));
}
return FEELFnResult.ofResult( n.setScale( scale.intValue(), RoundingMode.DOWN ) );
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,10 @@ public FEELFnResult<BigDecimal> invoke(@ParameterName( "n" ) BigDecimal n, @Para
if ( scale == null ) {
return FEELFnResult.ofError(new InvalidParametersEvent(Severity.ERROR, "scale", "cannot be null"));
}
// Based on Table 76: Semantics of numeric functions, the scale is in range −6111 .. 6176
if (scale.compareTo(BigDecimal.valueOf(-6111)) < 0 || scale.compareTo(BigDecimal.valueOf(6176)) > 0) {
return FEELFnResult.ofError(new InvalidParametersEvent(Severity.ERROR, "scale", "must be in range between -6111 to 6176."));
}
return FEELFnResult.ofResult( n.setScale( scale.intValue(), RoundingMode.HALF_DOWN ) );
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,10 @@ public FEELFnResult<BigDecimal> invoke(@ParameterName( "n" ) BigDecimal n, @Para
if ( scale == null ) {
return FEELFnResult.ofError(new InvalidParametersEvent(Severity.ERROR, "scale", "cannot be null"));
}
// Based on Table 76: Semantics of numeric functions, the scale is in range −6111 .. 6176
if (scale.compareTo(BigDecimal.valueOf(-6111)) < 0 || scale.compareTo(BigDecimal.valueOf(6176)) > 0) {
return FEELFnResult.ofError(new InvalidParametersEvent(Severity.ERROR, "scale", "must be in range between -6111 to 6176."));
}
return FEELFnResult.ofResult( n.setScale( scale.intValue(), RoundingMode.HALF_UP ) );
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,10 @@ public FEELFnResult<BigDecimal> invoke(@ParameterName( "n" ) BigDecimal n, @Para
if ( scale == null ) {
return FEELFnResult.ofError(new InvalidParametersEvent(Severity.ERROR, "scale", "cannot be null"));
}
// Based on Table 76: Semantics of numeric functions, the scale is in range −6111 .. 6176
if (scale.compareTo(BigDecimal.valueOf(-6111)) < 0 || scale.compareTo(BigDecimal.valueOf(6176)) > 0) {
return FEELFnResult.ofError(new InvalidParametersEvent(Severity.ERROR, "scale", "must be in range between -6111 to 6176."));
}
return FEELFnResult.ofResult( n.setScale( scale.intValue(), RoundingMode.UP ) );
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -156,13 +156,31 @@ private static Collection<Object[]> data() {
{ "decimal( 1.5, 0 )", new BigDecimal("2") , null},
{ "decimal( 2.5, 0 )", new BigDecimal("2") , null},
{ "decimal( null, 0 )", null , FEELEvent.Severity.ERROR},
{ "decimal( 1.555, 2 )", new BigDecimal("1.56") , null},
{ "decimal( -1.56, 1 )", new BigDecimal("-1.6") , null},
{ "decimal( 1.5, 6177 )", null , FEELEvent.Severity.ERROR},
{ "decimal( 1.5, -6122 )", null , FEELEvent.Severity.ERROR},
{ "decimal( 1.5, null )", null , FEELEvent.Severity.ERROR},
{ "decimal( null, null )", null , FEELEvent.Severity.ERROR},
{ "floor( 1.5 )", new BigDecimal("1") , null},
{ "floor( -1.5 )", new BigDecimal("-2") , null},
{ "floor( null )", null , FEELEvent.Severity.ERROR},
{ "floor( 1.555, 2 )", new BigDecimal("1.55") , null},
{ "floor( -1.55, 1 )", new BigDecimal("-1.6") , null},
{ "floor( 1.5, 6177 )", null , FEELEvent.Severity.ERROR},
{ "floor( 1.5, -6122 )", null , FEELEvent.Severity.ERROR},
{ "floor( 1.5, null )", null , FEELEvent.Severity.ERROR},
{ "floor( null, null )", null , FEELEvent.Severity.ERROR},
{ "ceiling( 1.5 )", new BigDecimal("2") , null},
{ "ceiling( -1.5 )", new BigDecimal("-1") , null},
{ "ceiling( null )", null , FEELEvent.Severity.ERROR},
{ "ceiling( n : 1.5 )", new BigDecimal("2") , null},
{ "ceiling( 1.555, 2 )", new BigDecimal("1.56") , null},
{ "ceiling( -1.56, 1 )", new BigDecimal("-1.5") , null},
{ "ceiling( 1.5, 6177 )", null , FEELEvent.Severity.ERROR},
{ "ceiling( 1.5, -6122 )", null , FEELEvent.Severity.ERROR},
{ "ceiling( 1.5, null )", null , FEELEvent.Severity.ERROR},
{ "ceiling( null, null )", null , FEELEvent.Severity.ERROR},
{ "abs( 10 )", new BigDecimal("10") , null},
{ "abs( -10 )", new BigDecimal("10") , null},
{ "abs( n: -10 )", new BigDecimal("10") , null},
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -73,18 +73,26 @@ private static Collection<Object[]> data() {
{ "round up(-5.5, 0) ", new BigDecimal("-6"), null },
{ "round up(1.121, 2) ", new BigDecimal("1.13"), null },
{ "round up(-1.126, 2) ", new BigDecimal("-1.13"), null },
{ "round up(1.126, 6177) ", null, FEELEvent.Severity.ERROR },
{ "round up(1.126, -6112) ", null, FEELEvent.Severity.ERROR },
{ "round down(5.5, 0)", new BigDecimal("5"), null },
{ "round down(-5.5, 0) ", new BigDecimal("-5"), null },
{ "round down(1.121, 2) ", new BigDecimal("1.12"), null },
{ "round down (-1.126, 2) ", new BigDecimal("-1.12"), null },
{ "round down(-1.126, 2) ", new BigDecimal("-1.12"), null },
{ "round down(1.126, 6177) ", null, FEELEvent.Severity.ERROR },
{ "round down(1.126, -6112) ", null, FEELEvent.Severity.ERROR },
{ "round half up(5.5, 0)", new BigDecimal("6"), null },
{ "round half up(-5.5, 0) ", new BigDecimal("-6"), null },
{ "round half up(1.121, 2) ", new BigDecimal("1.12"), null },
{ "round half up(-1.126, 2) ", new BigDecimal("-1.13"), null },
{ "round half up(1.126, 6177) ", null, FEELEvent.Severity.ERROR },
{ "round half up(1.126, -6112) ", null, FEELEvent.Severity.ERROR },
{ "round half down(5.5, 0)", new BigDecimal("5"), null },
{ "round half down(-5.5, 0) ", new BigDecimal("-5"), null },
{ "round half down(1.121, 2) ", new BigDecimal("1.12"), null },
{ "round half down(-1.126, 2) ", new BigDecimal("-1.13"), null },
{ "round half down(1.126, 6177) ", null, FEELEvent.Severity.ERROR },
{ "round half down(1.126, -6112) ", null, FEELEvent.Severity.ERROR },
{ "after( 1, 2 )", Boolean.FALSE, null },
{ "after( date(\"2018-08-15\"), date(\"2018-07-25\") )", Boolean.TRUE, null },
{ "after( date(\"2018-08-15\"), [date(\"2018-07-25\")..date(\"2018-08-10\")] )", Boolean.TRUE, null },
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,9 @@ void setUp() {
@Test
void invokeNull() {
FunctionTestUtil.assertResultError(ceilingFunction.invoke(null), InvalidParametersEvent.class);
}
FunctionTestUtil.assertResultError(ceilingFunction.invoke((BigDecimal) null, null), InvalidParametersEvent.class);
FunctionTestUtil.assertResultError(ceilingFunction.invoke(BigDecimal.ONE, null), InvalidParametersEvent.class);
FunctionTestUtil.assertResultError(ceilingFunction.invoke(null, BigDecimal.ONE), InvalidParametersEvent.class); }

@Test
void invokeZero() {
Expand All @@ -52,4 +54,10 @@ void invokePositive() {
void invokeNegative() {
FunctionTestUtil.assertResultBigDecimal(ceilingFunction.invoke(BigDecimal.valueOf(-10.2)), BigDecimal.valueOf(-10));
}

@Test
void invokeOutRangeScale() {
FunctionTestUtil.assertResultError(ceilingFunction.invoke(BigDecimal.valueOf(1.5), BigDecimal.valueOf(6177)), InvalidParametersEvent.class);
FunctionTestUtil.assertResultError(ceilingFunction.invoke(BigDecimal.valueOf(1.5), BigDecimal.valueOf(-6122)), InvalidParametersEvent.class);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -64,4 +64,10 @@ void invokeRoundingOdd() {
void invokeLargerScale() {
FunctionTestUtil.assertResult(decimalFunction.invoke(BigDecimal.valueOf(10.123456789), BigDecimal.valueOf(6)), BigDecimal.valueOf(10.123457));
}

@Test
void invokeOutRangeScale() {
FunctionTestUtil.assertResultError(decimalFunction.invoke(BigDecimal.valueOf(1.5), BigDecimal.valueOf(6177)), InvalidParametersEvent.class);
FunctionTestUtil.assertResultError(decimalFunction.invoke(BigDecimal.valueOf(1.5), BigDecimal.valueOf(-6122)), InvalidParametersEvent.class);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,9 @@ void setUp() {
@Test
void invokeNull() {
FunctionTestUtil.assertResultError(floorFunction.invoke(null), InvalidParametersEvent.class);
FunctionTestUtil.assertResultError(floorFunction.invoke((BigDecimal) null, null), InvalidParametersEvent.class);
FunctionTestUtil.assertResultError(floorFunction.invoke(BigDecimal.ONE, null), InvalidParametersEvent.class);
FunctionTestUtil.assertResultError(floorFunction.invoke(null, BigDecimal.ONE), InvalidParametersEvent.class);
}

@Test
Expand All @@ -53,4 +56,9 @@ void invokeNegative() {
FunctionTestUtil.assertResultBigDecimal(floorFunction.invoke(BigDecimal.valueOf(-10.2)), BigDecimal.valueOf(-11));
}

@Test
void invokeOutRangeScale() {
FunctionTestUtil.assertResultError(floorFunction.invoke(BigDecimal.valueOf(1.5), BigDecimal.valueOf(6177)), InvalidParametersEvent.class);
FunctionTestUtil.assertResultError(floorFunction.invoke(BigDecimal.valueOf(1.5), BigDecimal.valueOf(-6122)), InvalidParametersEvent.class);
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,79 @@
/**
* 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.kie.dmn.feel.runtime.functions.extended;

import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Test;
import org.kie.dmn.feel.runtime.events.InvalidParametersEvent;
import org.kie.dmn.feel.runtime.functions.FunctionTestUtil;

import java.math.BigDecimal;

class RoundDownFunctionTest {

private RoundDownFunction roundDownFunction;

@BeforeEach
void setUp() {
roundDownFunction = new RoundDownFunction();
}

@Test
void invokeNull() {
FunctionTestUtil.assertResultError(roundDownFunction.invoke(null), InvalidParametersEvent.class);
FunctionTestUtil.assertResultError(roundDownFunction.invoke((BigDecimal) null, null), InvalidParametersEvent.class);
FunctionTestUtil.assertResultError(roundDownFunction.invoke(BigDecimal.ONE, null), InvalidParametersEvent.class);
FunctionTestUtil.assertResultError(roundDownFunction.invoke(null, BigDecimal.ONE), InvalidParametersEvent.class);
}

@Test
void invokeRoundingUp() {
FunctionTestUtil.assertResult(roundDownFunction.invoke(BigDecimal.valueOf(10.27)), BigDecimal.valueOf(10));
FunctionTestUtil.assertResult(roundDownFunction.invoke(BigDecimal.valueOf(10.27), BigDecimal.ONE), BigDecimal.valueOf(10.2));
}

@Test
void invokeRoundingDown() {
FunctionTestUtil.assertResult(roundDownFunction.invoke(BigDecimal.valueOf(10.24)), BigDecimal.valueOf(10));
FunctionTestUtil.assertResult(roundDownFunction.invoke(BigDecimal.valueOf(10.24), BigDecimal.ONE), BigDecimal.valueOf(10.2));
}

@Test
void invokeRoundingEven() {
FunctionTestUtil.assertResult(roundDownFunction.invoke(BigDecimal.valueOf(10.25)), BigDecimal.valueOf(10));
FunctionTestUtil.assertResult(roundDownFunction.invoke(BigDecimal.valueOf(10.25), BigDecimal.ONE), BigDecimal.valueOf(10.2));
}

@Test
void invokeRoundingOdd() {
FunctionTestUtil.assertResult(roundDownFunction.invoke(BigDecimal.valueOf(10.35)), BigDecimal.valueOf(10));
FunctionTestUtil.assertResult(roundDownFunction.invoke(BigDecimal.valueOf(10.35), BigDecimal.ONE), BigDecimal.valueOf(10.3));
}

@Test
void invokeLargerScale() {
FunctionTestUtil.assertResult(roundDownFunction.invoke(BigDecimal.valueOf(10.123456789), BigDecimal.valueOf(6)), BigDecimal.valueOf(10.123456));
}

@Test
void invokeOutRangeScale() {
FunctionTestUtil.assertResultError(roundDownFunction.invoke(BigDecimal.valueOf(1.5), BigDecimal.valueOf(6177)), InvalidParametersEvent.class);
FunctionTestUtil.assertResultError(roundDownFunction.invoke(BigDecimal.valueOf(1.5), BigDecimal.valueOf(-6122)), InvalidParametersEvent.class);
}
}
Loading

0 comments on commit 0d89fa1

Please sign in to comment.