2009-03-01 10 views
4

検索を実行するためにnHibernate条件式をビルドしようとしています。次のデータ・モデルを考えるnHibernateでの結合のフィルター

  • 操作は、ゼロ以上 セッションを有することができます。
  • 操作の種類が0より大きく、操作タイプが である可能性があります。

が、私は次の基準に基づいて、すべてのセッションを検索したい:操作 のisActiveフラグがtrueの場合は

  • (必須)、( フラグが

O真実であるIsPublishedオプションで)、操作状態/終了日がユーザー指定の日付範囲内にある場合

o(オプション)およびセッションregionidは、ユーザ指定のID

(任意に)O、セッション分割を(任意に)ユーザ指定ID

Oと一致するとの一致Operation.OperationTypesは、タイプIDのユーザが指定したリストにある場合

私は(すべてのオプションパラメータが供給されている与えられた)として、SQLでこれを表現します:

0:として

SELECT  
    [Session].* 
FROM   
    [OperationTypeOperation] 
LEFT OUTER JOIN 
    [Operation] ON [OperationTypeOperation].[OperationId] = [Operation].[OperationId] 
RIGHT OUTER JOIN 
    [Session] ON [Operation].[OperationId] = [Session].[OperationId] 
WHERE 
    ([Operation].[IsPublished] = 1) 
AND 
    ([Operation].[IsActive] = 1) 
AND 
    ([Session].[RegionId] = 66) 
AND 
    ([Session].[DivisionId] = 99) 
AND 
    ([Operation].[AdvertisingStartDate] < GETDATE()) 
AND 
    ([Operation].[AdvertisingEndDate] > GETDATE()) 
AND 
    ([OperationTypeOperation].[OperationTypeId] IN (1, 2, 3)) 

そして、私のNHibernateはクエリで

nHibernate関数が演算の型について不平を言っていて、 "InExpressionでコレクションを使用できません"という例外がスローされています。プラス私は結合されたテーブルを正しくフィルタリングしているかどうかはわかりません。誰も正しい方法で上記のSQLをnHibernate式として書くことができますか?

答えて

5

OperationTypeはエンティティクラス(列挙型ではない)と仮定します。エンティティのリストにInを使用することはできません。あなたはidを使って参加することができます。

criteria 
    .CreateCriteria("Operation") 
    // add other expressions 
    .CreateCriteria("OperationTypes", "operationTypes", JoinType.LeftOuterJoin) 
    .Add(Expression.In("operationTypes.Id", operationTypeId)) 

私は_session.Get(id)がデータベースクエリを実行すると仮定します。とにかくこれを避けるべきです。

PS:オペレーションタイプがコンポジットコレクション(<composite-element>タグ付き)としてマッピングされている場合、残念ながら、条件と結合できません。回避策があるかどうかはわかりません。しかし、保留中のパッチがあります。

私が書くより良い方法があると思い
1

criteria 
    .CreateCriteria("Operation") 
    // add other expressions 
    .CreateCriteria("OperationTypes", "operationTypes", JoinType.LeftOuterJoin) 
    .Add(Expression.In("operationTypes.Id", operationTypeId)) 

追加の参加が"Operation"

上で実行されているため、あなたは簡単に書くことができます。

criteria.Add(Expression.In("OperationTypes", operationTypeId)) 
.CreateCriteria("Operation") 
         .Add(Expression.Eq("IsPublished", true)) 
         .Add(Expression.Eq("IsActive", true)) 
         .Add(Expression.Le("AdvertisingStartDate", DateTime.Now)) 
         .Add(Expression.Ge("AdvertisingEndDate", DateTime.Now)) 
         .SetResultTransformer(new DistinctRootEntityResultTransformer()) 
関連する問題