hibernate/hibernate-orm · error · NullPointerException

Attempted to refresh null

Error message

Attempted to refresh null

What it means

NullPointerException thrown by DefaultRefreshEventListener.onRefresh when event.getObject() is null, i.e. session.refresh(null) / EntityManager.refresh(null). The refresh pipeline needs a real managed instance to reload from the database; the listener enforces the @Nonnull contract with an explicit null check. A null here is almost always a bug in the caller's data flow (a lookup that returned null was passed on).

Source

Thrown at hibernate-core/src/main/java/org/hibernate/event/internal/DefaultRefreshEventListener.java:61

 */
public class DefaultRefreshEventListener implements RefreshEventListener {

	@Override
	public void onRefresh(@Nonnull RefreshEvent event) {
		onRefresh( event, RefreshContext.create() );
	}

	/**
	 * Handle the given refresh event.
	 *
	 * @param event The refresh event to be handled.
	 */
	@Override
	public void onRefresh(@Nonnull RefreshEvent event, @Nonnull RefreshContext refreshedAlready) {
		final Object object = event.getObject();
		//noinspection ConstantValue
		if ( object == null ) {
			throw new NullPointerException( "Attempted to refresh null" );
		}
		final var source = event.getEventSource();
		if ( isUninitialized( object, source ) ) {
			handleUninitializedProxy( event, refreshedAlready );
		}
		else {
			final Object entity = forceInitialize( object, source );
			if ( refreshedAlready.add( entity ) ) {
				refresh( event, refreshedAlready, entity );
			}
			else {
				EVENT_LISTENER_LOGGER.alreadyRefreshed();
			}
		}
	}

	private static void handleUninitializedProxy(@Nonnull RefreshEvent event, @Nonnull RefreshContext refreshedAlready) {
		final var source = event.getEventSource();

View on GitHub (pinned to fad1729dce)

Solutions

  1. Null-check (or wrap in Optional) before calling refresh, and treat null as 'row not found' business logic instead of refreshable state
  2. Trace the null to its origin — usually a find() miss caused by a wrong id, a not-yet-committed insert from another transaction, or a deleted row
  3. Use Optional-style chaining so a null can never reach the session API

Example fix

// before
Order o = em.find(Order.class, id);
em.refresh(o); // NPE: Attempted to refresh null when id does not exist

// after
Optional.ofNullable(em.find(Order.class, id)).ifPresent(em::refresh);
Defensive patterns

Strategy: validation

Validate before calling

if (order != null) {
    session.refresh(order);
}
// or: Optional.ofNullable(find(id)).ifPresent(em::refresh);

Type guard

null

Try / catch

null

Prevention

When it happens

Trigger: session.refresh(x) or em.refresh(x) where x is null — typically the result of em.find(Entity.class, id) for a non-existent row (find returns null) being forwarded to refresh unconditionally; nullable relation fields dereferenced into refresh helpers.

Common situations: Optional-entity flows where a missing row silently becomes null; batch helper methods like refreshAll(List) invoked with a null list; test code or mocks passing null; JPA spec expects IllegalArgumentException for refresh(null), so ported code that relied on that behavior hits the NPE wording instead.

Related errors


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