alibaba/spring-ai-alibaba · error · Exception

Either language or code must be provided.

Error message

Either language or code must be provided.

What it means

LocalCommandlineCodeExecutor.executeCode throws a checked Exception when either the language or the code argument is null. The executor needs both to pick the interpreter and to materialize the code into a temp file under the work directory.

Source

Thrown at spring-boot-starters/spring-ai-alibaba-starter-builtin-nodes/src/main/java/com/alibaba/cloud/ai/graph/node/code/LocalCommandlineCodeExecutor.java:77

			// "bash", "shell", "sh", "python"
			result = executeCode(language, code, codeExecutionConfig);
			allLogs.append("\n").append(result.logs());
			if (result.exitCode() != 0) {
				return new CodeExecutionResult(result.exitCode(), allLogs.toString());
			}
		}
		return new CodeExecutionResult(0, allLogs.toString());
	}

	@Override
	public void restart() {

		logger.warn("Restarting local command line code executor is not supported. No action is taken.");
	}

	public CodeExecutionResult executeCode(String language, String code, CodeExecutionConfig config) throws Exception {
		if (Objects.isNull(language) || Objects.isNull(code)) {
			throw new Exception("Either language or code must be provided.");
		}
		String workDir = config.getWorkDir();
		String codeHash = DigestUtils.md5Hex(code);
		String fileExt = CodeUtils.getFileExtForLanguage(language);
		String filename = String.format("tmp_code_%s.%s", codeHash, fileExt);

		// write the code string to a file specified by the filename.
		FileUtils.writeCodeToFile(workDir, filename, code);

		// Copy required JAR files to workDir if language is Java
		if ("java".equals(language)) {
			FileUtils.copyResourceJarToWorkDir(workDir);
		}

		CodeExecutionResult executionResult = executeCodeLocally(language, workDir, filename, config);

		FileUtils.deleteFile(workDir, filename);

View on GitHub (pinned to f82da0b50f)

Solutions

  1. Validate language and code are non-null/non-blank before calling executeCode.
  2. If blocks come from an LLM response, check parsing and require the model to output both fields (prompt or schema enforcement).
  3. Wrap the call and surface a clearer message to the caller instead of the raw Exception.

Example fix

// before
executor.executeCode(language, code, config); // throws if either is null
// after
Objects.requireNonNull(language, "language must not be null");
Objects.requireNonNull(code, "code must not be null");
executor.executeCode(language, code, config);
Defensive patterns

Strategy: validation

Validate before calling

if (language == null || language.isBlank()) throw new IllegalArgumentException("language is required");
if (code == null || code.isBlank()) throw new IllegalArgumentException("code is required");

Type guard

boolean isExecutableBlock(String language, String code) {
    return language != null && !language.isBlank() && code != null && !code.isBlank();
}

Try / catch

try {
    return executor.executeCode(language, code, config);
} catch (Exception e) {
    if (e.getMessage() != null && e.getMessage().contains("language or code")) {
        return CodeExecutionResult.empty();
    }
    throw new RuntimeException(e);
}

Prevention

When it happens

Trigger: Calling executeCode(language, code, config) with a null language, a null code string, or a code block whose fields were never populated (e.g. an LLM produced a code block missing the 'language' or 'code' key).

Common situations: An LLM response parsed into code blocks where the model omitted the language tag; programmatically building CodeExecutionBlock and forgetting to set code; passing a null map value from configuration.

Related errors


AI-assisted analysis of alibaba/spring-ai-alibaba@f82da0b50f (2026-09-09). Data as JSON: /api/errors/70cc0bdb8647a6bb. Report an issue: GitHub.