java - hibernate 异常: unexpected token: HAVING

标签 java mysql spring hibernate rest

我必须通过比较给定的距离输入(即纬度和经度)来从数据库中整理结果。冲浪后,我在 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:意外 token :HAVING。 请注意,在此 distanceInKm 中是一个虚拟列。我还需要将虚拟列添加到响应中。我尝试使用 where 而不是 having 但它显示未知列距离InKm

方法

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 中,您只能将 HAVING 子句与 GROUP BY 一起使用。如果您必须使用 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

@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 方法。应设置条件@Column(insertable = false, updatable = false)

关于java - hibernate 异常: unexpected token: HAVING,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/31825091/

相关文章:

java - 当 textArea 为空时,按钮不会变为禁用状态

mysql - 表被指定两次,既作为 INSERT 的目标又作为单独的数据源

mysql - 如何用 JOIN 替换 NOT EXISTS?

java - 如何使用 gradle 将类添加到类路径?

java - 运行应用程序时 eclipse 挂起(应用程序运行正常,eclipse 挂起)

java - Liferay 7 和 Vaadin 8 : Vaadin Shared is not active

java - 过滤掉集合中的记录

mysql - 这个简单的 sql 模式应该如何在 Mongodb 中建模

java - 查询异常 : ResultTransformer is not allowed for 'select new' queries

spring - 多部分文件(未给定条件)。错误 400(错误请求)