alibaba/spring-ai-alibaba · error · RuntimeException

input is not List

Error message

input is not List

What it means

In LIST mode, ListOperatorNode.apply requires the state value at inputKey to be an instance of java.util.List. If it is anything else (a JSON string, array, null) this RuntimeException is thrown. It's a runtime type guard so the subsequent (List<T>) cast is safe.

Solutions

  1. Set mode to JSON_STR if the upstream value is a JSON string.
  2. Ensure the upstream node writes an actual List under inputKey.
  3. Check for state-key collisions where another node overwrites the value.
  4. Add a pre-check node validating the state value type before ListOperatorNode runs.

Example fix

// before
ListOperatorNode.<Item>start().mode(Mode.LIST).inputKey("items")... // items is a JSON string
// after
ListOperatorNode.<Item>start().mode(Mode.JSON_STR).inputKey("items")...
Defensive patterns

Strategy: type-guard

Validate before calling

Object v = state.value("items").orElse(null);
if (!(v instanceof List)) throw new IllegalStateException("'items' must be a List for Mode.LIST, got " + (v == null ? "null" : v.getClass()));

Type guard

boolean isListInput(OverAllState state, String key) {
    return state.value(key).map(v -> v instanceof List<?>).orElse(false);
}

Try / catch

try {
    out = listOperator.apply(state);
} catch (RuntimeException e) {
    if ("input is not List".equals(e.getMessage())) {
        throw new IllegalStateException("Upstream emitted non-List for key; switch mode or fix upstream", e);
    }
    throw e;
}

Prevention

When it happens

Trigger: Mode LIST configured while upstream node wrote a JSON string, a primitive array, a Map, or nothing (null) under inputKey.

Common situations: Mixing nodes that emit JSON strings with nodes expecting structured lists; refactoring upstream output from List to serialized JSON; key collisions in OverAllState overwriting the list.

Understand the failure class

Background: Type mismatch errors: IllegalArgumentException, TypeError and type guards across 150 open-source libraries — this error's family across 150 libraries.

Related errors


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

Appendix: source

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

		this.type = type;
	}

	@Override
	public Map<String, Object> apply(OverAllState t) throws Exception {
		try {
			Object inputObject = t.value(inputKey).orElse(null);
			List<T> inputList = switch (mode) {
				case JSON_STR -> {
					if (!(inputObject instanceof String)) {
						throw new RuntimeException("input is not String");
					}
					String inputJsonString = inputObject.toString();
					JavaType javaType = objectMapper.getTypeFactory().constructParametricType(List.class, type);
					yield objectMapper.readValue(inputJsonString, javaType);
				}
				case LIST -> {
					if (!(inputObject instanceof List)) {
						throw new RuntimeException("input is not List");
					}
					yield (List<T>) inputObject;
				}
				case ARRAY -> {
					if (inputObject == null || !inputObject.getClass().isArray()) {
						throw new RuntimeException("input is not Array");
					}
					yield Arrays.asList((T[]) inputObject);
				}
			};
			List<T> listElements = inputList.stream()
				.filter(filterChain)
				.sorted(comparatorChain)
				.limit(limitNumber != null && limitNumber > 0 ? limitNumber : Long.MAX_VALUE)
				.toList();

			Object output = switch (mode) {
				case JSON_STR -> objectMapper.writeValueAsString(listElements);

View on GitHub (pinned to f82da0b50f)