hibernate/hibernate-orm · error · NoSuchElementException

No node for attribute: {}

Error message

No node for attribute: {}

What it means

GraphImpl.getAttributeNode(String) throws NoSuchElementException('No node for attribute: ...') when the name resolves to a real attribute of the graphed type (including inherited ones) but this graph holds no node for it — nothing was ever added via addAttributeNode, or the node was removed. It signals an absent node, not an unknown attribute (that case throws IllegalArgumentException).

Source

Thrown at hibernate-core/src/main/java/org/hibernate/graph/internal/GraphImpl.java:116

			&& attributeNodes.containsKey( attribute );
	}

	@Override
	public boolean hasAttributeNode(@Nonnull Attribute<? super J, ?> attribute) {
		return attributeNodes != null
			&& attributeNodes.containsKey( (PersistentAttribute<? super J, ?>) attribute );
	}

	@Override
	@Nonnull
	public <Y> AttributeNodeImplementor<Y,?,?> getAttributeNode(@Nonnull String attributeName) {
		final var attribute = findAttributeInSupertypes( attributeName );
		if ( attribute == null ) {
			throw new IllegalArgumentException( "Unknown attribute: " + attributeName );
		}
		final var node = attributeNodes == null ? null : attributeNodes.get( attribute );
		if ( node == null ) {
			throw new NoSuchElementException( "No node for attribute: " + attributeName );
		}
		@SuppressWarnings("unchecked") // The JPA API is unsafe by nature
		final var castNode = (AttributeNodeImplementor<Y, ?, ?>) node;
		return castNode;
	}

	@Override
	@Nonnull
	public <Y> AttributeNodeImplementor<Y,?,?> getAttributeNode(@Nonnull Attribute<? super J, Y> attribute) {
		final var node = attributeNodes == null ? null
				: attributeNodes.get( (PersistentAttribute<? super J, ?>) attribute );
		if ( node == null ) {
			throw new NoSuchElementException( "No node for attribute: " + attribute );
		}
		@SuppressWarnings("unchecked")
		final var castNode = (AttributeNodeImplementor<Y, ?, ?>) node;
		return castNode;
	}

View on GitHub (pinned to fad1729dce)

Solutions

  1. Create the node instead of assuming it exists: addAttributeNode(name) returns the existing or newly created node
  2. Check presence via getAttributeNodes() names (or hasAttributeNode after validating the name) before fetching
  3. When inspecting graphs you did not build, treat a missing node as 'attribute not fetched' rather than an error

Example fix

// before
var node = graph.getAttributeNode("customer"); // graph never added it → NoSuchElementException

// after — addAttributeNode returns the existing or newly created node
var node = graph.addAttributeNode("customer");
Defensive patterns

Strategy: validation

Validate before calling

// Check node presence without exceptions before getAttributeNode(name)
static Optional<jakarta.persistence.AttributeNode<?>> nodeFor(EntityGraph<?> graph, String attrName) {
    return graph.getAttributeNodes().stream()
            .filter(n -> n.getAttributeName().equals(attrName))
            .findFirst();
}

Prevention

When it happens

Trigger: Calling getAttributeNode(name) on a freshly created empty graph (nodes only exist after addAttributeNode), after the node was removed, or when inspecting a graph parsed from a string or loaded by name that never mentioned the attribute.

Common situations: Graph merge/inspection utilities assuming nodes exist for all attributes; reading named/parsed graphs for attributes that were never included; interleaving removal and lookup logic.

Related errors


AI-assisted analysis of hibernate/hibernate-orm@fad1729dce (2026-08-22). Data as JSON: /api/errors/23c0cbf76eeb03c7. Report an issue: GitHub.