2012-07-11 79 views
2

我正在使用Jesey在java中實現Restful Web服務(JAX-RS)。我在Tomcat v7.0上運行它,我使用Hibernate將數據映射到數據庫(MySQL)。我有一個查詢來獲取交付清單:使用MySQL的SQL查詢

deliverables = (List<Deliverable>) session.createQuery("Select deliverable from 
       Task as t where t.project.id= :id And t.user.username = :name") 
    .setLong("id", projectId).setString("name", username).list(); 

這是給我交付了一百,但我想在工作表前三名。我很感激任何幫助。我如何修改查詢?

請注意,這三個可交付成果不應重複。

與@FGreg答案有衝突。當我使用這些查詢,一切工作正常:

deliverables = (List<Deliverable>) session.createQuery(
    "from Deliverable as d where d.project.id= :id").setLong("id", projectId).list(); 
    long task_id; 
    for(Deliverable d: deliverables) { 
     task_id = (long) session.createQuery("Select Max(id) from Task as t where  
     t.deliverable.id = :id and t.user.username = :name") 
     .setLong("id", d.getId()).setString("name", username).uniqueResult(); 
     d.setTask_id(task_id); 
    } 
    sortDeliverable(deliverables); // sort by Task_id 

我想通過@FGreg提供的查詢中,MAX(ID)不被視爲例如交付與TASK_ID = 31,643使用兩次。它可能會考慮Task_id = 31,這是錯誤的。任何幫助解決它?

我試着@FGreg查詢沒有不同。然後除了重複問題,它工作正常。

我嘗試這樣做:

deliverables = (List<Deliverable>) session.createQuery("from Deliverable as d inner join 
Task as t where t.id = (select max(t1.id) from Task as t1 where t1.deliverable.id = d.id) 
and d.project.id= :id and t.user.username = :name order by t.id desc") 
        .setMaxResults(3) 
        .setLong("id", projectId) 
        .setString("name", username) 
        .list(); 

而且我得到的堆棧跟蹤新的錯誤:

Jul 13, 2012 5:03:10 PM org.hibernate.hql.internal.ast.ErrorCounter reportError 
ERROR: Path expected for join! 
Jul 13, 2012 5:03:10 PM org.hibernate.hql.internal.ast.ErrorCounter reportError 
ERROR: Path expected for join! 
Path expected for join! 
    at org.hibernate.hql.internal.ast.HqlSqlWalker.createFromJoinElement(HqlSqlWalker.java:371) 
    at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.joinElement(HqlSqlBaseWalker.java:3477) 
    at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.fromElement(HqlSqlBaseWalker.java:3263) 
    at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.fromElementList(HqlSqlBaseWalker.java:3141) 
    at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.fromClause(HqlSqlBaseWalker.java:694) 
    at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.query(HqlSqlBaseWalker.java:550) 
    at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.selectStatement(HqlSqlBaseWalker.java:287) 
    at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.statement(HqlSqlBaseWalker.java:235) 
    at org.hibernate.hql.internal.ast.QueryTranslatorImpl.analyze(QueryTranslatorImpl.java:248) 
    at org.hibernate.hql.internal.ast.QueryTranslatorImpl.doCompile(QueryTranslatorImpl.java:183) 
    at org.hibernate.hql.internal.ast.QueryTranslatorImpl.compile(QueryTranslatorImpl.java:136) 
    at org.hibernate.engine.query.spi.HQLQueryPlan.<init>(HQLQueryPlan.java:101) 
    at org.hibernate.engine.query.spi.HQLQueryPlan.<init>(HQLQueryPlan.java:80) 
    at org.hibernate.engine.query.spi.QueryPlanCache.getHQLQueryPlan(QueryPlanCache.java:119) 
    at org.hibernate.internal.AbstractSessionImpl.getHQLQueryPlan(AbstractSessionImpl.java:214) 
    at org.hibernate.internal.AbstractSessionImpl.createQuery(AbstractSessionImpl.java:192) 
    at org.hibernate.internal.SessionImpl.createQuery(SessionImpl.java:1537) 
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) 
    at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source) 
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source) 
    at java.lang.reflect.Method.invoke(Unknown Source) 
    at org.hibernate.context.internal.ThreadLocalSessionContext$TransactionProtectionWrapper.invoke(ThreadLocalSessionContext.java:350) 
    at $Proxy65.createQuery(Unknown Source) 
    at se.softwerk.timelog.controller.DeliverableManager.deliverableList2(DeliverableManager.java:185) 
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) 
    at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source) 
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source) 
    at java.lang.reflect.Method.invoke(Unknown Source) 
    at com.sun.jersey.spi.container.JavaMethodInvokerFactory$1.invoke(JavaMethodInvokerFactory.java:60) 
    at com.sun.jersey.server.impl.model.method.dispatch.AbstractResourceMethodDispatchProvider$ResponseOutInvoker._dispatch(AbstractResourceMethodDispatchProvider.java:205) 
    at com.sun.jersey.server.impl.model.method.dispatch.ResourceJavaMethodDispatcher.dispatch(ResourceJavaMethodDispatcher.java:75) 
    at com.sun.jersey.server.impl.uri.rules.HttpMethodRule.accept(HttpMethodRule.java:288) 
    at com.sun.jersey.server.impl.uri.rules.RightHandPathRule.accept(RightHandPathRule.java:147) 
    at com.sun.jersey.server.impl.uri.rules.ResourceClassRule.accept(ResourceClassRule.java:108) 
    at com.sun.jersey.server.impl.uri.rules.RightHandPathRule.accept(RightHandPathRule.java:147) 
    at com.sun.jersey.server.impl.uri.rules.RootResourceClassesRule.accept(RootResourceClassesRule.java:84) 
    at com.sun.jersey.server.impl.application.WebApplicationImpl._handleRequest(WebApplicationImpl.java:1469) 
    at com.sun.jersey.server.impl.application.WebApplicationImpl._handleRequest(WebApplicationImpl.java:1400) 
    at com.sun.jersey.server.impl.application.WebApplicationImpl.handleRequest(WebApplicationImpl.java:1349) 
    at com.sun.jersey.server.impl.application.WebApplicationImpl.handleRequest(WebApplicationImpl.java:1339) 
    at com.sun.jersey.spi.container.servlet.WebComponent.service(WebComponent.java:416) 
    at com.sun.jersey.spi.container.servlet.ServletContainer.service(ServletContainer.java:537) 
    at com.sun.jersey.spi.container.servlet.ServletContainer.service(ServletContainer.java:708) 
    at javax.servlet.http.HttpServlet.service(HttpServlet.java:722) 
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:305) 
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:210) 
    at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:224) 
    at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:169) 
    at org.apache.catalina.authenticator.AuthenticatorBase.invoke(AuthenticatorBase.java:472) 
    at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:168) 
    at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:98) 
    at org.apache.catalina.valves.AccessLogValve.invoke(AccessLogValve.java:928) 
    at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:118) 
    at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:407) 
    at org.apache.coyote.http11.AbstractHttp11Processor.process(AbstractHttp11Processor.java:987) 
    at org.apache.coyote.AbstractProtocol$AbstractConnectionHandler.process(AbstractProtocol.java:539) 
    at org.apache.tomcat.util.net.JIoEndpoint$SocketProcessor.run(JIoEndpoint.java:298) 
    at java.util.concurrent.ThreadPoolExecutor.runWorker(Unknown Source) 
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(Unknown Source) 
    at java.lang.Thread.run(Unknown Source) 

