This is an automated email from the ASF dual-hosted git repository.

tzimanyi pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/incubator-kie-drools.git


The following commit(s) were added to refs/heads/main by this push:
     new 30b4961cab [kie-issues#745] Handle lists and maps in method calls and 
constructors in drools-mvel-compiler (#5617)
30b4961cab is described below

commit 30b4961cabc8549426c54df8be9e9e96df69bdcb
Author: Tibor Zimányi <[email protected]>
AuthorDate: Fri Dec 15 15:05:17 2023 +0100

    [kie-issues#745] Handle lists and maps in method calls and constructors in 
drools-mvel-compiler (#5617)
---
 .../drools/mvelcompiler/MethodCallExprVisitor.java |  92 +++----
 .../java/org/drools/mvelcompiler/RHSPhase.java     | 116 ++++----
 .../org/drools/mvelcompiler/ast/ListExprT.java     |  47 ++++
 .../java/org/drools/mvelcompiler/ast/MapExprT.java |  53 ++++
 .../drools/mvelcompiler/ast/MethodCallExprT.java   |   2 +-
 .../mvelcompiler/util/MethodResolutionUtils.java   | 224 +++++++++++++++
 .../drools/mvelcompiler/util/VisitorContext.java   |  24 ++
 .../src/test/java/org/drools/Person.java           |  21 ++
 .../util/MethodResolutionUtilsTest.java            | 303 +++++++++++++++++++++
 .../mvel/parser/ast/visitor/DrlGenericVisitor.java |   8 +-
 .../integrationtests/MVELEmptyCollectionsTest.java | 167 ++++++++++++
 .../org/drools/mvel/integrationtests/MVELTest.java |   2 +
 .../mvel/integrationtests/facts/FactWithList.java  |   4 +
 .../facts/{FactWithList.java => FactWithMap.java}  |  26 +-
 .../{FactWithList.java => FactWithObject.java}     |  21 +-
 15 files changed, 972 insertions(+), 138 deletions(-)

diff --git 
a/drools-model/drools-mvel-compiler/src/main/java/org/drools/mvelcompiler/MethodCallExprVisitor.java
 
b/drools-model/drools-mvel-compiler/src/main/java/org/drools/mvelcompiler/MethodCallExprVisitor.java
index 4d0b38ed08..ab007da941 100644
--- 
a/drools-model/drools-mvel-compiler/src/main/java/org/drools/mvelcompiler/MethodCallExprVisitor.java
+++ 
b/drools-model/drools-mvel-compiler/src/main/java/org/drools/mvelcompiler/MethodCallExprVisitor.java
@@ -18,28 +18,32 @@
  */
 package org.drools.mvelcompiler;
 
-import java.lang.reflect.Method;
-import java.lang.reflect.Type;
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.List;
-import java.util.Optional;
-import java.util.stream.Collectors;
-
 import com.github.javaparser.ast.Node;
+import com.github.javaparser.ast.NodeList;
 import com.github.javaparser.ast.expr.Expression;
 import com.github.javaparser.ast.expr.MethodCallExpr;
-import org.drools.util.MethodUtils;
+import com.github.javaparser.utils.Pair;
+import org.drools.mvel.parser.ast.expr.ListCreationLiteralExpression;
+import org.drools.mvel.parser.ast.expr.MapCreationLiteralExpression;
 import org.drools.mvel.parser.ast.visitor.DrlGenericVisitor;
 import org.drools.mvelcompiler.ast.MethodCallExprT;
 import org.drools.mvelcompiler.ast.TypedExpression;
 import org.drools.mvelcompiler.context.DeclaredFunction;
 import org.drools.mvelcompiler.context.MvelCompilerContext;
-import org.drools.util.ClassUtils;
+import org.drools.mvelcompiler.util.MethodResolutionUtils;
+import org.drools.mvelcompiler.util.VisitorContext;
+
+import java.lang.reflect.Method;
+import java.lang.reflect.Type;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
+import java.util.Optional;
+import java.util.stream.Collectors;
 
 import static org.drools.util.StreamUtils.optionalToStream;
 
-public class MethodCallExprVisitor implements 
DrlGenericVisitor<TypedExpression, RHSPhase.Context> {
+public class MethodCallExprVisitor implements 
DrlGenericVisitor<TypedExpression, VisitorContext> {
 
     final RHSPhase parentVisitor;
     final MvelCompilerContext mvelCompilerContext;
@@ -50,24 +54,18 @@ public class MethodCallExprVisitor implements 
DrlGenericVisitor<TypedExpression,
     }
 
     @Override
-    public TypedExpression defaultMethod(Node n, RHSPhase.Context context) {
+    public TypedExpression defaultMethod(Node n, VisitorContext context) {
         return n.accept(parentVisitor, context);
     }
 
     @Override
-    public TypedExpression visit(MethodCallExpr n, RHSPhase.Context arg) {
-        Optional<TypedExpression> scope = n.getScope().map(s -> s.accept(this, 
arg));
-        TypedExpression name = n.getName().accept(this, new 
RHSPhase.Context(scope.orElse(null)));
-        final List<TypedExpression> arguments = new 
ArrayList<>(n.getArguments().size());
-        for (Expression child : n.getArguments()) {
-            TypedExpression a = child.accept(this, arg);
-            arguments.add(a);
-        }
-
-        Class<?>[] argumentsTypes = parametersType(arguments);
-
-        return parseMethodFromDeclaredFunction(n, arguments)
-                .orElseGet(() -> parseMethod(n, scope, name, arguments, 
argumentsTypes));
+    public TypedExpression visit(final MethodCallExpr n, final VisitorContext 
arg) {
+        final Optional<TypedExpression> scope = n.getScope().map(s -> 
s.accept(this, arg));
+        final TypedExpression name = n.getName().accept(this, new 
VisitorContext(scope.orElse(null)));
+        final Pair<List<TypedExpression>, List<Integer>> typedArgumentsResult =
+                
MethodResolutionUtils.getTypedArgumentsWithEmptyCollectionArgumentDetection(n.getArguments(),
 this, arg);
+        return parseMethodFromDeclaredFunction(n, typedArgumentsResult.a)
+                .orElseGet(() -> parseMethod(n, scope, name, 
typedArgumentsResult.a, typedArgumentsResult.b));
     }
 
     private Optional<TypedExpression> 
parseMethodFromDeclaredFunction(MethodCallExpr n, List<TypedExpression> 
arguments) {
@@ -89,43 +87,21 @@ public class MethodCallExprVisitor implements 
DrlGenericVisitor<TypedExpression,
                                         Optional<TypedExpression> scope,
                                         TypedExpression name,
                                         List<TypedExpression> arguments,
-                                        Class<?>[] argumentsType) {
-        Optional<Method> method = scope.flatMap(TypedExpression::getType)
-                .<Class<?>>map(ClassUtils::classFromType)
-                .map(scopeClazz -> MethodUtils.findMethod(scopeClazz, 
n.getNameAsString(), argumentsType));
-
-        if (method.isEmpty()) {
-            method = mvelCompilerContext.getRootPattern()
-                    .map(scopeClazz -> MethodUtils.findMethod(scopeClazz, 
n.getNameAsString(), argumentsType));
-            if(method.isPresent()) {
-                scope = mvelCompilerContext.createRootTypePrefix();
-            }
+                                        List<Integer> 
emptyCollectionArgumentIndexes) {
+        Pair<Optional<Method>, Optional<TypedExpression>> resolveMethodResult =
+                MethodResolutionUtils.resolveMethod(n, mvelCompilerContext, 
scope, arguments);
+        // This is a workaround for mvel empty list and map ambiguity, please 
see the description in getTypedArguments() method.
+        if (resolveMethodResult.a.isEmpty() && 
!emptyCollectionArgumentIndexes.isEmpty()) {
+            resolveMethodResult = 
MethodResolutionUtils.resolveMethodWithEmptyCollectionArguments(n, 
mvelCompilerContext, resolveMethodResult.b, arguments, 
emptyCollectionArgumentIndexes);
         }
-
-        if (method.isEmpty()) {
-            method = mvelCompilerContext.findStaticMethod(n.getNameAsString());
-        }
-
-        Optional<Method> finalMethod = method;
-        Optional<Type> methodReturnType =
-                name.getType()
-                        .map(Optional::of)
-                        .orElseGet(() -> 
finalMethod.map(Method::getReturnType));
-
-        List<Class<?>> actualArgumentType = optionalToStream(method)
+        final Optional<Method> finalMethod = resolveMethodResult.a;
+        final Optional<TypedExpression> finalScope = resolveMethodResult.b;
+        final Optional<Type> methodReturnType = name.getType().or(() -> 
finalMethod.map(Method::getReturnType));
+        final List<Class<?>> actualArgumentType = optionalToStream(finalMethod)
                 .flatMap((Method m) -> Arrays.stream(m.getParameterTypes()))
                 .collect(Collectors.toList());
 
-        return new MethodCallExprT(n.getName().asString(), scope, arguments,
+        return new MethodCallExprT(n.getName().asString(), finalScope, 
arguments,
                                    actualArgumentType, methodReturnType);
     }
-
-    private Class<?>[] parametersType(List<TypedExpression> arguments) {
-        return arguments.stream()
-                .map(TypedExpression::getType)
-                .filter(Optional::isPresent)
-                .map(Optional::get)
-                .map(ClassUtils::classFromType)
-                .toArray(Class[]::new);
-    }
 }
diff --git 
a/drools-model/drools-mvel-compiler/src/main/java/org/drools/mvelcompiler/RHSPhase.java
 
b/drools-model/drools-mvel-compiler/src/main/java/org/drools/mvelcompiler/RHSPhase.java
index d85917abc3..533fab5680 100644
--- 
a/drools-model/drools-mvel-compiler/src/main/java/org/drools/mvelcompiler/RHSPhase.java
+++ 
b/drools-model/drools-mvel-compiler/src/main/java/org/drools/mvelcompiler/RHSPhase.java
@@ -52,9 +52,13 @@ import com.github.javaparser.ast.expr.UnaryExpr;
 import com.github.javaparser.ast.expr.VariableDeclarationExpr;
 import com.github.javaparser.ast.stmt.ExpressionStmt;
 import com.github.javaparser.ast.stmt.YieldStmt;
+import com.github.javaparser.utils.Pair;
 import org.drools.mvel.parser.ast.expr.BigDecimalLiteralExpr;
 import org.drools.mvel.parser.ast.expr.BigIntegerLiteralExpr;
 import org.drools.mvel.parser.ast.expr.DrlNameExpr;
+import org.drools.mvel.parser.ast.expr.ListCreationLiteralExpression;
+import org.drools.mvel.parser.ast.expr.ListCreationLiteralExpressionElement;
+import org.drools.mvel.parser.ast.expr.MapCreationLiteralExpression;
 import org.drools.mvel.parser.ast.visitor.DrlGenericVisitor;
 import org.drools.mvelcompiler.ast.BigDecimalArithmeticExprT;
 import org.drools.mvelcompiler.ast.BigDecimalConvertedExprT;
@@ -69,7 +73,9 @@ import org.drools.mvelcompiler.ast.FieldAccessTExpr;
 import org.drools.mvelcompiler.ast.FieldToAccessorTExpr;
 import org.drools.mvelcompiler.ast.IntegerLiteralExpressionT;
 import org.drools.mvelcompiler.ast.ListAccessExprT;
+import org.drools.mvelcompiler.ast.ListExprT;
 import org.drools.mvelcompiler.ast.LongLiteralExpressionT;
+import org.drools.mvelcompiler.ast.MapExprT;
 import org.drools.mvelcompiler.ast.ObjectCreationExpressionT;
 import org.drools.mvelcompiler.ast.SimpleNameTExpr;
 import org.drools.mvelcompiler.ast.StringLiteralExpressionT;
@@ -77,6 +83,8 @@ import org.drools.mvelcompiler.ast.TypedExpression;
 import org.drools.mvelcompiler.ast.UnalteredTypedExpression;
 import org.drools.mvelcompiler.context.Declaration;
 import org.drools.mvelcompiler.context.MvelCompilerContext;
+import org.drools.mvelcompiler.util.MethodResolutionUtils;
+import org.drools.mvelcompiler.util.VisitorContext;
 import org.drools.util.ClassUtils;
 import org.drools.util.MethodUtils.NullType;
 
@@ -100,7 +108,7 @@ import static org.drools.util.ClassUtils.getAccessor;
  * might need to create new variables accordingly.
  *
  */
-public class RHSPhase implements DrlGenericVisitor<TypedExpression, 
RHSPhase.Context> {
+public class RHSPhase implements DrlGenericVisitor<TypedExpression, 
VisitorContext> {
 
     private static final Set<BinaryExpr.Operator> arithmeticOperators = Set.of(
             BinaryExpr.Operator.PLUS,
@@ -121,18 +129,6 @@ public class RHSPhase implements 
DrlGenericVisitor<TypedExpression, RHSPhase.Con
 
     private final MethodCallExprVisitor methodCallExprVisitor;
 
-    static class Context {
-        final Optional<TypedExpression> scope;
-
-        Context(TypedExpression scope) {
-            this.scope = ofNullable(scope);
-        }
-
-        Optional<Type> getScopeType() {
-            return scope.flatMap(TypedExpression::getType);
-        }
-    }
-
     private final MvelCompilerContext mvelCompilerContext;
 
     RHSPhase(MvelCompilerContext mvelCompilerContext) {
@@ -141,19 +137,19 @@ public class RHSPhase implements 
DrlGenericVisitor<TypedExpression, RHSPhase.Con
     }
 
     public TypedExpression invoke(Node statement) {
-        Context ctx = new Context(null);
+        VisitorContext ctx = new VisitorContext(null);
 
         return statement.accept(this, ctx);
     }
 
     @Override
-    public TypedExpression visit(DrlNameExpr n, Context arg) {
+    public TypedExpression visit(DrlNameExpr n, VisitorContext arg) {
         return n.getName().accept(this, arg);
     }
 
     @Override
-    public TypedExpression visit(SimpleName n, Context arg) {
-        if (arg.scope.isEmpty()) { // first node
+    public TypedExpression visit(SimpleName n, VisitorContext arg) {
+        if (arg.getScope().isEmpty()) { // first node
             return simpleNameAsFirstNode(n);
         } else {
             return simpleNameAsField(n, arg);
@@ -161,17 +157,17 @@ public class RHSPhase implements 
DrlGenericVisitor<TypedExpression, RHSPhase.Con
     }
 
     @Override
-    public TypedExpression visit(YieldStmt n, Context arg) {
+    public TypedExpression visit(YieldStmt n, VisitorContext arg) {
         return null;
     }
 
     @Override
-    public TypedExpression visit(TextBlockLiteralExpr n, Context arg) {
+    public TypedExpression visit(TextBlockLiteralExpr n, VisitorContext arg) {
         return new UnalteredTypedExpression(n, String.class);
     }
 
     @Override
-    public TypedExpression visit(PatternExpr n, Context arg) {
+    public TypedExpression visit(PatternExpr n, VisitorContext arg) {
         return null;
     }
 
@@ -184,15 +180,15 @@ public class RHSPhase implements 
DrlGenericVisitor<TypedExpression, RHSPhase.Con
                 .orElseGet(() -> new UnalteredTypedExpression(n));
     }
 
-    private TypedExpression simpleNameAsField(SimpleName n, Context arg) {
+    private TypedExpression simpleNameAsField(SimpleName n, VisitorContext 
arg) {
         return asPropertyAccessor(n, arg)
                 .map(Optional::of)
                 .orElseGet(() -> asFieldAccessTExpr(n, arg))
                 .orElseGet(() -> new UnalteredTypedExpression(n));
     }
 
-    private Optional<TypedExpression> asFieldAccessTExpr(SimpleName n, Context 
arg) {
-        Optional<TypedExpression> lastTypedExpression = arg.scope;
+    private Optional<TypedExpression> asFieldAccessTExpr(SimpleName n, 
VisitorContext arg) {
+        Optional<TypedExpression> lastTypedExpression = arg.getScope();
         Optional<Type> scopeType = arg.getScopeType();
 
         Optional<Field> fieldType = scopeType.flatMap(te -> {
@@ -217,8 +213,8 @@ public class RHSPhase implements 
DrlGenericVisitor<TypedExpression, RHSPhase.Con
         return enumType.map(clazz -> new SimpleNameTExpr(n.asString(), clazz));
     }
 
-    private Optional<TypedExpression> asPropertyAccessor(SimpleName n, Context 
arg) {
-        Optional<TypedExpression> lastTypedExpression = arg.scope;
+    private Optional<TypedExpression> asPropertyAccessor(SimpleName n, 
VisitorContext arg) {
+        Optional<TypedExpression> lastTypedExpression = arg.getScope();
 
         Optional<Type> scopeType = 
lastTypedExpression.filter(ListAccessExprT.class::isInstance)
                                                       
.map(ListAccessExprT.class::cast)
@@ -238,18 +234,18 @@ public class RHSPhase implements 
DrlGenericVisitor<TypedExpression, RHSPhase.Con
     }
 
     @Override
-    public TypedExpression visit(FieldAccessExpr n, Context arg) {
+    public TypedExpression visit(FieldAccessExpr n, VisitorContext arg) {
         TypedExpression scope = n.getScope().accept(this, arg);
-        return n.getName().accept(this, new Context(scope));
+        return n.getName().accept(this, new VisitorContext(scope));
     }
 
     @Override
-    public TypedExpression visit(MethodCallExpr n, Context arg) {
+    public TypedExpression visit(MethodCallExpr n, VisitorContext arg) {
         return n.accept(methodCallExprVisitor, arg);
     }
 
     @Override
-    public TypedExpression visit(BinaryExpr n, Context arg) {
+    public TypedExpression visit(BinaryExpr n, VisitorContext arg) {
         TypedExpression left = n.getLeft().accept(this, arg);
         TypedExpression right = n.getRight().accept(this, arg);
         return withPossiblyBigDecimalConversion(left, right, n.getOperator());
@@ -303,78 +299,82 @@ public class RHSPhase implements 
DrlGenericVisitor<TypedExpression, RHSPhase.Con
     }
 
     @Override
-    public TypedExpression visit(ExpressionStmt n, Context arg) {
+    public TypedExpression visit(ExpressionStmt n, VisitorContext arg) {
         return n.getExpression().accept(this, arg);
     }
 
     @Override
-    public TypedExpression visit(VariableDeclarationExpr n, Context arg) {
+    public TypedExpression visit(VariableDeclarationExpr n, VisitorContext 
arg) {
         return n.getVariables().iterator().next().accept(this, arg);
     }
 
     @Override
-    public TypedExpression visit(VariableDeclarator n, Context arg) {
+    public TypedExpression visit(VariableDeclarator n, VisitorContext arg) {
         Optional<TypedExpression> initExpression = n.getInitializer().map(i -> 
i.accept(this, arg));
         return initExpression.orElse(null);
     }
 
     @Override
-    public TypedExpression visit(AssignExpr n, Context arg) {
+    public TypedExpression visit(AssignExpr n, VisitorContext arg) {
         return n.getValue().accept(this, arg);
     }
 
     @Override
-    public TypedExpression visit(StringLiteralExpr n, Context arg) {
+    public TypedExpression visit(StringLiteralExpr n, VisitorContext arg) {
         return new StringLiteralExpressionT(n);
     }
 
     @Override
-    public TypedExpression visit(IntegerLiteralExpr n, Context arg) {
+    public TypedExpression visit(IntegerLiteralExpr n, VisitorContext arg) {
         return new IntegerLiteralExpressionT(n);
     }
 
     @Override
-    public TypedExpression visit(DoubleLiteralExpr n, Context arg) {
+    public TypedExpression visit(DoubleLiteralExpr n, VisitorContext arg) {
         return new DoubleLiteralExpressionT(n);
     }
 
     @Override
-    public TypedExpression visit(CharLiteralExpr n, Context arg) {
+    public TypedExpression visit(CharLiteralExpr n, VisitorContext arg) {
         return new CharacterLiteralExpressionT(n);
     }
 
     @Override
-    public TypedExpression visit(LongLiteralExpr n, Context arg) {
+    public TypedExpression visit(LongLiteralExpr n, VisitorContext arg) {
         return new LongLiteralExpressionT(n);
     }
 
     @Override
-    public TypedExpression visit(BooleanLiteralExpr n, Context arg) {
+    public TypedExpression visit(BooleanLiteralExpr n, VisitorContext arg) {
         return new BooleanLiteralExpressionT(n);
     }
 
     @Override
-    public TypedExpression defaultMethod(Node n, Context context) {
+    public TypedExpression defaultMethod(Node n, VisitorContext context) {
         return new UnalteredTypedExpression(n);
     }
 
     @Override
-    public TypedExpression visit(ObjectCreationExpr n, Context arg) {
-        List<TypedExpression> constructorArguments = new ArrayList<>();
-        for(Expression e : n.getArguments()) {
-            TypedExpression compiledArgument = e.accept(this, arg);
-            constructorArguments.add(compiledArgument);
+    public TypedExpression visit(ObjectCreationExpr n, VisitorContext arg) {
+        final Class<?> type = resolveType(n.getType());
+        final Pair<List<TypedExpression>, List<Integer>> typedArgumentsResult =
+                
MethodResolutionUtils.getTypedArgumentsWithEmptyCollectionArgumentDetection(n.getArguments(),
 this, arg);
+        if (!typedArgumentsResult.b.isEmpty()) {
+            return new ObjectCreationExpressionT(
+                    
MethodResolutionUtils.coerceCorrectConstructorArguments(type, 
typedArgumentsResult.a, typedArgumentsResult.b),
+                    type);
+        } else {
+            return new ObjectCreationExpressionT(typedArgumentsResult.a, type);
         }
-        return new ObjectCreationExpressionT(constructorArguments, 
resolveType(n.getType()));
     }
 
     @Override
-    public TypedExpression visit(NullLiteralExpr n, Context arg) {
+    public TypedExpression visit(NullLiteralExpr n, VisitorContext arg) {
         return new UnalteredTypedExpression(n, NullType.class);
     }
 
     @Override
-    public TypedExpression visit(ArrayAccessExpr n, Context arg) {
+    public TypedExpression visit(ArrayAccessExpr n, VisitorContext arg) {
         TypedExpression name = n.getName().accept(this, arg);
 
         Optional<Type> type = name.getType();
@@ -385,28 +385,28 @@ public class RHSPhase implements 
DrlGenericVisitor<TypedExpression, RHSPhase.Con
     }
 
     @Override
-    public TypedExpression visit(EnclosedExpr n, Context arg) {
+    public TypedExpression visit(EnclosedExpr n, VisitorContext arg) {
         return n.getInner().accept(this, arg);
     }
 
     @Override
-    public TypedExpression visit(CastExpr n, Context arg) {
+    public TypedExpression visit(CastExpr n, VisitorContext arg) {
         TypedExpression innerExpr = n.getExpression().accept(this, arg);
         return new CastExprT(innerExpr, resolveType(n.getType()));
     }
 
     @Override
-    public TypedExpression visit(BigDecimalLiteralExpr n, Context arg) {
+    public TypedExpression visit(BigDecimalLiteralExpr n, VisitorContext arg) {
         return new BigDecimalConvertedExprT(new StringLiteralExpressionT(new 
StringLiteralExpr(n.getValue())));
     }
 
     @Override
-    public TypedExpression visit(BigIntegerLiteralExpr n, Context arg) {
+    public TypedExpression visit(BigIntegerLiteralExpr n, VisitorContext arg) {
         return new BigIntegerConvertedExprT(new StringLiteralExpressionT(new 
StringLiteralExpr(n.getValue())));
     }
 
     @Override
-    public TypedExpression visit(UnaryExpr n, Context arg) {
+    public TypedExpression visit(UnaryExpr n, VisitorContext arg) {
         Expression innerExpr = n.getExpression();
         UnaryExpr.Operator operator = n.getOperator();
         if (innerExpr instanceof BigDecimalLiteralExpr && operator == 
UnaryExpr.Operator.MINUS) {
@@ -418,6 +418,16 @@ public class RHSPhase implements 
DrlGenericVisitor<TypedExpression, RHSPhase.Con
         }
     }
 
+    @Override
+    public TypedExpression visit(ListCreationLiteralExpression n, 
VisitorContext arg) {
+        return new ListExprT(n);
+    }
+
+    @Override
+    public TypedExpression visit(MapCreationLiteralExpression n, 
VisitorContext arg) {
+        return new MapExprT(n);
+    }
+
     private Class<?> resolveType(com.github.javaparser.ast.type.Type type) {
         return mvelCompilerContext.resolveType(type.asString());
     }
diff --git 
a/drools-model/drools-mvel-compiler/src/main/java/org/drools/mvelcompiler/ast/ListExprT.java
 
b/drools-model/drools-mvel-compiler/src/main/java/org/drools/mvelcompiler/ast/ListExprT.java
new file mode 100644
index 0000000000..3b9d8a56f3
--- /dev/null
+++ 
b/drools-model/drools-mvel-compiler/src/main/java/org/drools/mvelcompiler/ast/ListExprT.java
@@ -0,0 +1,47 @@
+package org.drools.mvelcompiler.ast;
+
+import com.github.javaparser.ast.Node;
+import com.github.javaparser.ast.NodeList;
+import com.github.javaparser.ast.expr.Expression;
+import com.github.javaparser.ast.expr.MethodCallExpr;
+import com.github.javaparser.ast.expr.NameExpr;
+import org.drools.mvel.parser.ast.expr.ListCreationLiteralExpression;
+import org.drools.mvel.parser.ast.expr.ListCreationLiteralExpressionElement;
+
+import java.lang.reflect.Type;
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.List;
+import java.util.Optional;
+
+import static com.github.javaparser.ast.NodeList.toNodeList;
+
+public class ListExprT implements TypedExpression {
+
+    private final ListCreationLiteralExpression listExpression;
+
+    public ListExprT(final ListCreationLiteralExpression listExpression) {
+        this.listExpression = listExpression;
+    }
+
+    @Override
+    public Optional<Type> getType() {
+        return Optional.of(List.class);
+    }
+
+    @Override
+    public Node toJavaExpression() {
+        if (listExpression.getExpressions() == null || 
listExpression.getExpressions().isEmpty()) {
+            return new MethodCallExpr(new 
NameExpr(Collections.class.getCanonicalName()), "emptyList");
+        } else {
+            return new MethodCallExpr(new 
NameExpr(List.class.getCanonicalName()), "of", 
getValueExpressionsFromListElements(listExpression.getExpressions()));
+        }
+    }
+
+    private NodeList<Expression> getValueExpressionsFromListElements(final 
NodeList<Expression> listItems) {
+        return listItems.stream()
+                .filter(listItem -> listItem instanceof 
ListCreationLiteralExpressionElement)
+                .map(listItem -> ((ListCreationLiteralExpressionElement) 
listItem).getValue())
+                .collect(toNodeList());
+    }
+}
diff --git 
a/drools-model/drools-mvel-compiler/src/main/java/org/drools/mvelcompiler/ast/MapExprT.java
 
b/drools-model/drools-mvel-compiler/src/main/java/org/drools/mvelcompiler/ast/MapExprT.java
new file mode 100644
index 0000000000..8291905fab
--- /dev/null
+++ 
b/drools-model/drools-mvel-compiler/src/main/java/org/drools/mvelcompiler/ast/MapExprT.java
@@ -0,0 +1,53 @@
+package org.drools.mvelcompiler.ast;
+
+import com.github.javaparser.ast.Node;
+import com.github.javaparser.ast.NodeList;
+import com.github.javaparser.ast.expr.Expression;
+import com.github.javaparser.ast.expr.MethodCallExpr;
+import com.github.javaparser.ast.expr.NameExpr;
+import org.drools.mvel.parser.ast.expr.ListCreationLiteralExpressionElement;
+import org.drools.mvel.parser.ast.expr.MapCreationLiteralExpression;
+import 
org.drools.mvel.parser.ast.expr.MapCreationLiteralExpressionKeyValuePair;
+
+import java.lang.reflect.Type;
+import java.util.Collections;
+import java.util.List;
+import java.util.Map;
+import java.util.Optional;
+
+import static com.github.javaparser.ast.NodeList.toNodeList;
+
+public class MapExprT implements TypedExpression {
+
+    private final MapCreationLiteralExpression mapExpression;
+
+    public MapExprT(final MapCreationLiteralExpression mapExpression) {
+        this.mapExpression = mapExpression;
+    }
+
+    @Override
+    public Optional<Type> getType() {
+        return Optional.of(Map.class);
+    }
+
+    @Override
+    public Node toJavaExpression() {
+        if (mapExpression.getExpressions() == null || 
mapExpression.getExpressions().isEmpty()) {
+            return new MethodCallExpr(new 
NameExpr(Collections.class.getCanonicalName()), "emptyMap");
+        } else {
+            return new MethodCallExpr(new 
NameExpr(Map.class.getCanonicalName()), "ofEntries", 
getMapEntryExpressions(mapExpression.getExpressions()));
+        }
+    }
+
+    private NodeList<Expression> getMapEntryExpressions(final 
NodeList<Expression> mapEntries) {
+        return mapEntries.stream()
+                .filter(mapEntry -> mapEntry instanceof 
MapCreationLiteralExpressionKeyValuePair)
+                .map(mapEntry ->
+                    new MethodCallExpr(
+                            new NameExpr(Map.class.getCanonicalName()),
+                            "entry",
+                            
NodeList.nodeList(((MapCreationLiteralExpressionKeyValuePair) 
mapEntry).getKey(),
+                                    
((MapCreationLiteralExpressionKeyValuePair) mapEntry).getValue()))
+                ).collect(toNodeList());
+    }
+}
diff --git 
a/drools-model/drools-mvel-compiler/src/main/java/org/drools/mvelcompiler/ast/MethodCallExprT.java
 
b/drools-model/drools-mvel-compiler/src/main/java/org/drools/mvelcompiler/ast/MethodCallExprT.java
index 688b031621..5d3337edc5 100644
--- 
a/drools-model/drools-mvel-compiler/src/main/java/org/drools/mvelcompiler/ast/MethodCallExprT.java
+++ 
b/drools-model/drools-mvel-compiler/src/main/java/org/drools/mvelcompiler/ast/MethodCallExprT.java
@@ -63,7 +63,7 @@ public class MethodCallExprT implements TypedExpression {
 
         List<Expression> methodArguments;
         // MVEL forces a to string on each String value in map
-        if(PUT_CALL.equals(name) && arguments.size() == 2) {
+        if (PUT_CALL.equals(name) && arguments.size() == 2) {
             methodArguments = coercedMapArguments();
         } else {
             methodArguments = toJavaExpressionArgument();
diff --git 
a/drools-model/drools-mvel-compiler/src/main/java/org/drools/mvelcompiler/util/MethodResolutionUtils.java
 
b/drools-model/drools-mvel-compiler/src/main/java/org/drools/mvelcompiler/util/MethodResolutionUtils.java
new file mode 100644
index 0000000000..7c648db28c
--- /dev/null
+++ 
b/drools-model/drools-mvel-compiler/src/main/java/org/drools/mvelcompiler/util/MethodResolutionUtils.java
@@ -0,0 +1,224 @@
+package org.drools.mvelcompiler.util;
+
+import com.github.javaparser.ast.NodeList;
+import com.github.javaparser.ast.expr.Expression;
+import com.github.javaparser.ast.expr.MethodCallExpr;
+import com.github.javaparser.utils.Pair;
+import org.drools.mvel.parser.ast.expr.ListCreationLiteralExpression;
+import org.drools.mvel.parser.ast.expr.MapCreationLiteralExpression;
+import org.drools.mvel.parser.ast.visitor.DrlGenericVisitor;
+import org.drools.mvelcompiler.ast.ListExprT;
+import org.drools.mvelcompiler.ast.MapExprT;
+import org.drools.mvelcompiler.ast.TypedExpression;
+import org.drools.mvelcompiler.context.MvelCompilerContext;
+import org.drools.util.ClassUtils;
+import org.drools.util.MethodUtils;
+
+import java.lang.reflect.Constructor;
+import java.lang.reflect.Method;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Objects;
+import java.util.Optional;
+
+public final class MethodResolutionUtils {
+
+    private MethodResolutionUtils() {
+        // It is forbidden to create instances of util classes.
+    }
+
+    /**
+     *  [] is ambiguous in mvel - it can represent an empty list or an empty 
map.
+     *    It cannot be distinguished on a language level, so this is a 
workaround:
+     *    - When there [] written in a rule, mvel parser parses it as an empty 
list.
+     *    - The only possible way with constructors, when there is such 
parameter, is try to guess the correct parameter type when trying to read the 
constructor from a class.
+     *    - This uses all indexes of empty lists or empty maps in the 
constructor parameters.
+     *    - When not possible to resolve the constructor with a list or map 
parameter, it will try to resolve a constructor with the other collection 
parameter.
+     *    - This happens for all empty list and map parameters resolved by the 
parser, until a proper constructor is found.
+     */
+    public static List<TypedExpression> coerceCorrectConstructorArguments(
+            final Class<?> type,
+            List<TypedExpression> arguments,
+            List<Integer> emptyCollectionArgumentsIndexes) {
+        Objects.requireNonNull(type, "Type parameter cannot be null as the 
method searches constructors from that class!");
+        Objects.requireNonNull(arguments, "Arguments parameter cannot be null! 
Use an empty list instance if needed instead.");
+        Objects.requireNonNull(emptyCollectionArgumentsIndexes, 
"EmptyListArgumentIndexes parameter cannot be null! Use an empty list instance 
if needed instead.");
+        if (emptyCollectionArgumentsIndexes.size() > arguments.size()) {
+            throw new IllegalArgumentException("There cannot be more empty 
collection arguments than all arguments! emptyCollectionArgumentsIndexes 
parameter has more items than arguments parameter. "
+                    + "(" + emptyCollectionArgumentsIndexes.size() + " > " + 
arguments.size() + ")");
+        }
+        // Rather work only with the argumentsType and when a method is 
resolved, flip the arguments list based on it.
+        final List<TypedExpression> coercedArgumentsTypesList = new 
ArrayList<>(arguments);
+        Constructor<?> constructor = resolveConstructor(type, 
coercedArgumentsTypesList);
+        if (constructor != null) {
+            return coercedArgumentsTypesList;
+        } else {
+            // This needs to go through all possible combinations.
+            final int indexesListSize = emptyCollectionArgumentsIndexes.size();
+            for (int numberOfProcessedIndexes = 0; numberOfProcessedIndexes < 
indexesListSize; numberOfProcessedIndexes++) {
+                for (int indexOfEmptyListIndex = numberOfProcessedIndexes; 
indexOfEmptyListIndex < indexesListSize; indexOfEmptyListIndex++) {
+                    
switchCollectionClassInArgumentsByIndex(coercedArgumentsTypesList, 
emptyCollectionArgumentsIndexes.get(indexOfEmptyListIndex));
+                    constructor = resolveConstructor(type, 
coercedArgumentsTypesList);
+                    if (constructor != null) {
+                        return coercedArgumentsTypesList;
+                    }
+                    
switchCollectionClassInArgumentsByIndex(coercedArgumentsTypesList, 
emptyCollectionArgumentsIndexes.get(indexOfEmptyListIndex));
+                }
+                
switchCollectionClassInArgumentsByIndex(coercedArgumentsTypesList, 
emptyCollectionArgumentsIndexes.get(numberOfProcessedIndexes));
+            }
+            // No constructor found, return the original arguments.
+            return arguments;
+        }
+    }
+
+    private static Constructor<?> resolveConstructor(final Class<?> type, 
List<TypedExpression> arguments) {
+        Constructor<?> constructor;
+        try {
+            constructor = type.getConstructor(parametersType(arguments));
+        } catch (NoSuchMethodException ex) {
+            constructor = null;
+        }
+        return constructor;
+    }
+
+    /**
+     *  [] is ambiguous in mvel - it can represent an empty list or an empty 
map.
+     *    It cannot be distinguished on a language level, so this is a 
workaround:
+     *    - When there [] written in a rule, mvel parser parses it as an empty 
list.
+     *    - The only possible way with methods, when there is such parameter, 
is try to guess the correct parameter type when trying to read the method from 
a class.
+     *    - This uses all indexes of empty lists or empty maps in the method 
parameters.
+     *    - When not possible to resolve the method with a list or map 
parameter, it will try to resolve a method with the other collection parameter.
+     *    - This happens for all empty list and map parameters resolved by the 
parser, until a proper method is found.
+     */
+    public static Pair<Optional<Method>, Optional<TypedExpression>> 
resolveMethodWithEmptyCollectionArguments(
+            final MethodCallExpr methodExpression,
+            final MvelCompilerContext mvelCompilerContext,
+            final Optional<TypedExpression> scope,
+            List<TypedExpression> arguments,
+            List<Integer> emptyCollectionArgumentsIndexes) {
+        Objects.requireNonNull(methodExpression, "MethodExpression parameter 
cannot be null as the method searches methods based on this expression!");
+        Objects.requireNonNull(mvelCompilerContext, "MvelCompilerContext 
parameter cannot be null!");
+        Objects.requireNonNull(arguments, "Arguments parameter cannot be null! 
Use an empty list instance if needed instead.");
+        Objects.requireNonNull(emptyCollectionArgumentsIndexes, 
"EmptyListArgumentIndexes parameter cannot be null! Use an empty list instance 
if needed instead.");
+        if (emptyCollectionArgumentsIndexes.size() > arguments.size()) {
+            throw new IllegalArgumentException("There cannot be more empty 
collection arguments than all arguments! emptyCollectionArgumentsIndexes 
parameter has more items than arguments parameter. "
+                    + "(" + emptyCollectionArgumentsIndexes.size() + " > " + 
arguments.size() + ")");
+        } else {
+            final List<TypedExpression> coercedArgumentsTypesList = new 
ArrayList<>(arguments);
+            Pair<Optional<Method>, Optional<TypedExpression>> 
resolveMethodResult =
+                    MethodResolutionUtils.resolveMethod(methodExpression, 
mvelCompilerContext, scope, coercedArgumentsTypesList);
+            if (resolveMethodResult.a.isPresent()) {
+                return resolveMethodResult;
+            } else {
+                // Rather work only with the argumentsType and when a method 
is resolved, flip the arguments list based on it.
+                // This needs to go through all possible combinations.
+                final int indexesListSize = 
emptyCollectionArgumentsIndexes.size();
+                for (int numberOfProcessedIndexes = 0; 
numberOfProcessedIndexes < indexesListSize; numberOfProcessedIndexes++) {
+                    for (int indexOfEmptyListIndex = numberOfProcessedIndexes; 
indexOfEmptyListIndex < indexesListSize; indexOfEmptyListIndex++) {
+                        
switchCollectionClassInArgumentsByIndex(coercedArgumentsTypesList, 
emptyCollectionArgumentsIndexes.get(indexOfEmptyListIndex));
+                        resolveMethodResult =
+                                
MethodResolutionUtils.resolveMethod(methodExpression, mvelCompilerContext, 
scope, coercedArgumentsTypesList);
+                        if (resolveMethodResult.a.isPresent()) {
+                            
modifyArgumentsBasedOnCoercedCollectionArguments(arguments, 
coercedArgumentsTypesList);
+                            return resolveMethodResult;
+                        }
+                        
switchCollectionClassInArgumentsByIndex(coercedArgumentsTypesList, 
emptyCollectionArgumentsIndexes.get(indexOfEmptyListIndex));
+                    }
+                    
switchCollectionClassInArgumentsByIndex(coercedArgumentsTypesList, 
emptyCollectionArgumentsIndexes.get(numberOfProcessedIndexes));
+                }
+                // No method found, return empty.
+                return new Pair<>(Optional.empty(), scope);
+            }
+        }
+    }
+
+    public static Pair<Optional<Method>, Optional<TypedExpression>> 
resolveMethod(
+            final MethodCallExpr methodExpression,
+            final MvelCompilerContext mvelCompilerContext,
+            final Optional<TypedExpression> scope,
+            final List<TypedExpression> arguments) {
+        Objects.requireNonNull(methodExpression, "MethodExpression parameter 
cannot be null as the method searches methods based on this expression!");
+        Objects.requireNonNull(mvelCompilerContext, "MvelCompilerContext 
parameter cannot be null!");
+        Objects.requireNonNull(arguments, "Arguments parameter cannot be null! 
Use an empty list instance if needed instead.");
+        final Class<?>[] argumentsTypesClasses = parametersType(arguments);
+        Optional<TypedExpression> finalScope = scope;
+        Optional<Method> resolvedMethod;
+        resolvedMethod = finalScope.flatMap(TypedExpression::getType)
+                .<Class<?>>map(ClassUtils::classFromType)
+                .map(scopeClazz -> MethodUtils.findMethod(scopeClazz, 
methodExpression.getNameAsString(), argumentsTypesClasses));
+
+        if (resolvedMethod.isEmpty()) {
+            resolvedMethod = mvelCompilerContext.getRootPattern()
+                    .map(scopeClazz -> MethodUtils.findMethod(scopeClazz, 
methodExpression.getNameAsString(), argumentsTypesClasses));
+            if (resolvedMethod.isPresent()) {
+                finalScope = mvelCompilerContext.createRootTypePrefix();
+            }
+        }
+
+        if (resolvedMethod.isEmpty()) {
+            resolvedMethod = 
mvelCompilerContext.findStaticMethod(methodExpression.getNameAsString());
+        }
+        return new Pair<>(resolvedMethod, finalScope);
+    }
+
+    public static Pair<List<TypedExpression>, List<Integer>> 
getTypedArgumentsWithEmptyCollectionArgumentDetection(
+            final NodeList<Expression> arguments,
+            final DrlGenericVisitor<TypedExpression, VisitorContext> 
drlGenericVisitor,
+            final VisitorContext arg) {
+        final List<TypedExpression> typedArguments = new ArrayList<>();
+        final List<Integer> emptyCollectionArgumentIndexes = new ArrayList<>();
+        int argumentIndex = 0;
+        for (Expression child : arguments) {
+            TypedExpression a = child.accept(drlGenericVisitor, arg);
+            typedArguments.add(a);
+            if (child instanceof ListCreationLiteralExpression
+                    && (((ListCreationLiteralExpression) 
child).getExpressions() == null
+                    || ((ListCreationLiteralExpression) 
child).getExpressions().isEmpty())) {
+                emptyCollectionArgumentIndexes.add(argumentIndex);
+            } else if (child instanceof MapCreationLiteralExpression
+                    && (((MapCreationLiteralExpression) 
child).getExpressions() == null
+                    || ((MapCreationLiteralExpression) 
child).getExpressions().isEmpty())) {
+                emptyCollectionArgumentIndexes.add(argumentIndex);
+            }
+            argumentIndex++;
+        }
+        return new Pair<>(typedArguments, emptyCollectionArgumentIndexes);
+    }
+
+    private static Class<?>[] parametersType(List<TypedExpression> arguments) {
+        return arguments.stream()
+                .map(TypedExpression::getType)
+                .filter(Optional::isPresent)
+                .map(Optional::get)
+                .map(ClassUtils::classFromType)
+                .toArray(Class[]::new);
+    }
+
+    private static void switchCollectionClassInArgumentsByIndex(final 
List<TypedExpression> argumentsTypesList, final int index) {
+        final Class<?> argumentTypeClass = 
argumentsTypesList.get(index).getClass();
+        if (argumentTypeClass.equals(ListExprT.class) || 
argumentTypeClass.equals(MapExprT.class)) {
+            if (argumentTypeClass.equals(ListExprT.class)) {
+                argumentsTypesList.set(index, new MapExprT(new 
MapCreationLiteralExpression(null, NodeList.nodeList())));
+            } else {
+                argumentsTypesList.set(index, new ListExprT(new 
ListCreationLiteralExpression(null, NodeList.nodeList())));
+            }
+        } else {
+            throw new IllegalArgumentException("Argument at index " + index + 
" from the list of arguments (argumentsTypesList) is not a collection type, but 
" + argumentTypeClass.getCanonicalName() + " type!");
+        }
+    }
+
+    private static void modifyArgumentsBasedOnCoercedCollectionArguments(final 
List<TypedExpression> arguments, final List<TypedExpression> 
coercedCollectionArguments) {
+        int index = 0;
+        for (TypedExpression coercedArgument : coercedCollectionArguments) {
+            if 
(!coercedArgument.getClass().equals(arguments.get(index).getClass())) {
+                // Originally the resolved type was a List, so if it is 
different, it is a Map.
+                if (coercedArgument.getClass().equals(MapExprT.class)) {
+                    arguments.set(index, new MapExprT(new 
MapCreationLiteralExpression(null, NodeList.nodeList())));
+                } else {
+                    arguments.set(index, new ListExprT(new 
ListCreationLiteralExpression(null, NodeList.nodeList())));
+                }
+            }
+            index++;
+        }
+    }
+}
diff --git 
a/drools-model/drools-mvel-compiler/src/main/java/org/drools/mvelcompiler/util/VisitorContext.java
 
b/drools-model/drools-mvel-compiler/src/main/java/org/drools/mvelcompiler/util/VisitorContext.java
new file mode 100644
index 0000000000..4945e669d1
--- /dev/null
+++ 
b/drools-model/drools-mvel-compiler/src/main/java/org/drools/mvelcompiler/util/VisitorContext.java
@@ -0,0 +1,24 @@
+package org.drools.mvelcompiler.util;
+
+import org.drools.mvelcompiler.ast.TypedExpression;
+
+import java.lang.reflect.Type;
+import java.util.Optional;
+
+import static java.util.Optional.ofNullable;
+
+public class VisitorContext {
+    private final Optional<TypedExpression> scope;
+
+    public VisitorContext(final TypedExpression scope) {
+        this.scope = ofNullable(scope);
+    }
+
+    public Optional<Type> getScopeType() {
+        return scope.flatMap(TypedExpression::getType);
+    }
+
+    public Optional<TypedExpression> getScope() {
+        return scope;
+    }
+}
diff --git 
a/drools-model/drools-mvel-compiler/src/test/java/org/drools/Person.java 
b/drools-model/drools-mvel-compiler/src/test/java/org/drools/Person.java
index e99d6887c1..00b60f8877 100644
--- a/drools-model/drools-mvel-compiler/src/test/java/org/drools/Person.java
+++ b/drools-model/drools-mvel-compiler/src/test/java/org/drools/Person.java
@@ -53,6 +53,9 @@ public class Person {
 
     private Integer ageAsInteger;
 
+    public Person() {
+    }
+
     public Person(String name) {
         this(name, null);
     }
@@ -67,6 +70,19 @@ public class Person {
         this.gender = gender;
     }
 
+    public Person(List<Address> addresses) {
+        this.addresses = addresses;
+    }
+
+    public Person(Map<String, String> items) {
+        this.items = items;
+    }
+
+    public Person(List<Address> addresses, Map<String, String> items) {
+        this.addresses = addresses;
+        this.items = items;
+    }
+
     public String getName() {
         return name;
     }
@@ -204,4 +220,9 @@ public class Person {
     public void setFloatBoxed(Float floatBoxed) {
         this.floatBoxed = floatBoxed;
     }
+
+    public void setAddressesAndItems(List<Address> addresses, Map<String, 
String> items) {
+        this.addresses = addresses;
+        this.items = items;
+    }
 }
diff --git 
a/drools-model/drools-mvel-compiler/src/test/java/org/drools/mvelcompiler/util/MethodResolutionUtilsTest.java
 
b/drools-model/drools-mvel-compiler/src/test/java/org/drools/mvelcompiler/util/MethodResolutionUtilsTest.java
new file mode 100644
index 0000000000..c449cfe5c1
--- /dev/null
+++ 
b/drools-model/drools-mvel-compiler/src/test/java/org/drools/mvelcompiler/util/MethodResolutionUtilsTest.java
@@ -0,0 +1,303 @@
+package org.drools.mvelcompiler.util;
+
+import com.github.javaparser.ast.NodeList;
+import com.github.javaparser.ast.expr.IntegerLiteralExpr;
+import com.github.javaparser.ast.expr.MethodCallExpr;
+import com.github.javaparser.ast.expr.StringLiteralExpr;
+import com.github.javaparser.utils.Pair;
+import org.assertj.core.api.Assertions;
+import org.drools.Person;
+import org.drools.mvel.parser.ast.expr.ListCreationLiteralExpression;
+import org.drools.mvel.parser.ast.expr.MapCreationLiteralExpression;
+import org.drools.mvelcompiler.ast.IntegerLiteralExpressionT;
+import org.drools.mvelcompiler.ast.ListExprT;
+import org.drools.mvelcompiler.ast.MapExprT;
+import org.drools.mvelcompiler.ast.ObjectCreationExpressionT;
+import org.drools.mvelcompiler.ast.StringLiteralExpressionT;
+import org.drools.mvelcompiler.ast.TypedExpression;
+import org.drools.mvelcompiler.context.MvelCompilerContext;
+import org.junit.Test;
+
+import java.lang.reflect.Method;
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.List;
+import java.util.Optional;
+import java.util.stream.Collectors;
+
+public class MethodResolutionUtilsTest {
+
+    @Test
+    public void coerceCorrectConstructorArgumentsTypeIsNull() {
+        Assertions.assertThatThrownBy(
+                        () -> 
MethodResolutionUtils.coerceCorrectConstructorArguments(
+                                null,
+                                null,
+                                null))
+                .isInstanceOf(NullPointerException.class);
+    }
+
+    @Test
+    public void coerceCorrectConstructorArgumentsArgumentsAreNull() {
+        Assertions.assertThatThrownBy(
+                        () -> 
MethodResolutionUtils.coerceCorrectConstructorArguments(
+                                Person.class,
+                                null,
+                                null))
+                .isInstanceOf(NullPointerException.class);
+    }
+
+    @Test
+    public void 
coerceCorrectConstructorArgumentsEmptyCollectionIndexesAreNull() {
+        Assertions.assertThatThrownBy(
+                        () -> 
MethodResolutionUtils.coerceCorrectConstructorArguments(
+                                Person.class,
+                                Collections.emptyList(),
+                                null))
+                .isInstanceOf(NullPointerException.class);
+    }
+
+    @Test
+    public void 
coerceCorrectConstructorArgumentsEmptyCollectionIndexesBiggerThanArguments() {
+        Assertions.assertThatThrownBy(
+                        () -> 
MethodResolutionUtils.coerceCorrectConstructorArguments(
+                                Person.class,
+                                Collections.emptyList(),
+                                List.of(1, 2, 4)))
+                .isInstanceOf(IllegalArgumentException.class);
+    }
+
+    @Test
+    public void coerceCorrectConstructorArgumentsNoCollectionArguments() {
+        final List<TypedExpression> arguments = List.of(new 
IntegerLiteralExpressionT(new IntegerLiteralExpr("12")));
+        final List<TypedExpression> coercedArguments = 
MethodResolutionUtils.coerceCorrectConstructorArguments(
+                Person.class, arguments, Collections.emptyList());
+        
Assertions.assertThat(coercedArguments).containsExactlyElementsOf(arguments);
+    }
+
+    @Test
+    public void coerceCorrectConstructorArgumentsIsNotCollectionAtIndex() {
+        final List<TypedExpression> arguments = List.of(new 
IntegerLiteralExpressionT(new IntegerLiteralExpr("12")));
+        Assertions.assertThatThrownBy(
+                        () -> 
MethodResolutionUtils.coerceCorrectConstructorArguments(
+                                Person.class,
+                                arguments,
+                                List.of(0)))
+                .isInstanceOf(IllegalArgumentException.class);
+    }
+
+    @Test
+    public void coerceCorrectConstructorArgumentsList() {
+        final List<TypedExpression> arguments = List.of(new ListExprT(new 
ListCreationLiteralExpression(null, NodeList.nodeList())));
+        final List<TypedExpression> coercedArguments = 
MethodResolutionUtils.coerceCorrectConstructorArguments(
+                Person.class, arguments, List.of(0));
+        
Assertions.assertThat(coercedArguments).containsExactlyElementsOf(arguments);
+    }
+
+    @Test
+    public void coerceCorrectConstructorArgumentsCoerceMap() {
+        final List<TypedExpression> arguments =
+                List.of(
+                        new ListExprT(new ListCreationLiteralExpression(null, 
NodeList.nodeList())),
+                        new ListExprT(new ListCreationLiteralExpression(null, 
NodeList.nodeList())));
+        final List<Class<?>> expectedArgumentClasses = 
List.of(ListExprT.class, MapExprT.class);
+        final List<TypedExpression> coercedArguments = 
MethodResolutionUtils.coerceCorrectConstructorArguments(
+                Person.class, arguments, List.of(1));
+        Assertions.assertThat(getTypedExpressionsClasses(coercedArguments))
+                .containsExactlyElementsOf(expectedArgumentClasses);
+    }
+
+    @Test
+    public void coerceCorrectConstructorArgumentsCoerceList() {
+        final List<TypedExpression> arguments =
+                List.of(
+                        new MapExprT(new MapCreationLiteralExpression(null, 
NodeList.nodeList())),
+                        new MapExprT(new MapCreationLiteralExpression(null, 
NodeList.nodeList())));
+        final List<Class<?>> expectedArgumentClasses = 
List.of(ListExprT.class, MapExprT.class);
+        final List<TypedExpression> coercedArguments = 
MethodResolutionUtils.coerceCorrectConstructorArguments(
+                Person.class, arguments, List.of(0));
+        Assertions.assertThat(getTypedExpressionsClasses(coercedArguments))
+                .containsExactlyElementsOf(expectedArgumentClasses);
+    }
+
+    @Test
+    public void coerceCorrectConstructorArgumentsCoerceListAndMap() {
+        final List<TypedExpression> arguments =
+                List.of(
+                        new MapExprT(new MapCreationLiteralExpression(null, 
NodeList.nodeList())),
+                        new ListExprT(new ListCreationLiteralExpression(null, 
NodeList.nodeList())));
+        final List<Class<?>> expectedArgumentClasses = 
List.of(ListExprT.class, MapExprT.class);
+        final List<TypedExpression> coercedArguments = 
MethodResolutionUtils.coerceCorrectConstructorArguments(
+                Person.class, arguments, List.of(0, 1));
+        Assertions.assertThat(getTypedExpressionsClasses(coercedArguments))
+                .containsExactlyElementsOf(expectedArgumentClasses);
+    }
+
+    @Test
+    public void 
resolveMethodWithEmptyCollectionArgumentsMethodExpressionIsNull() {
+        Assertions.assertThatThrownBy(
+                        () -> 
MethodResolutionUtils.resolveMethodWithEmptyCollectionArguments(
+                                null,
+                                null,
+                                Optional.empty(),
+                                null,
+                                null))
+                .isInstanceOf(NullPointerException.class);
+    }
+
+    @Test
+    public void 
resolveMethodWithEmptyCollectionArgumentsMvelCompilerContextIsNull() {
+        Assertions.assertThatThrownBy(
+                        () -> 
MethodResolutionUtils.resolveMethodWithEmptyCollectionArguments(
+                                new MethodCallExpr(),
+                                null,
+                                Optional.empty(),
+                                null,
+                                null))
+                .isInstanceOf(NullPointerException.class);
+    }
+
+    @Test
+    public void resolveMethodWithEmptyCollectionArgumentsArgumentsAreNull() {
+        Assertions.assertThatThrownBy(
+                        () -> 
MethodResolutionUtils.resolveMethodWithEmptyCollectionArguments(
+                                new MethodCallExpr(),
+                                new MvelCompilerContext(null),
+                                Optional.empty(),
+                                null,
+                                null))
+                .isInstanceOf(NullPointerException.class);
+    }
+
+    @Test
+    public void 
resolveMethodWithEmptyCollectionArgumentsEmptyCollectionIndexesAreNull() {
+        Assertions.assertThatThrownBy(
+                        () -> 
MethodResolutionUtils.resolveMethodWithEmptyCollectionArguments(
+                                new MethodCallExpr(),
+                                new MvelCompilerContext(null),
+                                Optional.empty(),
+                                Collections.emptyList(),
+                                null))
+                .isInstanceOf(NullPointerException.class);
+    }
+
+    @Test
+    public void 
resolveMethodWithEmptyCollectionArgumentsEmptyCollectionIndexesBiggerThanArguments()
 {
+        Assertions.assertThatThrownBy(
+                        () -> 
MethodResolutionUtils.resolveMethodWithEmptyCollectionArguments(
+                                new MethodCallExpr(),
+                                new MvelCompilerContext(null),
+                                Optional.empty(),
+                                Collections.emptyList(),
+                                List.of(1, 2, 4)))
+                .isInstanceOf(IllegalArgumentException.class);
+    }
+
+    @Test
+    public void 
resolveMethodWithEmptyCollectionArgumentsNoCollectionArguments() {
+        final MethodCallExpr methodExpression = new 
MethodCallExpr("setIntegerBoxed", new IntegerLiteralExpr("12"));
+        final List<TypedExpression> arguments = List.of(new 
IntegerLiteralExpressionT(new IntegerLiteralExpr("12")));
+        final List<TypedExpression> expectedArguments = new 
ArrayList<>(arguments);
+        final TypedExpression scope = new ObjectCreationExpressionT(arguments, 
Person.class);
+        final Pair<Optional<Method>, Optional<TypedExpression>> 
resolvedMethodResult =
+                
MethodResolutionUtils.resolveMethodWithEmptyCollectionArguments(
+                        methodExpression,
+                        new MvelCompilerContext(null),
+                        Optional.of(scope),
+                        arguments,
+                        Collections.emptyList());
+        Assertions.assertThat(resolvedMethodResult.a).isPresent();
+        
Assertions.assertThat(arguments).containsExactlyElementsOf(expectedArguments);
+    }
+
+    @Test
+    public void 
resolveMethodWithEmptyCollectionArgumentsIsNotCollectionAtIndex() {
+        final MethodCallExpr methodExpression = new 
MethodCallExpr("setIntegerBoxed", new IntegerLiteralExpr("12"));
+        final List<TypedExpression> arguments = List.of(new 
StringLiteralExpressionT(new StringLiteralExpr("12")));
+        final TypedExpression scope = new ObjectCreationExpressionT(arguments, 
Person.class);
+        Assertions.assertThatThrownBy(
+                        () -> 
MethodResolutionUtils.resolveMethodWithEmptyCollectionArguments(
+                                methodExpression,
+                                new MvelCompilerContext(null),
+                                Optional.of(scope),
+                                arguments,
+                                List.of(0)))
+                .isInstanceOf(IllegalArgumentException.class);
+    }
+
+    @Test
+    public void resolveMethodWithEmptyCollectionArguments() {
+        final MethodCallExpr methodExpression = new 
MethodCallExpr("setAddresses", new ListCreationLiteralExpression(null, 
NodeList.nodeList()));
+        final List<TypedExpression> arguments = List.of(new ListExprT(new 
ListCreationLiteralExpression(null, NodeList.nodeList())));
+        final TypedExpression scope = new ObjectCreationExpressionT(arguments, 
Person.class);
+        final Pair<Optional<Method>, Optional<TypedExpression>> 
resolvedMethodResult =
+                
MethodResolutionUtils.resolveMethodWithEmptyCollectionArguments(
+                        methodExpression,
+                        new MvelCompilerContext(null),
+                        Optional.of(scope),
+                        arguments,
+                        List.of(0));
+        Assertions.assertThat(resolvedMethodResult.a).isPresent();
+        Assertions.assertThat(getTypedExpressionsClasses(arguments))
+                .containsExactlyElementsOf(List.of(ListExprT.class));
+    }
+
+    @Test
+    public void resolveMethodWithEmptyCollectionArgumentsCoerceMap() {
+        final MethodCallExpr methodExpression = new MethodCallExpr("setItems", 
new MapCreationLiteralExpression(null, NodeList.nodeList()));
+        final List<TypedExpression> arguments = new ArrayList<>();
+        arguments.add(new ListExprT(new ListCreationLiteralExpression(null, 
NodeList.nodeList())));
+        final TypedExpression scope = new 
ObjectCreationExpressionT(Collections.emptyList(), Person.class);
+        final Pair<Optional<Method>, Optional<TypedExpression>> 
resolvedMethodResult =
+                
MethodResolutionUtils.resolveMethodWithEmptyCollectionArguments(
+                        methodExpression,
+                        new MvelCompilerContext(null),
+                        Optional.of(scope),
+                        arguments,
+                        List.of(0));
+        Assertions.assertThat(resolvedMethodResult.a).isPresent();
+        Assertions.assertThat(getTypedExpressionsClasses(arguments))
+                .containsExactlyElementsOf(List.of(MapExprT.class));
+    }
+
+    @Test
+    public void resolveMethodWithEmptyCollectionArgumentsCoerceList() {
+        final MethodCallExpr methodExpression = new 
MethodCallExpr("setAddresses", new MapCreationLiteralExpression(null, 
NodeList.nodeList()));
+        final List<TypedExpression> arguments = new ArrayList<>();
+        arguments.add(new MapExprT(new MapCreationLiteralExpression(null, 
NodeList.nodeList())));
+        final TypedExpression scope = new 
ObjectCreationExpressionT(Collections.emptyList(), Person.class);
+        final Pair<Optional<Method>, Optional<TypedExpression>> 
resolvedMethodResult =
+                
MethodResolutionUtils.resolveMethodWithEmptyCollectionArguments(
+                        methodExpression,
+                        new MvelCompilerContext(null),
+                        Optional.of(scope),
+                        arguments,
+                        List.of(0));
+        Assertions.assertThat(resolvedMethodResult.a).isPresent();
+        Assertions.assertThat(getTypedExpressionsClasses(arguments))
+                .containsExactlyElementsOf(List.of(ListExprT.class));
+    }
+
+    @Test
+    public void resolveMethodWithEmptyCollectionArgumentsCoerceListAndMap() {
+        final MethodCallExpr methodExpression = new 
MethodCallExpr("setAddressesAndItems", new MapCreationLiteralExpression(null, 
NodeList.nodeList()));
+        final List<TypedExpression> arguments = new ArrayList<>();
+        arguments.add(new MapExprT(new MapCreationLiteralExpression(null, 
NodeList.nodeList())));
+        arguments.add(new ListExprT(new ListCreationLiteralExpression(null, 
NodeList.nodeList())));
+        final TypedExpression scope = new 
ObjectCreationExpressionT(Collections.emptyList(), Person.class);
+        final Pair<Optional<Method>, Optional<TypedExpression>> 
resolvedMethodResult =
+                
MethodResolutionUtils.resolveMethodWithEmptyCollectionArguments(
+                        methodExpression,
+                        new MvelCompilerContext(null),
+                        Optional.of(scope),
+                        arguments,
+                        List.of(0, 1));
+        Assertions.assertThat(resolvedMethodResult.a).isPresent();
+        Assertions.assertThat(getTypedExpressionsClasses(arguments))
+                .containsExactlyElementsOf(List.of(ListExprT.class, 
MapExprT.class));
+    }
+
+    private List<Class<?>> getTypedExpressionsClasses(List<TypedExpression> 
typedExpressions) {
+        return 
typedExpressions.stream().map(TypedExpression::getClass).collect(Collectors.toList());
+    }
+}
\ No newline at end of file
diff --git 
a/drools-model/drools-mvel-parser/src/main/java/org/drools/mvel/parser/ast/visitor/DrlGenericVisitor.java
 
b/drools-model/drools-mvel-parser/src/main/java/org/drools/mvel/parser/ast/visitor/DrlGenericVisitor.java
index 8bfa2fa91e..e22961cf30 100644
--- 
a/drools-model/drools-mvel-parser/src/main/java/org/drools/mvel/parser/ast/visitor/DrlGenericVisitor.java
+++ 
b/drools-model/drools-mvel-parser/src/main/java/org/drools/mvel/parser/ast/visitor/DrlGenericVisitor.java
@@ -639,11 +639,15 @@ public interface DrlGenericVisitor<R, A> extends 
GenericVisitor<R,A> {
         return defaultMethod(n, arg);
     }
 
-    default R visit(MapCreationLiteralExpression n, A arg) { return null; }
+    default R visit(MapCreationLiteralExpression n, A arg) {
+        return defaultMethod(n, arg);
+    }
 
     default R visit(MapCreationLiteralExpressionKeyValuePair n, A arg) { 
return null; }
 
-    default R visit(ListCreationLiteralExpression n, A arg) { return null; }
+    default R visit(ListCreationLiteralExpression n, A arg) {
+        return defaultMethod(n, arg);
+    }
 
     default R visit(ListCreationLiteralExpressionElement n, A arg) { return 
null; }
 
diff --git 
a/drools-test-coverage/test-compiler-integration/src/test/java/org/drools/mvel/integrationtests/MVELEmptyCollectionsTest.java
 
b/drools-test-coverage/test-compiler-integration/src/test/java/org/drools/mvel/integrationtests/MVELEmptyCollectionsTest.java
new file mode 100644
index 0000000000..aa884f989b
--- /dev/null
+++ 
b/drools-test-coverage/test-compiler-integration/src/test/java/org/drools/mvel/integrationtests/MVELEmptyCollectionsTest.java
@@ -0,0 +1,167 @@
+/**
+ * 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.drools.mvel.integrationtests;
+
+import org.drools.base.base.ClassObjectType;
+import org.drools.base.rule.constraint.AlphaNodeFieldConstraint;
+import org.drools.core.reteoo.AlphaNode;
+import org.drools.core.reteoo.ObjectTypeNode;
+import org.drools.kiesession.rulebase.InternalKnowledgeBase;
+import org.drools.mvel.MVELConstraint;
+import org.drools.mvel.accessors.ClassFieldReader;
+import org.drools.mvel.compiler.Address;
+import org.drools.mvel.compiler.Cheese;
+import org.drools.mvel.compiler.Cheesery;
+import org.drools.mvel.compiler.FactA;
+import org.drools.mvel.compiler.Person;
+import org.drools.mvel.compiler.TestEnum;
+import org.drools.mvel.expr.MVELDebugHandler;
+import org.drools.mvel.extractors.MVELObjectClassFieldReader;
+import org.drools.mvel.integrationtests.facts.FactWithList;
+import org.drools.mvel.integrationtests.facts.FactWithMap;
+import org.drools.mvel.integrationtests.facts.FactWithObject;
+import org.drools.testcoverage.common.util.KieBaseTestConfiguration;
+import org.drools.testcoverage.common.util.KieBaseUtil;
+import org.drools.testcoverage.common.util.KieUtil;
+import org.drools.testcoverage.common.util.TestParametersUtil;
+import org.drools.util.DateUtils;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.junit.runners.Parameterized;
+import org.kie.api.KieBase;
+import org.kie.api.builder.KieBuilder;
+import org.kie.api.builder.Message;
+import org.kie.api.definition.type.FactType;
+import org.kie.api.runtime.KieSession;
+import org.kie.api.runtime.StatelessKieSession;
+import org.mvel2.MVEL;
+import org.mvel2.ParserContext;
+
+import java.io.Serializable;
+import java.math.BigDecimal;
+import java.math.BigInteger;
+import java.math.MathContext;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Collection;
+import java.util.Date;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import static org.assertj.core.api.Assertions.assertThat;
+import static org.assertj.core.api.Assertions.fail;
+
+@RunWith(Parameterized.class)
+public class MVELEmptyCollectionsTest {
+
+    private final KieBaseTestConfiguration kieBaseTestConfiguration;
+
+    public MVELEmptyCollectionsTest(final KieBaseTestConfiguration 
kieBaseTestConfiguration) {
+        this.kieBaseTestConfiguration = kieBaseTestConfiguration;
+    }
+
+    @Parameterized.Parameters(name = "KieBase type={0}")
+    public static Collection<Object[]> getParameters() {
+        // Some of these fail without executable model, so test only 
executable model.
+        return TestParametersUtil.getKieBaseCloudOnlyExecModelConfiguration();
+    }
+
+    @Test
+    public void testEmptyListAsMethodParameter() {
+        final String drl =
+                "import " + FactWithList.class.getCanonicalName() + "; \n" +
+                "rule \"test\"\n" +
+                "dialect \"mvel\" \n" +
+                "when\n" +
+                "    $p: FactWithList()\n" +
+                "then\n" +
+                "    $p.setItems([]); \n" +
+                "end";
+
+        KieBase kbase = KieBaseUtil.getKieBaseFromKieModuleFromDrl("test", 
kieBaseTestConfiguration, drl);
+        KieSession ksession = kbase.newKieSession();
+        final FactWithList f = new FactWithList("testString");
+        ksession.insert(f);
+        assertThat(ksession.fireAllRules()).isEqualTo(1);
+        assertThat(f.getItems()).hasSize(0);
+    }
+
+    @Test
+    public void testEmptyListAsConstructorParameter() {
+        final String drl =
+                "import " + FactWithList.class.getCanonicalName() + "; \n" +
+                        "import " + FactWithObject.class.getCanonicalName() + 
"; \n" +
+                        "rule \"test\"\n" +
+                        "dialect \"mvel\" \n" +
+                        "when\n" +
+                        "    $p: FactWithObject()\n" +
+                        "then\n" +
+                        "    $p.setObjectValue(new FactWithList([])); \n" +
+                        "end";
+
+        KieBase kbase = KieBaseUtil.getKieBaseFromKieModuleFromDrl("test", 
kieBaseTestConfiguration, drl);
+        KieSession ksession = kbase.newKieSession();
+        final FactWithObject f = new FactWithObject(null);
+        ksession.insert(f);
+        assertThat(ksession.fireAllRules()).isEqualTo(1);
+        assertThat(f.getObjectValue()).isInstanceOf(FactWithList.class);
+    }
+
+    @Test
+    public void testEmptyMapAsMethodParameter() {
+        final String drl =
+                "import " + FactWithMap.class.getCanonicalName() + "; \n" +
+                        "rule \"test\"\n" +
+                        "dialect \"mvel\" \n" +
+                        "when\n" +
+                        "    $p: FactWithMap()\n" +
+                        "then\n" +
+                        "    $p.setItemsMap([]); \n" +
+                        "end";
+
+        KieBase kbase = KieBaseUtil.getKieBaseFromKieModuleFromDrl("test", 
kieBaseTestConfiguration, drl);
+        KieSession ksession = kbase.newKieSession();
+        final FactWithMap f = new FactWithMap(1, "testString");
+        ksession.insert(f);
+        assertThat(ksession.fireAllRules()).isEqualTo(1);
+        assertThat(f.getItemsMap()).hasSize(0);
+    }
+
+    @Test
+    public void testEmptyMapAsConstructorParameter() {
+        final String drl =
+                "import " + FactWithMap.class.getCanonicalName() + "; \n" +
+                        "import " + FactWithObject.class.getCanonicalName() + 
"; \n" +
+                        "rule \"test\"\n" +
+                        "dialect \"mvel\" \n" +
+                        "when\n" +
+                        "    $p: FactWithObject()\n" +
+                        "then\n" +
+                        "    $p.setObjectValue(new FactWithMap([])); \n" +
+                        "end";
+
+        KieBase kbase = KieBaseUtil.getKieBaseFromKieModuleFromDrl("test", 
kieBaseTestConfiguration, drl);
+        KieSession ksession = kbase.newKieSession();
+        final FactWithObject f = new FactWithObject(null);
+        ksession.insert(f);
+        assertThat(ksession.fireAllRules()).isEqualTo(1);
+        
assertThat(f.getObjectValue()).isNotNull().isInstanceOf(FactWithMap.class);
+    }
+}
diff --git 
a/drools-test-coverage/test-compiler-integration/src/test/java/org/drools/mvel/integrationtests/MVELTest.java
 
b/drools-test-coverage/test-compiler-integration/src/test/java/org/drools/mvel/integrationtests/MVELTest.java
index e878e4c65a..a7c5565919 100644
--- 
a/drools-test-coverage/test-compiler-integration/src/test/java/org/drools/mvel/integrationtests/MVELTest.java
+++ 
b/drools-test-coverage/test-compiler-integration/src/test/java/org/drools/mvel/integrationtests/MVELTest.java
@@ -36,6 +36,8 @@ import org.drools.base.base.ClassObjectType;
 import org.drools.core.reteoo.AlphaNode;
 import org.drools.core.reteoo.ObjectTypeNode;
 import org.drools.base.rule.constraint.AlphaNodeFieldConstraint;
+import org.drools.mvel.compiler.PersonHolder;
+import org.drools.mvel.integrationtests.facts.FactWithList;
 import org.drools.util.DateUtils;
 import org.drools.mvel.MVELConstraint;
 import org.drools.mvel.compiler.Address;
diff --git 
a/drools-test-coverage/test-compiler-integration/src/test/java/org/drools/mvel/integrationtests/facts/FactWithList.java
 
b/drools-test-coverage/test-compiler-integration/src/test/java/org/drools/mvel/integrationtests/facts/FactWithList.java
index a4ab4c647a..eff913cc64 100644
--- 
a/drools-test-coverage/test-compiler-integration/src/test/java/org/drools/mvel/integrationtests/facts/FactWithList.java
+++ 
b/drools-test-coverage/test-compiler-integration/src/test/java/org/drools/mvel/integrationtests/facts/FactWithList.java
@@ -31,6 +31,10 @@ public class FactWithList {
         this.items.add(factString);
     }
 
+    public FactWithList(final List<String> items) {
+        this.items = items;
+    }
+
     public List<String> getItems() {
         return items;
     }
diff --git 
a/drools-test-coverage/test-compiler-integration/src/test/java/org/drools/mvel/integrationtests/facts/FactWithList.java
 
b/drools-test-coverage/test-compiler-integration/src/test/java/org/drools/mvel/integrationtests/facts/FactWithMap.java
similarity index 62%
copy from 
drools-test-coverage/test-compiler-integration/src/test/java/org/drools/mvel/integrationtests/facts/FactWithList.java
copy to 
drools-test-coverage/test-compiler-integration/src/test/java/org/drools/mvel/integrationtests/facts/FactWithMap.java
index a4ab4c647a..e92423e8b2 100644
--- 
a/drools-test-coverage/test-compiler-integration/src/test/java/org/drools/mvel/integrationtests/facts/FactWithList.java
+++ 
b/drools-test-coverage/test-compiler-integration/src/test/java/org/drools/mvel/integrationtests/facts/FactWithMap.java
@@ -18,24 +18,28 @@
  */
 package org.drools.mvel.integrationtests.facts;
 
-import java.util.ArrayList;
-import java.util.List;
+import java.util.HashMap;
+import java.util.Map;
 
-public class FactWithList {
+public class FactWithMap {
 
-    private List<String> items = new ArrayList<>();
+    private Map<Integer, String> itemsMap = new HashMap<>();
 
-    public FactWithList() { }
+    public FactWithMap() { }
 
-    public FactWithList(final String factString) {
-        this.items.add(factString);
+    public FactWithMap(final Integer key, final String value) {
+        this.itemsMap.put(key, value);
     }
 
-    public List<String> getItems() {
-        return items;
+    public FactWithMap(final Map<Integer, String> itemsMap) {
+        this.itemsMap = itemsMap;
     }
 
-    public void setItems(List<String> items) {
-        this.items = items;
+    public Map<Integer, String> getItemsMap() {
+        return itemsMap;
+    }
+
+    public void setItemsMap(Map<Integer, String> itemsMap) {
+        this.itemsMap = itemsMap;
     }
 }
diff --git 
a/drools-test-coverage/test-compiler-integration/src/test/java/org/drools/mvel/integrationtests/facts/FactWithList.java
 
b/drools-test-coverage/test-compiler-integration/src/test/java/org/drools/mvel/integrationtests/facts/FactWithObject.java
similarity index 69%
copy from 
drools-test-coverage/test-compiler-integration/src/test/java/org/drools/mvel/integrationtests/facts/FactWithList.java
copy to 
drools-test-coverage/test-compiler-integration/src/test/java/org/drools/mvel/integrationtests/facts/FactWithObject.java
index a4ab4c647a..7a468e1662 100644
--- 
a/drools-test-coverage/test-compiler-integration/src/test/java/org/drools/mvel/integrationtests/facts/FactWithList.java
+++ 
b/drools-test-coverage/test-compiler-integration/src/test/java/org/drools/mvel/integrationtests/facts/FactWithObject.java
@@ -18,24 +18,19 @@
  */
 package org.drools.mvel.integrationtests.facts;
 
-import java.util.ArrayList;
-import java.util.List;
+public class FactWithObject {
 
-public class FactWithList {
+    private Object objectValue;
 
-    private List<String> items = new ArrayList<>();
-
-    public FactWithList() { }
-
-    public FactWithList(final String factString) {
-        this.items.add(factString);
+    public FactWithObject(final Object objectValue) {
+        this.objectValue = objectValue;
     }
 
-    public List<String> getItems() {
-        return items;
+    public Object getObjectValue() {
+        return objectValue;
     }
 
-    public void setItems(List<String> items) {
-        this.items = items;
+    public void setObjectValue(final Object objectValue) {
+        this.objectValue = objectValue;
     }
 }


---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]

Reply via email to