自定义查询 Spring 数据 JPA + REST
Custom query Spring Data JPA + REST
在我的数据库中,我有一个 table "CITA" 具有以下属性:id、fecha_hora、descripcion、id_empleado、id_cliente。
我也有一个 Spring JPA 存储库:
public interface CitaRepository extends JpaRepository<Cita, Long> {...}
并且我需要这个查询:
"SELECT id_empleado, count(id) from Cita GROUP BY id_empleado ORDER BY fecha_hora"
我的问题是我不知道应该把它放在哪里 return 我像 Map
因为它不起作用:
@Query("SELECT id_empleado, count(id) from Cita GROUP BY id_empleado ORDER BY fecha_hora")
Map<Integer,Integer> estadisticas();
编辑
如果我尝试从我的 REST 控制器调用 estadisticas(),我会出错。
这是我的 REST 控制器:
@RestController
@RequestMapping("/app")
public class CitaResource {
private final Logger log = LoggerFactory.getLogger(CitaResource.class);
@Inject
private CitaRepository citaRepository;
@RequestMapping(value = "/rest/citas/estadisticas",
method = RequestMethod.GET,
produces = MediaType.APPLICATION_JSON_VALUE)
@Timed
public List<CitaDTO> estadisticas() {
return citaRepository.estadisticas();
}
这是我的 JPA 存储库:
public interface CitaRepository extends JpaRepository<Cita, Long> {
@Query("SELECT new com.raquel.tfg.web.rest.dto.CitaDTO(c.empleado_id, count(c)) from Cita c GROUP BY c.empleado_id ORDER BY c.fecha_hora")
List<CitaDTO> estadisticas();
}
这是我的 DTO class:
package com.raquel.tfg.web.rest.dto;
public class CitaDTO {
private int empleado_id;
private long count;
public CitaDTO(int empleado_id, long count) {
this.empleado_id = empleado_id;
this.count = count;
}
//get & set
}
这是我的实体 Cita:
@Entity
@Table(name = "T_CITA")
@Cache(usage = CacheConcurrencyStrategy.NONSTRICT_READ_WRITE)
public class Cita implements Serializable {
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
private Long id;
@Type(type = "org.jadira.usertype.dateandtime.joda.PersistentDateTime")
@JsonSerialize(using = CustomDateTimeSerializer.class)
@JsonDeserialize(using = CustomDateTimeDeserializer.class)
@Column(name = "fecha_hora", nullable = false)
private DateTime fecha_hora;
@Column(name = "descripcion")
private String descripcion;
@ManyToMany
@Cache(usage = CacheConcurrencyStrategy.NONSTRICT_READ_WRITE)
private Set<Servicio> servicios = new HashSet<>();
@ManyToOne
private Cliente cliente;
@ManyToOne
private Empleado empleado;
}
我有这个错误:
org.springframework.boot.SpringApplication - Application startup failed
org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'citaResource': Injection of autowired dependencies failed; nested exception is org.springframework.beans.factory.BeanCreationException: Could not autowire field: private com.raquel.tfg.repository.CitaRepository com.raquel.tfg.web.rest.CitaResource.citaRepository; nested exception is org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'citaRepository': Invocation of init method failed; nested exception is java.lang.IllegalArgumentException: Validation failed for query for method public abstract java.util.List com.raquel.tfg.repository.CitaRepository.estadisticas()!
at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessPropertyValues(AutowiredAnnotationBeanPostProcessor.java:334) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.populateBean(AbstractAutowireCapableBeanFactory.java:1202) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:537) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:476) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory.getObject(AbstractBeanFactory.java:302) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:230) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:298) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:193) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingletons(DefaultListableBeanFactory.java:762) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:757) ~[spring-context-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:480) ~[spring-context-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.boot.context.embedded.EmbeddedWebApplicationContext.refresh(EmbeddedWebApplicationContext.java:109) ~[spring-boot-1.2.0.RELEASE.jar:1.2.0.RELEASE]
at org.springframework.boot.SpringApplication.refresh(SpringApplication.java:691) ~[spring-boot-1.2.0.RELEASE.jar:1.2.0.RELEASE]
at org.springframework.boot.SpringApplication.run(SpringApplication.java:321) ~[spring-boot-1.2.0.RELEASE.jar:1.2.0.RELEASE]
at com.raquel.tfg.Application.main(Application.java:56) [classes/:na]
Caused by: org.springframework.beans.factory.BeanCreationException: Could not autowire field: private com.raquel.tfg.repository.CitaRepository com.raquel.tfg.web.rest.CitaResource.citaRepository; nested exception is org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'citaRepository': Invocation of init method failed; nested exception is java.lang.IllegalArgumentException: Validation failed for query for method public abstract java.util.List com.raquel.tfg.repository.CitaRepository.estadisticas()!
at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:558) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.annotation.InjectionMetadata.inject(InjectionMetadata.java:87) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessPropertyValues(AutowiredAnnotationBeanPostProcessor.java:331) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
... 14 common frames omitted
Caused by: org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'citaRepository': Invocation of init method failed; nested exception is java.lang.IllegalArgumentException: Validation failed for query for method public abstract java.util.List com.raquel.tfg.repository.CitaRepository.estadisticas()!
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1566) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:539) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:476) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory.getObject(AbstractBeanFactory.java:302) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:230) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:298) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:193) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.DefaultListableBeanFactory.findAutowireCandidates(DefaultListableBeanFactory.java:1127) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1051) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:949) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:530) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
... 16 common frames omitted
Caused by: java.lang.IllegalArgumentException: Validation failed for query for method public abstract java.util.List com.raquel.tfg.repository.CitaRepository.estadisticas()!
at org.springframework.data.jpa.repository.query.SimpleJpaQuery.validateQuery(SimpleJpaQuery.java:87) ~[spring-data-jpa-1.7.1.RELEASE.jar:na]
at org.springframework.data.jpa.repository.query.SimpleJpaQuery.<init>(SimpleJpaQuery.java:57) ~[spring-data-jpa-1.7.1.RELEASE.jar:na]
at org.springframework.data.jpa.repository.query.JpaQueryFactory.fromMethodWithQueryString(JpaQueryFactory.java:70) ~[spring-data-jpa-1.7.1.RELEASE.jar:na]
at org.springframework.data.jpa.repository.query.JpaQueryFactory.fromQueryAnnotation(JpaQueryFactory.java:51) ~[spring-data-jpa-1.7.1.RELEASE.jar:na]
at org.springframework.data.jpa.repository.query.JpaQueryLookupStrategy$DeclaredQueryLookupStrategy.resolveQuery(JpaQueryLookupStrategy.java:137) ~[spring-data-jpa-1.7.1.RELEASE.jar:na]
at org.springframework.data.jpa.repository.query.JpaQueryLookupStrategy$CreateIfNotFoundQueryLookupStrategy.resolveQuery(JpaQueryLookupStrategy.java:202) ~[spring-data-jpa-1.7.1.RELEASE.jar:na]
at org.springframework.data.jpa.repository.query.JpaQueryLookupStrategy$AbstractQueryLookupStrategy.resolveQuery(JpaQueryLookupStrategy.java:80) ~[spring-data-jpa-1.7.1.RELEASE.jar:na]
at org.springframework.data.repository.core.support.RepositoryFactorySupport$QueryExecutorMethodInterceptor.<init>(RepositoryFactorySupport.java:357) ~[spring-data-commons-1.9.1.RELEASE.jar:na]
at org.springframework.data.repository.core.support.RepositoryFactorySupport.getRepository(RepositoryFactorySupport.java:192) ~[spring-data-commons-1.9.1.RELEASE.jar:na]
at org.springframework.data.repository.core.support.RepositoryFactoryBeanSupport.initAndReturn(RepositoryFactoryBeanSupport.java:239) ~[spring-data-commons-1.9.1.RELEASE.jar:na]
at org.springframework.data.repository.core.support.RepositoryFactoryBeanSupport.afterPropertiesSet(RepositoryFactoryBeanSupport.java:225) ~[spring-data-commons-1.9.1.RELEASE.jar:na]
at org.springframework.data.jpa.repository.support.JpaRepositoryFactoryBean.afterPropertiesSet(JpaRepositoryFactoryBean.java:92) ~[spring-data-jpa-1.7.1.RELEASE.jar:na]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.invokeInitMethods(AbstractAutowireCapableBeanFactory.java:1625) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1562) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
... 26 common frames omitted
Caused by: java.lang.IllegalArgumentException: org.hibernate.QueryException: could not resolve property: empleado_id of: com.raquel.tfg.domain.Cita [SELECT new com.raquel.tfg.web.rest.dto.CitaDTO(c.empleado_id, count(c)) from com.raquel.tfg.domain.Cita c GROUP BY c.empleado_id ORDER BY c.fecha_hora]
at org.hibernate.jpa.spi.AbstractEntityManagerImpl.convert(AbstractEntityManagerImpl.java:1750) ~[hibernate-entitymanager-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.jpa.spi.AbstractEntityManagerImpl.convert(AbstractEntityManagerImpl.java:1677) ~[hibernate-entitymanager-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.jpa.spi.AbstractEntityManagerImpl.convert(AbstractEntityManagerImpl.java:1683) ~[hibernate-entitymanager-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.jpa.spi.AbstractEntityManagerImpl.createQuery(AbstractEntityManagerImpl.java:331) ~[hibernate-entitymanager-4.3.6.Final.jar:4.3.6.Final]
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) ~[na:1.8.0_25]
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62) ~[na:1.8.0_25]
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) ~[na:1.8.0_25]
at java.lang.reflect.Method.invoke(Method.java:483) ~[na:1.8.0_25]
at org.springframework.orm.jpa.ExtendedEntityManagerCreator$ExtendedEntityManagerInvocationHandler.invoke(ExtendedEntityManagerCreator.java:344) ~[spring-orm-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at com.sun.proxy.$Proxy126.createQuery(Unknown Source) ~[na:na]
at org.springframework.data.jpa.repository.query.SimpleJpaQuery.validateQuery(SimpleJpaQuery.java:81) ~[spring-data-jpa-1.7.1.RELEASE.jar:na]
... 39 common frames omitted
Caused by: org.hibernate.QueryException: could not resolve property: empleado_id of: com.raquel.tfg.domain.Cita [SELECT new com.raquel.tfg.web.rest.dto.CitaDTO(c.empleado_id, count(c)) from com.raquel.tfg.domain.Cita c GROUP BY c.empleado_id ORDER BY c.fecha_hora]
at org.hibernate.QueryException.generateQueryException(QueryException.java:137) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.QueryException.wrapWithQueryString(QueryException.java:120) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.ast.QueryTranslatorImpl.doCompile(QueryTranslatorImpl.java:234) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.ast.QueryTranslatorImpl.compile(QueryTranslatorImpl.java:158) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.engine.query.spi.HQLQueryPlan.<init>(HQLQueryPlan.java:126) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.engine.query.spi.HQLQueryPlan.<init>(HQLQueryPlan.java:88) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.engine.query.spi.QueryPlanCache.getHQLQueryPlan(QueryPlanCache.java:167) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.internal.AbstractSessionImpl.getHQLQueryPlan(AbstractSessionImpl.java:301) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.internal.AbstractSessionImpl.createQuery(AbstractSessionImpl.java:236) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.internal.SessionImpl.createQuery(SessionImpl.java:1800) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.jpa.spi.AbstractEntityManagerImpl.createQuery(AbstractEntityManagerImpl.java:328) ~[hibernate-entitymanager-4.3.6.Final.jar:4.3.6.Final]
... 46 common frames omitted
Caused by: org.hibernate.QueryException: could not resolve property: empleado_id of: com.raquel.tfg.domain.Cita
at org.hibernate.persister.entity.AbstractPropertyMapping.propertyException(AbstractPropertyMapping.java:83) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.persister.entity.AbstractPropertyMapping.toType(AbstractPropertyMapping.java:77) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.persister.entity.AbstractEntityPersister.toType(AbstractEntityPersister.java:1978) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.ast.tree.FromElementType.getPropertyType(FromElementType.java:367) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.ast.tree.FromElement.getPropertyType(FromElement.java:500) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.ast.tree.DotNode.getDataType(DotNode.java:652) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.ast.tree.DotNode.prepareLhs(DotNode.java:275) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.ast.tree.DotNode.resolve(DotNode.java:219) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.ast.tree.FromReferenceNode.resolve(FromReferenceNode.java:126) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.ast.tree.FromReferenceNode.resolve(FromReferenceNode.java:121) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.ast.tree.DotNode.resolveSelectExpression(DotNode.java:714) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.ast.HqlSqlWalker.resolveSelectExpression(HqlSqlWalker.java:958) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.selectExpr(HqlSqlBaseWalker.java:2257) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.constructor(HqlSqlBaseWalker.java:2607) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.selectExpr(HqlSqlBaseWalker.java:2324) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.selectExprList(HqlSqlBaseWalker.java:2194) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.selectClause(HqlSqlBaseWalker.java:1476) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.query(HqlSqlBaseWalker.java:573) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.selectStatement(HqlSqlBaseWalker.java:301) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.statement(HqlSqlBaseWalker.java:249) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.ast.QueryTranslatorImpl.analyze(QueryTranslatorImpl.java:278) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.ast.QueryTranslatorImpl.doCompile(QueryTranslatorImpl.java:206) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
... 54 common frames omitted
JPA 方式将使用 Select new
查询。您需要一个 Java class (不是映射的 JPA 实体) - 通常称为 DTO,它包含两个字段 empleadoId
count
和一个构造函数
package com.example
public class Dto {
private int empleadoId;
private long count;
public Dto(int empleadoId, long count) {
this.empleadoId = empleadoId;
this.count = count;
}
//getter and setter
}
那么你可以写这个仓库方法:
@Query("SELECT new com.example.Dto(c.id_empleado, count(c)) " +
"from Cita c GROUP BY c.id_empleado ORDER BY c.fecha_hora")
Map<Integer,Integer> statistics();
注意:注意c.id_empleado
snf c.fecha_hora
必须匹配字段名称,而不是列
在我的数据库中,我有一个 table "CITA" 具有以下属性:id、fecha_hora、descripcion、id_empleado、id_cliente。
我也有一个 Spring JPA 存储库:
public interface CitaRepository extends JpaRepository<Cita, Long> {...}
并且我需要这个查询:
"SELECT id_empleado, count(id) from Cita GROUP BY id_empleado ORDER BY fecha_hora"
我的问题是我不知道应该把它放在哪里 return 我像 Map
因为它不起作用:
@Query("SELECT id_empleado, count(id) from Cita GROUP BY id_empleado ORDER BY fecha_hora")
Map<Integer,Integer> estadisticas();
编辑
如果我尝试从我的 REST 控制器调用 estadisticas(),我会出错。
这是我的 REST 控制器:
@RestController
@RequestMapping("/app")
public class CitaResource {
private final Logger log = LoggerFactory.getLogger(CitaResource.class);
@Inject
private CitaRepository citaRepository;
@RequestMapping(value = "/rest/citas/estadisticas",
method = RequestMethod.GET,
produces = MediaType.APPLICATION_JSON_VALUE)
@Timed
public List<CitaDTO> estadisticas() {
return citaRepository.estadisticas();
}
这是我的 JPA 存储库:
public interface CitaRepository extends JpaRepository<Cita, Long> {
@Query("SELECT new com.raquel.tfg.web.rest.dto.CitaDTO(c.empleado_id, count(c)) from Cita c GROUP BY c.empleado_id ORDER BY c.fecha_hora")
List<CitaDTO> estadisticas();
}
这是我的 DTO class:
package com.raquel.tfg.web.rest.dto;
public class CitaDTO {
private int empleado_id;
private long count;
public CitaDTO(int empleado_id, long count) {
this.empleado_id = empleado_id;
this.count = count;
}
//get & set
}
这是我的实体 Cita:
@Entity
@Table(name = "T_CITA")
@Cache(usage = CacheConcurrencyStrategy.NONSTRICT_READ_WRITE)
public class Cita implements Serializable {
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
private Long id;
@Type(type = "org.jadira.usertype.dateandtime.joda.PersistentDateTime")
@JsonSerialize(using = CustomDateTimeSerializer.class)
@JsonDeserialize(using = CustomDateTimeDeserializer.class)
@Column(name = "fecha_hora", nullable = false)
private DateTime fecha_hora;
@Column(name = "descripcion")
private String descripcion;
@ManyToMany
@Cache(usage = CacheConcurrencyStrategy.NONSTRICT_READ_WRITE)
private Set<Servicio> servicios = new HashSet<>();
@ManyToOne
private Cliente cliente;
@ManyToOne
private Empleado empleado;
}
我有这个错误:
org.springframework.boot.SpringApplication - Application startup failed
org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'citaResource': Injection of autowired dependencies failed; nested exception is org.springframework.beans.factory.BeanCreationException: Could not autowire field: private com.raquel.tfg.repository.CitaRepository com.raquel.tfg.web.rest.CitaResource.citaRepository; nested exception is org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'citaRepository': Invocation of init method failed; nested exception is java.lang.IllegalArgumentException: Validation failed for query for method public abstract java.util.List com.raquel.tfg.repository.CitaRepository.estadisticas()!
at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessPropertyValues(AutowiredAnnotationBeanPostProcessor.java:334) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.populateBean(AbstractAutowireCapableBeanFactory.java:1202) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:537) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:476) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory.getObject(AbstractBeanFactory.java:302) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:230) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:298) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:193) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingletons(DefaultListableBeanFactory.java:762) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:757) ~[spring-context-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:480) ~[spring-context-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.boot.context.embedded.EmbeddedWebApplicationContext.refresh(EmbeddedWebApplicationContext.java:109) ~[spring-boot-1.2.0.RELEASE.jar:1.2.0.RELEASE]
at org.springframework.boot.SpringApplication.refresh(SpringApplication.java:691) ~[spring-boot-1.2.0.RELEASE.jar:1.2.0.RELEASE]
at org.springframework.boot.SpringApplication.run(SpringApplication.java:321) ~[spring-boot-1.2.0.RELEASE.jar:1.2.0.RELEASE]
at com.raquel.tfg.Application.main(Application.java:56) [classes/:na]
Caused by: org.springframework.beans.factory.BeanCreationException: Could not autowire field: private com.raquel.tfg.repository.CitaRepository com.raquel.tfg.web.rest.CitaResource.citaRepository; nested exception is org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'citaRepository': Invocation of init method failed; nested exception is java.lang.IllegalArgumentException: Validation failed for query for method public abstract java.util.List com.raquel.tfg.repository.CitaRepository.estadisticas()!
at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:558) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.annotation.InjectionMetadata.inject(InjectionMetadata.java:87) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessPropertyValues(AutowiredAnnotationBeanPostProcessor.java:331) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
... 14 common frames omitted
Caused by: org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'citaRepository': Invocation of init method failed; nested exception is java.lang.IllegalArgumentException: Validation failed for query for method public abstract java.util.List com.raquel.tfg.repository.CitaRepository.estadisticas()!
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1566) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:539) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:476) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory.getObject(AbstractBeanFactory.java:302) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:230) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:298) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:193) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.DefaultListableBeanFactory.findAutowireCandidates(DefaultListableBeanFactory.java:1127) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1051) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:949) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:530) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
... 16 common frames omitted
Caused by: java.lang.IllegalArgumentException: Validation failed for query for method public abstract java.util.List com.raquel.tfg.repository.CitaRepository.estadisticas()!
at org.springframework.data.jpa.repository.query.SimpleJpaQuery.validateQuery(SimpleJpaQuery.java:87) ~[spring-data-jpa-1.7.1.RELEASE.jar:na]
at org.springframework.data.jpa.repository.query.SimpleJpaQuery.<init>(SimpleJpaQuery.java:57) ~[spring-data-jpa-1.7.1.RELEASE.jar:na]
at org.springframework.data.jpa.repository.query.JpaQueryFactory.fromMethodWithQueryString(JpaQueryFactory.java:70) ~[spring-data-jpa-1.7.1.RELEASE.jar:na]
at org.springframework.data.jpa.repository.query.JpaQueryFactory.fromQueryAnnotation(JpaQueryFactory.java:51) ~[spring-data-jpa-1.7.1.RELEASE.jar:na]
at org.springframework.data.jpa.repository.query.JpaQueryLookupStrategy$DeclaredQueryLookupStrategy.resolveQuery(JpaQueryLookupStrategy.java:137) ~[spring-data-jpa-1.7.1.RELEASE.jar:na]
at org.springframework.data.jpa.repository.query.JpaQueryLookupStrategy$CreateIfNotFoundQueryLookupStrategy.resolveQuery(JpaQueryLookupStrategy.java:202) ~[spring-data-jpa-1.7.1.RELEASE.jar:na]
at org.springframework.data.jpa.repository.query.JpaQueryLookupStrategy$AbstractQueryLookupStrategy.resolveQuery(JpaQueryLookupStrategy.java:80) ~[spring-data-jpa-1.7.1.RELEASE.jar:na]
at org.springframework.data.repository.core.support.RepositoryFactorySupport$QueryExecutorMethodInterceptor.<init>(RepositoryFactorySupport.java:357) ~[spring-data-commons-1.9.1.RELEASE.jar:na]
at org.springframework.data.repository.core.support.RepositoryFactorySupport.getRepository(RepositoryFactorySupport.java:192) ~[spring-data-commons-1.9.1.RELEASE.jar:na]
at org.springframework.data.repository.core.support.RepositoryFactoryBeanSupport.initAndReturn(RepositoryFactoryBeanSupport.java:239) ~[spring-data-commons-1.9.1.RELEASE.jar:na]
at org.springframework.data.repository.core.support.RepositoryFactoryBeanSupport.afterPropertiesSet(RepositoryFactoryBeanSupport.java:225) ~[spring-data-commons-1.9.1.RELEASE.jar:na]
at org.springframework.data.jpa.repository.support.JpaRepositoryFactoryBean.afterPropertiesSet(JpaRepositoryFactoryBean.java:92) ~[spring-data-jpa-1.7.1.RELEASE.jar:na]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.invokeInitMethods(AbstractAutowireCapableBeanFactory.java:1625) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1562) ~[spring-beans-4.1.3.RELEASE.jar:4.1.3.RELEASE]
... 26 common frames omitted
Caused by: java.lang.IllegalArgumentException: org.hibernate.QueryException: could not resolve property: empleado_id of: com.raquel.tfg.domain.Cita [SELECT new com.raquel.tfg.web.rest.dto.CitaDTO(c.empleado_id, count(c)) from com.raquel.tfg.domain.Cita c GROUP BY c.empleado_id ORDER BY c.fecha_hora]
at org.hibernate.jpa.spi.AbstractEntityManagerImpl.convert(AbstractEntityManagerImpl.java:1750) ~[hibernate-entitymanager-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.jpa.spi.AbstractEntityManagerImpl.convert(AbstractEntityManagerImpl.java:1677) ~[hibernate-entitymanager-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.jpa.spi.AbstractEntityManagerImpl.convert(AbstractEntityManagerImpl.java:1683) ~[hibernate-entitymanager-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.jpa.spi.AbstractEntityManagerImpl.createQuery(AbstractEntityManagerImpl.java:331) ~[hibernate-entitymanager-4.3.6.Final.jar:4.3.6.Final]
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) ~[na:1.8.0_25]
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62) ~[na:1.8.0_25]
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) ~[na:1.8.0_25]
at java.lang.reflect.Method.invoke(Method.java:483) ~[na:1.8.0_25]
at org.springframework.orm.jpa.ExtendedEntityManagerCreator$ExtendedEntityManagerInvocationHandler.invoke(ExtendedEntityManagerCreator.java:344) ~[spring-orm-4.1.3.RELEASE.jar:4.1.3.RELEASE]
at com.sun.proxy.$Proxy126.createQuery(Unknown Source) ~[na:na]
at org.springframework.data.jpa.repository.query.SimpleJpaQuery.validateQuery(SimpleJpaQuery.java:81) ~[spring-data-jpa-1.7.1.RELEASE.jar:na]
... 39 common frames omitted
Caused by: org.hibernate.QueryException: could not resolve property: empleado_id of: com.raquel.tfg.domain.Cita [SELECT new com.raquel.tfg.web.rest.dto.CitaDTO(c.empleado_id, count(c)) from com.raquel.tfg.domain.Cita c GROUP BY c.empleado_id ORDER BY c.fecha_hora]
at org.hibernate.QueryException.generateQueryException(QueryException.java:137) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.QueryException.wrapWithQueryString(QueryException.java:120) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.ast.QueryTranslatorImpl.doCompile(QueryTranslatorImpl.java:234) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.ast.QueryTranslatorImpl.compile(QueryTranslatorImpl.java:158) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.engine.query.spi.HQLQueryPlan.<init>(HQLQueryPlan.java:126) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.engine.query.spi.HQLQueryPlan.<init>(HQLQueryPlan.java:88) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.engine.query.spi.QueryPlanCache.getHQLQueryPlan(QueryPlanCache.java:167) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.internal.AbstractSessionImpl.getHQLQueryPlan(AbstractSessionImpl.java:301) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.internal.AbstractSessionImpl.createQuery(AbstractSessionImpl.java:236) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.internal.SessionImpl.createQuery(SessionImpl.java:1800) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.jpa.spi.AbstractEntityManagerImpl.createQuery(AbstractEntityManagerImpl.java:328) ~[hibernate-entitymanager-4.3.6.Final.jar:4.3.6.Final]
... 46 common frames omitted
Caused by: org.hibernate.QueryException: could not resolve property: empleado_id of: com.raquel.tfg.domain.Cita
at org.hibernate.persister.entity.AbstractPropertyMapping.propertyException(AbstractPropertyMapping.java:83) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.persister.entity.AbstractPropertyMapping.toType(AbstractPropertyMapping.java:77) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.persister.entity.AbstractEntityPersister.toType(AbstractEntityPersister.java:1978) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.ast.tree.FromElementType.getPropertyType(FromElementType.java:367) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.ast.tree.FromElement.getPropertyType(FromElement.java:500) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.ast.tree.DotNode.getDataType(DotNode.java:652) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.ast.tree.DotNode.prepareLhs(DotNode.java:275) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.ast.tree.DotNode.resolve(DotNode.java:219) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.ast.tree.FromReferenceNode.resolve(FromReferenceNode.java:126) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.ast.tree.FromReferenceNode.resolve(FromReferenceNode.java:121) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.ast.tree.DotNode.resolveSelectExpression(DotNode.java:714) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.ast.HqlSqlWalker.resolveSelectExpression(HqlSqlWalker.java:958) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.selectExpr(HqlSqlBaseWalker.java:2257) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.constructor(HqlSqlBaseWalker.java:2607) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.selectExpr(HqlSqlBaseWalker.java:2324) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.selectExprList(HqlSqlBaseWalker.java:2194) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.selectClause(HqlSqlBaseWalker.java:1476) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.query(HqlSqlBaseWalker.java:573) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.selectStatement(HqlSqlBaseWalker.java:301) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.statement(HqlSqlBaseWalker.java:249) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.ast.QueryTranslatorImpl.analyze(QueryTranslatorImpl.java:278) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
at org.hibernate.hql.internal.ast.QueryTranslatorImpl.doCompile(QueryTranslatorImpl.java:206) ~[hibernate-core-4.3.6.Final.jar:4.3.6.Final]
... 54 common frames omitted
JPA 方式将使用 Select new
查询。您需要一个 Java class (不是映射的 JPA 实体) - 通常称为 DTO,它包含两个字段 empleadoId
count
和一个构造函数
package com.example
public class Dto {
private int empleadoId;
private long count;
public Dto(int empleadoId, long count) {
this.empleadoId = empleadoId;
this.count = count;
}
//getter and setter
}
那么你可以写这个仓库方法:
@Query("SELECT new com.example.Dto(c.id_empleado, count(c)) " +
"from Cita c GROUP BY c.id_empleado ORDER BY c.fecha_hora")
Map<Integer,Integer> statistics();
注意:注意c.id_empleado
snf c.fecha_hora
必须匹配字段名称,而不是列