2017-04-27 3 views
1

私はこのLink少ないenvers

それが正常に動作しているが、私はに参加 を使用していながら、問題がある

、それは与えていない単一の結果、同社で見られるのと同じ疑問を持つ特定のリビジョンにより最大リビジョンを取得します。指定されたリビジョン未満のすべてのリビジョンを返します。

私のコードは

AuditReader reader = AuditReaderFactory.get(session); 
AuditQueryCreator audQueryCreator = reader.createQuery(); 

AuditQuery query_cusTagInst = audQueryCreator.forEntitiesAtRevision(CustomTagInstance.class, revision_Id) 
       .add(AuditEntity.revisionNumber().le(revision_Id)) 
       .traverseRelation("instrument", JoinType.INNER) 
       .add(AuditEntity.revisionNumber().maximize().computeAggregationInInstanceContext()) 
       .add(AuditEntity.property("instrumentId").eq(id)); 
CustomTagInstance customTagInst = null; 
List list_cusTagInst = query_cusTagInst.getResultList(); 
for(int i=0; i<list_cusTagInst.size(); i++){ 
    customTagInst = (CustomTagInstance) list_cusTagInst.get(i); 
} 

そして

@Audited 
@Table(name = "CUSTOM_TAG_INSTANCE") 
public class CustomTagInstance implements java.io.Serializable { 

private Long tagInstanceId; 
private Instrument instrument; 

@Id 
@Column(name = "TAG_INSTANCE_ID", unique = true, nullable = false, precision = 22, scale = 0) 
public Long getTagInstanceId() { 
    return this.tagInstanceId; 
} 

public void setTagInstanceId(Long tagInstanceId) { 
    this.tagInstanceId = tagInstanceId; 
} 

@ManyToOne(fetch = FetchType.LAZY) 
@JoinColumn(name = "INSTRUMENT_ID") 
public Instrument getInstrument() { 
    return this.instrument; 
} 

public void setInstrument(Instrument instrument) { 
    this.instrument = instrument; 
} 

を教えてください以下の通りである私は与えられたリビジョンに未満のみ最大のリビジョンを取得するために使用するために必要なものがあります。

+0

結果または実際のエンティティインスタンスとしてRevisionNumberを取得する予定ですか?さらに、IDKはこれが 'computeAggregationInInstanceContext'ですか? '#max()'メソッドは射影クエリに対してのみ適用できます。 – Naros

+0

いいえ、私は最大リビジョンだけを望んでいません。私は各エンティティの最大リビジョンが指定されたリビジョン番号以下であることを確認しようとしています。私は自分の質問に似ている私の質問へのリンクを追加しました。しかし、ここでは** Join **を使う必要があります。そして、Joinを追加した後、複数のレコードを与えます。 –

+0

** ** computeAggregationInInstanceContext **この[Link_1](https://hibernate.atlassian.net/browse/HHH-7827)でこれを見つけました。この[Link_2](http://stackoverflow.com/questions/) 25723323/find-max-revision-of-each-entity-less-than-given-to-given-revision-with-enver) –

答えて

0

これを純粋なSQLの観点から見れば、記述しているのは、特定の述語セットに一致する値または集約値を取得しようとすることです。これは自動的に投影クエリを意味します。ここ

ソリューションは、のようになります。

final AuditQuery query = AuditReaderFactory.get(session) 
    .createQuery() 
    .forEntitiesAtRevision(CustomTag.class, revisionId) 
    .add(AuditEntity.revisionNumber().le(revisionId)) 
    .traverseRelation("instrument", JoinType.INNER) 
    .add(AuditRevisionNumber().maximize().computeAggregationInInstanceContext()) 
    .add(AuditEntity.property("instrumentId").eq(id)) 
    .up() 
    .addProjection(AuditEntity.selectEntity(true)) 
    .addOrder(AuditEntity.revisionNumber().desc()) 
    .setMaxResults(1); 

あなたが欠落していたキーパーツでは、クエリの最後線です。

addProjection(AuditEntity.selectEntity(true))は、エンティティインスタンス自体に固有値を生成して、戻り値が一意のエンティティインスタンスであることを通知します。これは結合/重複の問題を避けるべきです。

次に、addOrder(AuditEnttiy.revisionNumber().desc())オーダーの節を追加して、結果を降順で並べ替えます。これは、改訂番号がrevisionId以下の行を1行取得することを目的としているため、これを行います。これにより、その行が結果セットの最初の行になります。

setMaxResults(1)を適用します。目標に基づいて、これは我々が追加したorder by節と関連しています。これは、Hibernateに、関心のある行を返すように要求します。結果セットの先頭にあるリビジョン番号等しい。revisionId

HTH。

+0

説明していただきありがとうございますが、 'addProjection(AuditEntity.selectEntity(true))'クエリ結果は** Instrumentオブジェクト**(Joinを実行しています)を与えている間、** CustomTagInstance **オブジェクト。私はこれが** JoinType **のためかもしれないと思ったので、左結合もチェックしましたが結果は同じです。その後、この行を削除した後、単一の結果が得られましたが、与えられたリビジョンIDと等しく、与えられた数より少ないランダムな値を選んだ、最大値を求めたいのです –

+0

順序は問題ですか?あなたのコードの順序を変更した後、私が行ったのと同じように良い結果が得られたことを意味します。 'AuditQuery query_cusTagInst = audQueryCreator.forEntitiesAtRevision(CustomTagInstance.class、revision_Id).add(AuditEntity.revisionNumber()。lt(revision_Id))。addOrder (AuditEntity.property( "instrumentId").eq(id)).setMaxResults(1); ' –

関連する問題