2016-12-17 12 views
-1

JPQLを使用してSQLで結合テーブルからデータを取り出す最良の方法を理解しようとしています。このシナリオは次のとおりです。JPQLで結合テーブルからデータを取得

私は、費用リストのリストを持つユーザーエンティティを持っています。 ExpenseListエンティティはUserにマップされ、OneToMany関係になります。 プログラムを実行してユーザーの新しいリストを作成すると、User_Lists(JoinedTable)テーブルは、ユーザーのIDとそれがマップされているリストのIDで更新されます。この問題は、User_Listsテーブルからデータを取得しようとしています。私が試してみるたびに、それはマップされていないと言います。

ユーザークラス:

package com.emmaobo.expensetracker.model; 

import java.util.List; 

import javax.persistence.Column; 
import javax.persistence.Entity; 
import javax.persistence.EnumType; 
import javax.persistence.Enumerated; 
import javax.persistence.GeneratedValue; 
import javax.persistence.Id; 
import javax.persistence.JoinTable; 
import javax.persistence.OneToMany; 
import javax.persistence.Table; 

import com.emmaobo.expensetracker.enumeration.AccountType; 

@Entity 
@Table(name="USERS") 
public class User 
{ 

    @Id @GeneratedValue 
    private Long id; 

    @Column(name="USERNAME") 
    private String username; 

    @Column(name="PASSWORD") 
    private String password; 

    @Column(name="EMAIL") 
    private String email; 

    @Enumerated(EnumType.STRING) 
    private AccountType account; 

    @OneToMany(targetEntity=ExpenseList.class) 
    @JoinTable(name = "USER_LISTS") 
    private List<ExpenseList> list; 


    public User(){} 

    public User(String username, String password, String email) 
    { 
     this.username = username; 
     this.password = password; 
     this.email = email; 
    } 


    public Long getId() { 
     return id; 
    } 

    public void setId(Long id) { 
     this.id = id; 
    } 

    public String getUsername() { 
     return username; 
    } 

    public void setUsername(String username) { 
     this.username = username; 
    } 

    public String getPassword() { 
     return password; 
    } 

    public void setPassword(String password) { 
     this.password = password; 
    } 

    public String getEmail() { 
     return email; 
    } 

    public void setEmail(String email) { 
     this.email = email; 
    } 

    public AccountType getAccount() { 
     return account; 
    } 

    public void setAccount(AccountType account) { 
     this.account = account; 
    } 

    public List<ExpenseList> getList() { 
     return list; 
    } 

    public void setList(List<ExpenseList> list) { 
     this.list = list; 
    } 

    public void addList(ExpenseList newList) 
    { 
     this.list.add(newList); 
    } 

} 

ExpenseListクラス:私は以前にしようとしていた

package com.emmaobo.expensetracker.model; 

import java.math.BigDecimal; 
import java.util.List; 

import javax.persistence.Column; 
import javax.persistence.Entity; 
import javax.persistence.GeneratedValue; 
import javax.persistence.Id; 
import javax.persistence.OneToMany; 
import javax.persistence.Table; 

@Entity 
@Table(name="EXPENSE_LIST") 
public class ExpenseList 
{ 
    @Id @GeneratedValue 
    private Long id; 

    private String title; 

    @Column(name = "TOTAL") 
    private BigDecimal total; 

    @OneToMany(targetEntity = Item.class) 
    private List<Item> items; 

    public ExpenseList(){} 

    public ExpenseList(String title) 
    { 
     this.title = title; 
    } 

    public Long getId() { 
     return id; 
    } 

    public void setId(Long id) { 
     this.id = id; 
    } 

    public BigDecimal getTotal() { 
     return total; 
    } 

    public void setTotal(BigDecimal total) { 
     this.total = total; 
    } 

    public List<Item> getItems() { 
     return items; 
    } 

    public void setItems(List<Item> items) { 
     this.items = items; 
    } 

    public String getTitle() { 
     return title; 
    } 

    public void setTitle(String title) { 
     this.title = title; 
    } 
} 

データアクセス方法:

public List<ExpenseList> viewUsersLists(Long id) 
{ 
    //TODO fix this (study how to retrieve data from Joined Tables) 
    em = emf.createEntityManager(); 
    et = em.getTransaction(); 
    List<ExpenseList>usersLists = new ArrayList<ExpenseList>(); 

    @SuppressWarnings("unchecked") 
    TypedQuery<Long> query = (TypedQuery<Long>) em.createQuery("SELECT LIST_ID FROM USERS_EXPENSE_LIST Where USER_ID = "+id); 
    List<Long> usersListIDs = query.getResultList(); 

    for(Long expid : usersListIDs) 
    { 
     usersLists.add((ExpenseList)em.createQuery("SELECT id FROM ExpenseList Where id ="+expid, ExpenseList.class)); 
    } 

    return usersLists; 

    } 

答えて

0

は、私は解決策を考え出しました。テーブルを結合するのではなく、リストを作成したユーザーのIDを列に追加するだけです。そして、そのようにデータを検索します。とても簡単!

2

あなたはすでに必要なものはすべて持っており、追加の列は必要ありません。 オブジェクトリレーショナルマッパーを使用しているので、テーブルではなくオブジェクトを処理します。あなたは、単にその関連をナビゲートすることができるように

Userインスタンスは、すでにExpenseListの関連したコレクションを持っています

User user = entityManager.find(User.class, id); 
List<ExpenseList> expenses = user.getExpenseList(); 

あなたは本当にExpenseListはバックを持っているように、あなたは関係が双方向に行うことができます照会したい場合@ManyToOneを介してそのユーザーを参照しています。それで簡単にできます:

User user = entityManager.find(User.class, id); 
TypedQuery<ExpenseList> q = 
     em.createQuery("SELECT e FROM UserExpenseList e Where e.user = :user); 
q.setParameter("user", user); 
List<ExpenseList> expenses q.getResultList(); 
+0

これは私の解決策よりもはるかに単純であり、私はあなたがそのようにコレクションを取り出すこともできないことに気付きませんでした。ありがとうございました –

+0

なぜあなたは正解を2日後に投稿されたものに変えましたか? –

関連する問題