mybatis/mybatis-3 · error · ReflectionException

Could not set property '{}' of '{}' with value '{}' Cause: {

Error message

Could not set property '{}' of '{}' with value '{}' Cause: {}

What it means

BeanWrapper.setBeanProperty invokes the property's write method via reflection. If the setter throws — most often IllegalArgumentException from a type mismatch between the supplied value and the setter parameter, or NPE inside custom setter logic — MyBatis wraps it in a ReflectionException naming the property, owner class, value, and cause. The Cause string identifies whether it is a conversion problem or setter logic failing.

Source

Thrown at src/main/java/org/apache/ibatis/reflection/wrapper/BeanWrapper.java:212

    } catch (RuntimeException e) {
      throw e;
    } catch (Throwable t) {
      throw new ReflectionException(
          "Could not get property '" + prop.getName() + "' from " + object.getClass() + ".  Cause: " + t.toString(), t);
    }
  }

  private void setBeanProperty(PropertyTokenizer prop, Object object, Object value) {
    try {
      Invoker method = metaClass.getSetInvoker(prop.getName());
      Object[] params = { value };
      try {
        method.invoke(object, params);
      } catch (Throwable t) {
        throw ExceptionUtil.unwrapThrowable(t);
      }
    } catch (Throwable t) {
      throw new ReflectionException("Could not set property '" + prop.getName() + "' of '" + object.getClass()
          + "' with value '" + value + "' Cause: " + t.toString(), t);
    }
  }

  @Override
  public boolean isCollection() {
    return false;
  }

  @Override
  public void add(Object element) {
    throw new UnsupportedOperationException();
  }

  @Override
  public <E> void addAll(List<E> list) {
    throw new UnsupportedOperationException();
  }

View on GitHub (pinned to 008069adb1)

Solutions

  1. Check the Cause: for IllegalArgumentException align the property type with the incoming value (add a typeHandler or change the field type)
  2. Use wrapper types (Integer instead of int) for nullable columns
  3. Register/select the correct TypeHandler in the resultMap mapping for the mismatched property
  4. Fix or relax custom setter validation that rejects the mapped data

Example fix

<!-- before -->
<result property="count" column="count" /> <!-- column is VARCHAR, field is int -->

<!-- after -->
<result property="count" column="count" typeHandler="org.apache.ibatis.type.IntegerTypeHandler" />
Defensive patterns

Strategy: try-catch

Validate before calling

// before mapping, sanity-check value type against the setter parameter type
Class<?> expected = metaClass.getSetterType("count");
if (value != null && !expected.isAssignableFrom(value.getClass())
    && !(expected.isPrimitive() || Number.class.isAssignableFrom(expected) /* conversions */)) {
  value = convert(value, expected); // your conversion or typeHandler
}

Try / catch

try {
  metaObject.setValue("count", rawValue);
} catch (ReflectionException e) {
  Throwable cause = e.getCause();
  if (cause instanceof IllegalArgumentException) {
    // type mismatch: convert value or configure a typeHandler, then retry once
  } else throw e;
}

Prevention

When it happens

Trigger: Result mapping feeds a String column value into an int setter (or any column-to-field type mismatch); a custom setter with validation that throws; mapping a null into a primitive setter; Enum vs String mismatch between JDBC value and property type.

Common situations: Column type changes in the DB (VARCHAR to NUMERIC) without updating the bean; resultMap jdbcType/javaType mismatches; DB nulls mapped into primitive fields; custom setters enforcing invariants that incoming data violates.

Related errors


AI-assisted analysis of mybatis/mybatis-3@008069adb1 (2026-08-14). Data as JSON: /api/errors/1ff57fd02948c678. Report an issue: GitHub.