2017-08-31 10 views
4

私はonetomany関係(ContactInfo)を持つJPAエンティティ(Person)を持っています。OneToManyを使用したSpringデータ投影は結果が多すぎます

@Entity 
public class Person { 
    @Id 
    @GeneratedValue 
    private Integer id; 
    private String name; 
    private String lastname; 
    private String sshKey; 
    @OneToMany(mappedBy = "personId") 
    private List<ContactInfo> contactInfoList; 
} 

@Entity 
public class ContactInfo { 
    @Id 
    @GeneratedValue 
    private Integer id; 
    private Integer personId; 
    private String description; 
} 

Iについて説明here、このonetomany関係を含む投影インタフェースを定義しました。

public interface PersonProjection { 
    Integer getId(); 
    String getName(); 
    String getLastname(); 
    List<ContactInfo> getContactInfoList(); 
} 

public interface PersonRepository extends JpaRepository<Person,Integer> { 
    List<PersonProjection> findAllProjectedBy(); 
} 

私はfindAllProjectedBy結果はあまりにも多くの行が含まれているとのデータを取得

。このデータセットについては、例えば

select p.id, p.name, p.lastname, ci.id, ci.person_id, ci.description 
from person p 
join contact_info ci on ci.person_id = p.id 

insert into person (id,name,lastname,ssh_key) values (1,'John','Wayne','SSH:KEY'); 

insert into contact_info (id, person_id, description) values (1,1,'+1 123 123 123'), (2,1,'[email protected]'); 

findAllProjectedBy方法は、2つのオブジェクト(誤って)戻る返されたデータがと同様のクエリを結合の結果であるように見えます標準findAllは1オブジェクト(正しく)を返します。

全プロジェクトは、私はいくつかのデバッグを行ってきた、問題がJPAクエリであると思われhere

です。 は、findAllメソッドは、このクエリを使用しています。

select generatedAlias0 from Person as generatedAlias0 

findAllProjectedByは、このクエリを使用しています。

select contactInfoList, generatedAlias0.id, generatedAlias0.name, generatedAlias0.lastname from Person as generatedAlias0 
left join generatedAlias0.contactInfoList as contactInfoList 

は、この不正な動作を修正する方法を誰もが知っていますか?この問題の

+0

これは正常な動作です。あなたは投影で何を達成したいのですか?たぶん、 'Person'の' ContactInfo'sのリストをロードするだけでいいのですか? – Cepr0

+0

'通常の動作' - どこに文書化されていますか?私が実装している一般的な使用例は、viewパラメータを持つAPIです。表示は、完全(findAll)または限定(findAllProjectedBy)のいずれかになります。私はDBから取得したデータを制限できるようにしたい。上記の例は非常に単純化されています。 – lbd01

+0

私にバグ/欠けているように見えます。問題を開くことはできますか? https://jira.spring.io/browse/DATAJPA/?selectedTab=com.atlassian.jira.jira-projects-plugin:summary-panel –

答えて

4

クイックフィックスは、ここで説明されています https://jira.spring.io/browse/DATAJPA-1173

あなたは@value注釈を持つ単一の投影のいずれかの属性を記述する必要があります。上に掲載された例では、次のようになります。

import java.util.List; 
import org.springframework.beans.factory.annotation.Value; 

public interface PersonProjection { 
    @Value("#{target.id}") 
    Integer getId(); 
    String getName(); 
    String getLastname(); 
    List<ContactInfo> getContactInfoList(); 
} 
+0

この注釈は、この投影を「閉鎖」ではなく「開」にします。彼らは、このバグを、メソッドの1つがコレクションまたはマップを返す場合に、デフォルトで投影が「開かれている」と仮定することによってこのバグを修正しました。 – Sam

+0

インターフェイスのDtoオブジェクトインスタンスを使用しているときに動作しません!私は次のようになっています:org.hibernate.hql.internal.ast.QuerySyntaxException:OPENが見つかる '、'、行1、列157の近く – pustypawel

+1

@Sam良い点。この結果、投影のエンティティ列のサブセットを返すとき、すべての列が選択されます。 – lbd01

関連する問題