Jul 13, 2012 5:03:10 PM org.hibernate.hql.internal.ast.ErrorCounter reportError 
ERROR: Invalid path: 't.id' 
Jul 13, 2012 5:03:10 PM org.hibernate.hql.internal.ast.ErrorCounter reportError 
ERROR: Invalid path: 't.id' 
Invalid path: 't.id' 
    at org.hibernate.hql.internal.ast.util.LiteralProcessor.lookupConstant(LiteralProcessor.java:131) 
    at org.hibernate.hql.internal.ast.tree.DotNode.resolve(DotNode.java:219) 
    at org.hibernate.hql.internal.ast.tree.FromReferenceNode.resolve(FromReferenceNode.java:118) 
    at org.hibernate.hql.internal.ast.tree.FromReferenceNode.resolve(FromReferenceNode.java:114) 
    at org.hibernate.hql.internal.ast.HqlSqlWalker.resolve(HqlSqlWalker.java:883) 
    at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.expr(HqlSqlBaseWalker.java:1246) 
    at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.exprOrSubquery(HqlSqlBaseWalker.java:4252) 
    at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.comparisonExpr(HqlSqlBaseWalker.java:3730) 
    at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.logicalExpr(HqlSqlBaseWalker.java:1923) 
    at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.logicalExpr(HqlSqlBaseWalker.java:1848) 
    at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.logicalExpr(HqlSqlBaseWalker.java:1848) 
    at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.whereClause(HqlSqlBaseWalker.java:782) 
    at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.query(HqlSqlBaseWalker.java:583) 
    at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.selectStatement(HqlSqlBaseWalker.java:287) 
    at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.statement(HqlSqlBaseWalker.java:235) 
    at org.hibernate.hql.internal.ast.QueryTranslatorImpl.analyze(QueryTranslatorImpl.java:248) 
    at org.hibernate.hql.internal.ast.QueryTranslatorImpl.doCompile(QueryTranslatorImpl.java:183) 
    at org.hibernate.hql.internal.ast.QueryTranslatorImpl.compile(QueryTranslatorImpl.java:136) 
    at org.hibernate.engine.query.spi.HQLQueryPlan.<init>(HQLQueryPlan.java:101) 
    at org.hibernate.engine.query.spi.HQLQueryPlan.<init>(HQLQueryPlan.java:80) 
    at org.hibernate.engine.query.spi.QueryPlanCache.getHQLQueryPlan(QueryPlanCache.java:119) 
    at org.hibernate.internal.AbstractSessionImpl.getHQLQueryPlan(AbstractSessionImpl.java:214) 
    at org.hibernate.internal.AbstractSessionImpl.createQuery(AbstractSessionImpl.java:192) 
    at org.hibernate.internal.SessionImpl.createQuery(SessionImpl.java:1537) 
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) 
    at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source) 
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source) 
    at java.lang.reflect.Method.invoke(Unknown Source) 
    at org.hibernate.context.internal.ThreadLocalSessionContext$TransactionProtectionWrapper.invoke(ThreadLocalSessionContext.java:350) 
    at $Proxy65.createQuery(Unknown Source) 
    at se.softwerk.timelog.controller.DeliverableManager.deliverableList2(DeliverableManager.java:185) 
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) 
    at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source) 
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source) 
    at java.lang.reflect.Method.invoke(Unknown Source) 

