Skip to content

CREATE JAVA ACTION: AS $$ block generates uncompilable Java (imports in method body) #127

@engalar

Description

@engalar

Problem

CREATE JAVA ACTION ... AS $$ ... $$ generates Java files that fail to compile, because the $$ code is placed verbatim into the executeAction() method body (BEGIN USER CODE region) without handling imports.

Per Mendix official docs:

Only the following code will be retained when actions are regenerated:

  • the import list
  • the code between BEGIN USER CODE and END USER CODE
  • the code between BEGIN EXTRA CODE and END EXTRA CODE

Imports are a separate preserved region at file top level, but mxcli has no mechanism to populate it.

Reproduction

CREATE JAVA ACTION MyModule.ReadCSV(File: System.FileDocument) RETURNS String
AS $$
IContext context = this.getContext();
InputStream is = Core.getFileDocumentContent(context, File.getMendixObject());
BufferedReader reader = new BufferedReader(new InputStreamReader(is, "UTF-8"));
String line = reader.readLine();
reader.close();
return line;
$$;

Generated Java file only has default imports:

import com.mendix.systemwideinterfaces.core.IContext;
import com.mendix.systemwideinterfaces.core.UserAction;
import com.mendix.systemwideinterfaces.core.IMendixObject;

Core, InputStream, BufferedReader, InputStreamReader are all unresolved → compilation error.

What happens when AI agents write the code

AI agents naturally prepend import statements inside $$:

AS $$
import com.mendix.core.Core;
import java.io.*;
// actual code...
$$;

These end up inside the method body, which is illegal Java:

public String executeAction() throws Exception {
    // BEGIN USER CODE
    import com.mendix.core.Core;     // ← syntax error
    import java.io.*;                 // ← syntax error
    // ...
}

This happened to all 3 Java Actions in our project (CreateOrdersFromCSV, ParseCSVFile, ReadResourceFile).

Root cause

AS $$ only writes to BEGIN USER CODE. The generated .java file has no mechanism to receive additional imports.

Suggested fixes

Option A: Strip import lines from $$ and move to file header (minimal, backward-compatible)

If $$ block contains lines matching ^\s*import\s+[\w.*]+;\s*$, extract them and place in the import section instead of the method body. This makes AI-generated code "just work".

Option B: Add IMPORT clause to MDL syntax

CREATE JAVA ACTION MyModule.ReadCSV(File: System.FileDocument) RETURNS String
IMPORT com.mendix.core.Core, java.io.*, java.util.*
AS $$
// can use short names
$$;

Option C: Auto-detect types and inject imports

Scan $$ code for known type references and auto-add imports. A reasonable default mapping:

Type Import
Core com.mendix.core.Core
IContext com.mendix.systemwideinterfaces.core.IContext
IMendixObject com.mendix.systemwideinterfaces.core.IMendixObject
IMendixIdentifier com.mendix.systemwideinterfaces.core.IMendixIdentifier
InputStream java.io.InputStream
BufferedReader java.io.BufferedReader
InputStreamReader java.io.InputStreamReader
BigDecimal java.math.BigDecimal
List, ArrayList java.util.List, java.util.ArrayList
Map, HashMap java.util.Map, java.util.HashMap
ILogNode com.mendix.logging.ILogNode

Bonus: Support BEGIN EXTRA CODE

Consider an EXTRA $$...$$ block for helper methods:

CREATE JAVA ACTION MyModule.MyAction() RETURNS String
AS $$
return helper();
$$
EXTRA $$
private String helper() { return "ok"; }
$$;

Also: skill doc java-actions.md references removed API

The Core API Reference table in java-actions.md lists:

Core.retrieveXPathQuery(context, xpath)

This method does not exist in Mendix 10+/11. The correct API per official docs is:

Core.createXPathQuery(xpath).execute(context)

This causes AI agents to generate code that compiles but fails with method not found.

Environment

  • mxcli: 0.1.0
  • Mendix: 11.6.4
  • Platform: Windows 11

Copied from engalar#44

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions