休眠异常:意外令牌:HAVING
Posted
技术标签:
【中文标题】休眠异常:意外令牌:HAVING【英文标题】:Hibernate Exception : unexpected token: HAVING 【发布时间】:2015-10-27 18:59:32 【问题描述】:我必须通过比较给定的距离输入,即纬度和经度来从 DB 中整理出结果。冲浪后,我在 SQL 中找到了解决方案,并将其转换为相应的 HQL。
我的查询是:
SELECT restaurantId,restaurantName,address1,((ACOS(SIN(9.9986 * PI() / 180) * SIN(latitude * PI() / 180) + COS(9.9986 * PI() / 180) * COS(latitude * PI() / 180) * COS((76.3125-longitude) * PI() / 180)) * 180 / PI()) * 60 * 1.1515) AS distanceInKm FROM Restaurants HAVING distanceInKm<=1 ORDER BY distanceInKm ASC
这会出现错误Hibernate Exception : unexpected token: HAVING
。
请注意,在这个distanceInKm
中是一个虚拟列。我需要将虚拟列也添加到响应中。我尝试使用where
而不是having
,但它显示Unknown column distanceInKm
方法
public List<Restaurants> getRestaurantsByDistance(FilterMovieRequest filterMovieRequest) throws SQLException, ClassNotFoundException, IOException
Session session = sessionFactory.getCurrentSession();
String sql = "SELECT restaurantId,restaurantName,address1,((ACOS(SIN(9.9986 * PI() / 180) * SIN(latitude * PI() / 180) + COS(9.9986 * PI() / 180) * COS(latitude * PI() / 180) * COS((76.3125-longitude) * PI() / 180)) * 180 / PI()) * 60 * 1.1515) AS distanceInKm FROM Restaurants HAVING distanceInKm<=1 ORDER BY distanceInKm ASC";
Query query = session.createQuery(sql);
List<Restaurants> rows = query.list();
return rows;
实体
@Entity
@Table(name = "restaurants")
public class Restaurants implements Serializable
private static final long serialVersionUID = 1L;
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
@Column(name = "restaurant_id")
private int restaurantId;
@Column(name = "restaurant_name")
private String restaurantName;
@Column(name = "category_id")
private Integer categoryId;
@Column(name = "image_url")
private String imageUrl;
private Float longitude;
private Float latitude;
@Column(name = "contact_name")
private String contactName;
@Column(name = "primary_phone")
private String primaryPhone;
@Column(name = "secondary_phone")
private String secondaryPhone;
private String fax;
private String address1;
private String address2;
//Getters and setters
我找到了与此相关的标签,但它不足以解决我的问题。
错误:
05-Aug-2015 12:16:56.017 SEVERE [http-nio-8084-exec-103] org.apache.catalina.core.StandardWrapperValve.invoke Servlet.service() for servlet [WeekenterServlet] in context with path [/Weekenter] threw exception [Request processing failed; nested exception is org.hibernate.hql.ast.QuerySyntaxException: unexpected token: HAVING near line 1, column 290 [SELECT restaurantId,restaurantName,address1,((ACOS(SIN(9.9986 * PI() / 180) * SIN(latitude * PI() / 180) + COS(9.9986 * PI() / 180) * COS(latitude * PI() / 180) * COS((76.3125-longitude) * PI() / 180)) * 180 / PI()) * 60 * 1.1515) AS distanceInKm FROM com.weekenter.www.entity.Restaurants HAVING distanceInKm<=1 ORDER BY distanceInKm ASC]] with root cause
org.hibernate.hql.ast.QuerySyntaxException: unexpected token: HAVING near line 1, column 290 [SELECT restaurantId,restaurantName,address1,((ACOS(SIN(9.9986 * PI() / 180) * SIN(latitude * PI() / 180) + COS(9.9986 * PI() / 180) * COS(latitude * PI() / 180) * COS((76.3125-longitude) * PI() / 180)) * 180 / PI()) * 60 * 1.1515) AS distanceInKm FROM com.weekenter.www.entity.Restaurants HAVING distanceInKm<=1 ORDER BY distanceInKm ASC]
at org.hibernate.hql.ast.QuerySyntaxException.convert(QuerySyntaxException.java:54)
at org.hibernate.hql.ast.QuerySyntaxException.convert(QuerySyntaxException.java:47)
at org.hibernate.hql.ast.ErrorCounter.throwQueryException(ErrorCounter.java:82)
at org.hibernate.hql.ast.QueryTranslatorImpl.parse(QueryTranslatorImpl.java:284)
at org.hibernate.hql.ast.QueryTranslatorImpl.doCompile(QueryTranslatorImpl.java:182)
at org.hibernate.hql.ast.QueryTranslatorImpl.compile(QueryTranslatorImpl.java:136)
at org.hibernate.engine.query.HQLQueryPlan.<init>(HQLQueryPlan.java:101)
at org.hibernate.engine.query.HQLQueryPlan.<init>(HQLQueryPlan.java:80)
at org.hibernate.engine.query.QueryPlanCache.getHQLQueryPlan(QueryPlanCache.java:98)
at org.hibernate.impl.AbstractSessionImpl.getHQLQueryPlan(AbstractSessionImpl.java:156)
at org.hibernate.impl.AbstractSessionImpl.createQuery(AbstractSessionImpl.java:135)
at org.hibernate.impl.SessionImpl.createQuery(SessionImpl.java:1760)
at com.weekenter.www.dao.impl.UtilityDaoImpl.getRestaurantsByDistance(UtilityDaoImpl.java:196)
at com.weekenter.www.service.impl.UtilityServiceImpl.getRestaurantsByDistance(UtilityServiceImpl.java:140)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:497)
at org.springframework.aop.support.AopUtils.invokeJoinpointUsingReflection(AopUtils.java:317)
at org.springframework.aop.framework.ReflectiveMethodInvocation.invokeJoinpoint(ReflectiveMethodInvocation.java:183)
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:150)
at org.springframework.transaction.interceptor.TransactionInterceptor$1.proceedWithInvocation(TransactionInterceptor.java:96)
at org.springframework.transaction.interceptor.TransactionAspectSupport.invokeWithinTransaction(TransactionAspectSupport.java:260)
at org.springframework.transaction.interceptor.TransactionInterceptor.invoke(TransactionInterceptor.java:94)
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:172)
at org.springframework.aop.framework.JdkDynamicAopProxy.invoke(JdkDynamicAopProxy.java:204)
at com.sun.proxy.$Proxy938.getRestaurantsByDistance(Unknown Source)
at com.weekenter.www.controller.UtilityController.getRestaurantsByDistance(UtilityController.java:212)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:497)
at org.springframework.web.method.support.InvocableHandlerMethod.invoke(InvocableHandlerMethod.java:219)
at org.springframework.web.method.support.InvocableHandlerMethod.invokeForRequest(InvocableHandlerMethod.java:132)
at org.springframework.web.servlet.mvc.method.annotation.ServletInvocableHandlerMethod.invokeAndHandle(ServletInvocableHandlerMethod.java:104)
at org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter.invokeHandleMethod(RequestMappingHandlerAdapter.java:745)
at org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter.handleInternal(RequestMappingHandlerAdapter.java:686)
at org.springframework.web.servlet.mvc.method.AbstractHandlerMethodAdapter.handle(AbstractHandlerMethodAdapter.java:80)
at org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:925)
at org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:856)
at org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:936)
at org.springframework.web.servlet.FrameworkServlet.doPost(FrameworkServlet.java:838)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:644)
at org.springframework.web.servlet.FrameworkServlet.service(FrameworkServlet.java:812)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:725)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:291)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206)
at org.apache.tomcat.websocket.server.WsFilter.doFilter(WsFilter.java:52)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:239)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206)
at org.netbeans.modules.web.monitor.server.MonitorFilter.doFilter(MonitorFilter.java:393)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:239)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:330)
at org.springframework.security.web.access.intercept.FilterSecurityInterceptor.invoke(FilterSecurityInterceptor.java:118)
at org.springframework.security.web.access.intercept.FilterSecurityInterceptor.doFilter(FilterSecurityInterceptor.java:84)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342)
at org.springframework.security.web.access.ExceptionTranslationFilter.doFilter(ExceptionTranslationFilter.java:113)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342)
at org.springframework.security.web.session.SessionManagementFilter.doFilter(SessionManagementFilter.java:103)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342)
at org.springframework.security.web.servletapi.SecurityContextHolderAwareRequestFilter.doFilter(SecurityContextHolderAwareRequestFilter.java:154)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342)
at org.springframework.security.web.savedrequest.RequestCacheAwareFilter.doFilter(RequestCacheAwareFilter.java:45)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342)
at org.springframework.security.oauth2.provider.authentication.OAuth2AuthenticationProcessingFilter.doFilter(OAuth2AuthenticationProcessingFilter.java:131)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342)
at org.springframework.security.web.context.request.async.WebAsyncManagerIntegrationFilter.doFilterInternal(WebAsyncManagerIntegrationFilter.java:50)
at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342)
at org.springframework.security.web.context.SecurityContextPersistenceFilter.doFilter(SecurityContextPersistenceFilter.java:87)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342)
at org.springframework.security.web.FilterChainProxy.doFilterInternal(FilterChainProxy.java:192)
at org.springframework.security.web.FilterChainProxy.doFilter(FilterChainProxy.java:160)
at org.springframework.web.filter.DelegatingFilterProxy.invokeDelegate(DelegatingFilterProxy.java:343)
at org.springframework.web.filter.DelegatingFilterProxy.doFilter(DelegatingFilterProxy.java:260)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:239)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206)
at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:219)
at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:106)
at org.apache.catalina.authenticator.AuthenticatorBase.invoke(AuthenticatorBase.java:501)
at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:142)
at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:79)
at org.apache.catalina.valves.AbstractAccessLogValve.invoke(AbstractAccessLogValve.java:610)
at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:88)
at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:537)
at org.apache.coyote.http11.AbstractHttp11Processor.process(AbstractHttp11Processor.java:1085)
at org.apache.coyote.AbstractProtocol$AbstractConnectionHandler.process(AbstractProtocol.java:658)
at org.apache.coyote.http11.Http11NioProtocol$Http11ConnectionHandler.process(Http11NioProtocol.java:222)
at org.apache.tomcat.util.net.NioEndpoint$SocketProcessor.doRun(NioEndpoint.java:1556)
at org.apache.tomcat.util.net.NioEndpoint$SocketProcessor.run(NioEndpoint.java:1513)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)
at org.apache.tomcat.util.threads.TaskThread$WrappingRunnable.run(TaskThread.java:61)
at java.lang.Thread.run(Thread.java:745)
【问题讨论】:
您使用的是哪个版本的 Hibernate,您是否有特定的原因通常针对 Hibernate 而不是 JPA?Hibernate 3.5
@chrylis.. 我也准备好使用JPA
如果它能给我结果的话..
发布您的完整堆栈跟踪
JPA 本质上是 Hibernate 的标准化版本,除非您有特定原因(通常是遗留问题),否则最好使用它。 Hibernate 仍将完成这项工作,但您将使用标准配置和 JPQL(几乎是 HQL)。当前的 Hibernate 版本是 4.3,我首先建议使用现代版本。
可能错误是它使用了Restaurants
的完整限定名:com.weekenter.www.entity.Restaurants
【参考方案1】:
在休眠中,您只能使用HAVING
子句和GROUP BY
only。如果您必须使用HAVING
,我更喜欢使用createSQLQuery
,如下所示。
public List<Restaurants> getRestaurantsByDistance(FilterMovieRequest filterMovieRequest) throws SQLException, ClassNotFoundException, IOException
Session session = sessionFactory.getCurrentSession();
Float latitude = Float.parseFloat(filterMovieRequest.Latitude() );//Get your latitude from request
Float longitude = Float.parseFloat(filterMovieRequest.Longitude());//Get your longitude from request
String sql = "SELECT restaurant_id,restaurant_name,category_id,image_url,longitude,latitude,contact_name,primary_phone,secondary_phone,fax,address1,address2,((ACOS(SIN(:lat * PI() / 180) * SIN(latitude * PI() / 180) + COS(:lat * PI() / 180) * COS(latitude * PI() / 180) * COS((:lon-longitude) * PI() / 180)) * 180 / PI()) * 60 * 1.1515) AS `distanceInKm` FROM `restaurants` HAVING `distanceInKm`<=1 ORDER BY `distanceInKm` ASC";
Query query = session.createSQLQuery(sql).addEntity(Restaurants.class);
query.setParameter("lat", latitude);
query.setParameter("lon", longitude);
List<Restaurants> restaurantses = query.list();
return restaurantses;
实体
@Entity
@Table(name = "restaurants")
public class Restaurants implements Serializable
private static final long serialVersionUID = 1L;
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
@Column(name = "restaurant_id")
private int restaurantId;
@Column(name = "restaurant_name")
private String restaurantName;
@Column(name = "category_id")
private Integer categoryId;
@Column(name = "image_url")
private String imageUrl;
private Float longitude;
private Float latitude;
@Column(name = "contact_name")
private String contactName;
@Column(name = "primary_phone")
private String primaryPhone;
@Column(name = "secondary_phone")
private String secondaryPhone;
private String fax;
private String address1;
private String address2;
@Column(insertable = false, updatable = false)
private String distanceInKm; /*Virtual column for user responds*/
注意:如果您想将您的虚拟列(即distanceInKm
)传递给用户,您应该只使用Getter method
来表示该特定内容。并且应该设置条件@Column(insertable = false, updatable = false)
【讨论】:
【参考方案2】:您是否尝试将所有请求字段封装在带括号的地图中? 像这样 : 选择新地图(餐厅 ID 作为餐厅 ID, 餐厅名称作为餐厅名称, address1 作为 adr1, ((ACOS(SIN(9.9986 * PI() / 180) * SIN(纬度 * PI() / 180) + COS(9.9986 * PI() / 180) * COS(纬度 * PI() / 180) * COS( (76.3125-经度) * PI() / 180)) * 180 / PI()) * 60 * 1.1515) AS distanceInKm) 来自.....
【讨论】:
以上是关于休眠异常:意外令牌:HAVING的主要内容,如果未能解决你的问题,请参考以下文章
意外的令牌:在休眠状态下使用 spring data jpa 时的位置
意外令牌:使用休眠、JPQL 和 postgres 函数时出现“<function_name>”错误