模型類:

@Entity 
public class Task { 

    @Id 
    @GeneratedValue 
    private long id; 

    @ManyToOne(optional = false) 
    private User user; 

    @ManyToOne(optional = false) 
    private Project project; 


    @ManyToOne(optional = false) 
    private Deliverable deliverable; 
} 

且可傳送:

@Entity 
public class Deliverable { 

    @Id 
    @GeneratedValue 
    private long id; 

    @Column(name = "short", nullable = false) 
    private String key; 

    @Column(nullable = false) 
    private String name; 

    @OneToMany(targetEntity = Task.class, mappedBy = "deliverable", fetch = FetchType.LAZY, cascade = CascadeType.ALL) 
    @JsonIgnore 
    private Collection<Task> tasks; 

    @ManyToOne(optional = false, fetch = FetchType.EAGER) 
    @JoinColumn(name = "project") 
    private Project project; 

    @ManyToOne(fetch = FetchType.EAGER) 
    @JoinColumn(name = "parent") 
    private Deliverable parent; 

    @OneToMany(targetEntity = Deliverable.class, mappedBy = "parent", fetch = FetchType.LAZY, cascade = CascadeType.ALL) 
    @JsonIgnore 
    private Collection<Deliverable> children; 
} 
+0

我提出了一個新問題,可能有助於解決這個問題。請檢查它:http://stackoverflow.com/questions/11457292/sql-query-using-hibernate-in-a-restful-web-service – Ali 2012-07-12 17:31:25

+0

該錯誤表明可能有一個問題與您的Hibernate之間的映射對象。確保你的映射文件中有''和''標籤正確。不管你是否有這個映射,我的下面的編輯應該工作。 – FGreg 2012-07-13 16:30:27

+0

我認爲映射文件中的標記能正常工作。我檢查了幾次。 – Ali 2012-07-13 16:40:49

回答

2

我想你是要求從ID排序的Task排名前3 Deliverable s。你可以嘗試這樣的事情:

編輯:好吧,我會再採取一個刺。這應該給你的前3 Deliverable S按Task.id下令採取只關聯到max(Task.id)

deliverables = 
     (List<Deliverable>) session.createQuery(
      "from Deliverable as d, Task as t 
       where t.deliverable.id = d.id and 
       t.id = (select max(t1.id) from Task t1 where t1.deliverable.id = d.id) 
       and d.project.id= :id 
       and t.user.username = :name 
       order by t.id desc") 
     .setMaxResults(3) 
     .setLong("id", projectId) 
     .setString("name", username) 
     .list(); 
+0

好幫手。我以某種方式問你這個問題,你誤解了。我正在編輯它。但我想它離我想要的很近。 (這三個交付物不應該重複。) – Ali 2012-07-11 21:17:59

+0

我再次感謝。有衝突,我編輯了這個問題,請你檢查一下。 – Ali 2012-07-11 22:48:22

+0

這是一個真正有用的編輯。但我再次發生錯誤。我不知道爲什麼。我只是將堆棧跟蹤中的錯誤複製到問題的結尾。也許是因爲(... =(從任務t1選擇max(t1.id),其中t1.deliverable.id = d.id))在澤西島可能不支持 – Ali 2012-07-13 15:14:47

1

Deliverable我不知道TOP功能是在MySQL中可用,但嘗試使用它,並分享結果。你可以這樣寫: SELECT TOP 2 * FROM Persons

檢查這個鏈接,它會提供給你更多的細節。 enter link description here

+0

我很欣賞,MySQL中不支持TOP功能。 – Ali 2012-07-12 11:42:13

2

mysql沒有TOP,在sql的末尾使用ORDER BY和LIMIT子句。

+0

我與我的朋友@ali檢查過,Barmar是正確的。嘗試探索如何使用LIMIT。 – Amir 2012-07-12 07:50:26

+0

@ali:現在檢查Barmar的答案,我添加了一個如何使用LIMIT的例子。 – Amir 2012-07-12 08:11:56

+0

我嘗試了LIMIT,它對我沒有幫助。但我猜如果它的工作結果是一樣的@FGerg響應。 「.setMaxResults(3)」也會得到相同的結果。 – Ali 2012-07-12 11:46:26