Spring JPA에서 Named Parameters 를 사용할 때 아래와 같은 메시지의 예외가 발생하였다.
For queries with named parameters you need to use provide names for method parameters. Use @Param for query method parameters, or when on Java 8+ use the javac flag -parameters.
위의 Spring Data Reference에 보아도 Named Parameters를 사용할 때 @Param를 사용하라고 적혀있다는 것이다. (6.3.6)
이상한 것은 전에는 @Param 없이도 잘 동작했는데 왜 그럴까?
일딴 그 예외를 발생시키는 주체는 ParameterBinder 안의 BasicQueryParameterSetterFactory 클래스였다. (getName 부분)
public class ParameterBinder {
static final String PARAMETER_NEEDS_TO_BE_NAMED = "For queries with named parameters you need to use provide names for method parameters. Use @Param for query method parameters, or when on Java 8+ use the javac flag -parameters.";
// in QueryParameterSetterFactory abstract class
private static class BasicQueryParameterSetterFactory extends QueryParameterSetterFactory {
// ..
@Nullable
private JpaParameter findParameterForBinding(ParameterBinding binding) {
JpaParameters bindableParameters = parameters.getBindableParameters();
for (JpaParameter bindableParameter : bindableParameters) {
if (binding.getRequiredName().equals(getName(bindableParameter))) {
return bindableParameter;
}
}
return null;
}
private Object getValue(JpaParametersParameterAccessor accessor, Parameter parameter) {
return accessor.getValue(parameter);
}
private static String getName(JpaParameter p) {
return p.getName().orElseThrow(() -> new IllegalStateException(ParameterBinder.PARAMETER_NEEDS_TO_BE_NAMED));
}
}
하지만 여기는 예외를 발생시키는 부분이지 원인은 아니였다.
SingleEntityExecution 클래스
단일 엔티티 수행에 대한 것은 SingleEntityExecution 이 오버라이드하고 있다.
inner class 로 구현을 하고 있는데 JpaQueryExecution 안에 포함하고 있다.
public abstract class JpaQueryExecution {
// ..
static class SingleEntityExecution extends JpaQueryExecution {
@Override
protected Object doExecute(AbstractJpaQuery query, JpaParametersParameterAccessor accessor) {
return query.createQuery(accessor).getSingleResult();
}
}
public abstract class | static class | comment |
JpaQueryExecution | PagedExecution | |
SingleEntityExecution | return a single entity | |
ModifyingExecution | update, insert, delete | |
DeleteExecution | Since: 1.6 | |
ExistsExecution | Since: 1.11 | |
ProcedureExecution | Since: 1.6 | |
StreamExecution | Since: 1.8 |
org.springframework.data.jpa.repository.query.AbstractStringBasedJpaQuery#doCreateQuery
org.springframework.data.jpa.repository.query.AbstractStringBasedJpaQuery#createBinder
org.springframework.data.jpa.repository.query.ParameterBinderFactory#createQueryAwareBinder