Repository: mvel/mvel (java)

Issue:
map == empty evaluates incorrectly in MVEL
**Summary**:
The `empty` keyword does not work correctly for `Map` in MVEL.
- `list == empty` correctly evaluates to `true`
- `map == empty` incorrectly evaluates to `false`, even when the map is actually empty.

**Reproducible Code**:
```java
import java.util.*;
import org.mvel2.MVEL;

public class MVELEmptyExample {
    public static void main(String[] args) {
        Map<String, Object> vars = new HashMap<>();
        vars.put("map", new HashMap<>());  // Empty map
        vars.put("list", new ArrayList<>()); // Empty list

        System.out.println("Is map empty? " + MVEL.eval("map == empty", vars)); // Expected: true, Actual: false
        System.out.println("Is list empty? " + MVEL.eval("list == empty", vars)); // Expected: true, Actual: true
    }
}
```
**Expected Behavior:**
map == empty should evaluate to true, just like list == empty.

**Actual Behavior**:
map == empty incorrectly evaluates to false, even when the map is empty.
However, map.isEmpty() works correctly.

**Version**:
MVEL Version: [2.5.2.Final]
Java Version: [21]

Pull request:
Fix issue #378 - add empty map check for blank literal
Fixes #378 

#### Motivation:
Refer #378 

#### Changes:

Added a check for empty map in BlankLiteral

Patch:
diff --git a/src/main/java/org/mvel2/compiler/BlankLiteral.java b/src/main/java/org/mvel2/compiler/BlankLiteral.java
index e381d882..736ca23d 100644
--- a/src/main/java/org/mvel2/compiler/BlankLiteral.java
+++ b/src/main/java/org/mvel2/compiler/BlankLiteral.java
@@ -20,6 +20,7 @@ package org.mvel2.compiler;
 
 import java.io.Serializable;
 import java.util.Collection;
+import java.util.Map;
 
 import static java.lang.String.valueOf;
 import static java.lang.reflect.Array.getLength;
@@ -47,6 +48,9 @@ public class BlankLiteral implements Serializable {
     if (obj instanceof Boolean) {
       return !(Boolean)obj;
     }
+    if (obj instanceof Map) {
+      return ((Map) obj).size() == 0;
+    }
     return false;
   }
 


Test patch:
diff --git a/src/test/java/org/mvel2/tests/core/CoreConfidenceTests.java b/src/test/java/org/mvel2/tests/core/CoreConfidenceTests.java
index 9e9ffd9b..413a2d9f 100644
--- a/src/test/java/org/mvel2/tests/core/CoreConfidenceTests.java
+++ b/src/test/java/org/mvel2/tests/core/CoreConfidenceTests.java
@@ -4587,6 +4587,34 @@ public class CoreConfidenceTests extends AbstractTest {
     assertEquals(false, MVEL.executeExpression(MVEL.compileExpression("nonEmptyString == empty", pctx), vars));
   }
 
+  public void testEmptyOperatorOnList() {
+    ParserConfiguration conf = new ParserConfiguration();
+    ParserContext pctx = new ParserContext( conf );
+    pctx.setStrictTypeEnforcement(true);
+    pctx.setStrongTyping(true);
+
+    pctx.addInput("list", ArrayList.class);
+    Map vars = new HashMap() {{
+      put("list", new ArrayList<>());
+    }};
+
+    assertEquals(true, MVEL.executeExpression(MVEL.compileExpression("list == empty", pctx), vars));
+  }
+
+  public void testEmptyOperatorOnMap() {
+    ParserConfiguration conf = new ParserConfiguration();
+    ParserContext pctx = new ParserContext( conf );
+    pctx.setStrictTypeEnforcement(true);
+    pctx.setStrongTyping(true);
+
+    pctx.addInput("map", HashMap.class);
+    Map vars = new HashMap() {{
+      put("map", new HashMap<>());
+    }};
+
+    assertEquals(true, MVEL.executeExpression(MVEL.compileExpression("map == empty", pctx), vars));
+  }
+
   public void testEmptyOperatorOnBoolean() {
     ParserConfiguration conf = new ParserConfiguration();
     ParserContext pctx = new ParserContext( conf );