Использование @EmbeddedId с JpaRepository
У меня есть простой класс Entitly с полями @EmbeddedId
(Integer
и String
в отдельном классе). И я использую Spring Data (org.springframework.data.jpa.repository.JpaRepository
) для доступа к базе данных (MySql), при этом нормальный Id обрабатывает запросы, как сгенерированные Spring, так и те, которые были написаны мной. С EmbeddedId
мне не удалось создать правильный запрос. То, что я хочу сделать, - это выбрать все id (одно из полей embeddedId, для которого выполняется какое-то условие). Здесь у вас есть образцы кода, может быть, кто-то будет иметь идею, как его решить.
Класс entity:
@Entity
@Table(name="table_name")
public class EntityClass {
@EmbeddedId
private EmbeddedIdClass id;
private String someField;
//rest of implemetation
}
класс EmbeddedId:
@Embeddable
public class EmbeddedIdClass implements Serializable {
public EmbeddedIdClass(Long id, String language) {
super();
this.id = id;
this.language = language;
}
public UserAdTextId() {}
@Column(name="ad_id", nullable=false)
private Integer id;
@Column(name="language_code", nullable=false)
private String language;
//rest of implemetation
}
и репозиторий:
@Transactional(readOnly=true)
public interface MyRepository extends JpaRepository<EntityClass, EmbeddedIdClass> {
@Query("select distinct ad_id from EntityClass where userId = :userId and (/*here the conditions*/)")
public Page<Integer> findUserAdsWithSearchString(@Param("userId") Integer userId, @Param("searchString") String searchString, Pageable page);
//rest of implemetation
}
Я не нашел документации о том, как создавать методы поддержки @EmbeddedId, я пытался использовать разные имена методов, но всегда получаю исключения из парсера метода.
Ответы
Ответ 1
Кажется, ваш запрос использует имена столбцов. Он должен содержать имена свойств, включая навигацию по встроенным объектам. Здесь также есть связанный с этим вопрос о SO: Как написать JPQL SELECT со встроенным id?
select distinct id.id from EntityClass where userId = :userId and (...)
Первый id
относится к атрибуту id
of EntityClass
(типа EmbeddedIdClass
), а второй относится к свойству id
EmbeddedIdClass
.
Кроме того, убедитесь, что в EntityClass
есть свойство userId
.
Ответ 2
(Йоси Лев)
Это можно сделать следующим образом:
Предположим, что ваш основной объект:
@Entity
@Table(name="JRULES_FLOW")
public class JrulesFlow implements Serializable {
private static final long serialVersionUID = 1L;
@EmbeddedId
private JrulesFlowPK id;
@Column(name="NEXT_SEQ")
private int nextSeq;
@Column(name="REF_ID")
private String refId;
@Column(name="TASK_TYPE")
private String taskType;
@Column(name="VALUE_TO_FIND")
private String valueToFind;
}
И ваш класс PK:
@Embeddable
public class JrulesFlowPK implements Serializable {
//default serial version id, required for serializable classes.
private static final long serialVersionUID = 1L;
@Column(name="FLOW_ID")
private String flowId;
@Column(name="TASK_SEQ")
private long taskSeq;
}
В именах методов метода репозитория JPA указано имя поля id в
основной класс, за которым следует свойство, которое вы хотите запросить вверх в классе PK:
public interface JrulesFlowRepository extends JpaRepository<JrulesFlow,
JrulesFlowPK> { // NOTE: put here both classes - also the pk class..
public List<JrulesFlow> findByIdFlowId(String flowId); // Id - is the
// @EmbeddedId in JrulesFlow. FlowId is an attribute
// within JrulesFlowPK
}