2011-07-15 11 views
0

私の現在のユースケースでは妥当性検査がうまくいきません。 私のアプリは標準的な構造を持っています(WEB < - > EJB3サービス< - > EJB3 DAO < - > DB)。 私は、検証アノテーションが適用されているエンティティを持っています。複雑なビジネス検証をJSR-303とマージするには?

enum NumberType { 
    FIXED, 
    MOBILE, 
    ANY 
} 

は、今私が適用される新しい検証ルールを持っている

@Entity 
class PhoneNumber { 

    ... 

    private NumberType numberType; 
} 

。 PhoneNumberの更新時に、以前にFIXEDまたはMOBILEのいずれかに設定されていた場合、NumberTypeをANYに変更することはできません。

私のBean検証ルールはdb操作の直前でチェックされ、上記のルールはDBにアクセスして比較するためのサービスレイヤー(少なくとも私はそうだと思います)に適用する必要があります。 しかし、まだ検証されていないBeanを持たないで、私は手動でチェックする必要があります。 numberTypeはnullではありません。

Bean検証を使用する場合、より複雑なビジネス検証(単一フィールドの値を単独でチェックするだけでなく)に対処する方法についていくつかのアドバイスや一般的なルールを教えてください。

答えて

0

Here「クロスフィールド」検証を行うカスタムバリデーターを作成する方法の良い説明があります。

+0

ありがとうございますが、これは私の問題に適合しません。私はクロスフィールド検証は必要ありません。私はその前の値(DBに格納されている)に対して1つのフィールドを検証する必要があります。 – grafthez

+0

したがって、カスタムバリデータのデータベースからエンティティをクエリし、その値と照合する必要があります。しかし、私はそれが良い習慣だとは思わない。代わりに、ビジネスロジックに古いエンティティをロードし、ここでその値をチェックします。この方法で、このロジックをバリデーターに隠すことはありません。 – Kai

3

私はBean検証がこの種のビジネスロジックを実装するための適切な解決策ではないと思います。

代わりにPhoneNumberエンティティのsetNumberType()メソッドでこのチェックを実装できます。そこには古い価値があり、サービス層の実装と比較すると、チェックを実装しているサービスを(偶然にまたは意図的に)迂回して不正な状態遷移を実行する機会はありません。

+1

私は最初の段落に同意します。しかし、私は実体にチェックを入れません。私の意見では、エンティティクラスは単なるPOJOであり、ビジネスロジックを含むべきではありません。さもなければ、セッターで何らかの暗黙的な変更が行われる可能性があるため、ビジネスロジックを推し進めることはできません。これにより、リファクタリングが難しくなり、ロジックが普及すればユースケースを監督することも難しくなります。 – Kai

関連する問題