2017-02-14 3 views
0

私は今この問題で2日から苦労しており、私はそれを手に入れることができません。私がする必要がどのようなコレクションに含まれるオブジェクトをフィールドとその逆にマップするにはどうすればよいですか? Dozer

public class ClientBo{ 
    ... 
    List<PersonBo> person; 
    ... 
} 

public class ClientVo{ 
    ... 
    PersonVo person; 
    ... 
} 

は何とかドーザを設定することですので、私は単一のフィールドPersonVoにPersonBo一覧からマッピングすることができます(Voのボーは、同じフィールド名を持つ):私が持っています。

Dozerには、コレクションから単一フィールドに変換するビルドイン機能がありますが、それ以外の方法はありません。 http://dozer.sourceforge.net/documentation/faq.html#mult-fields-to-single-field

私は考え出した唯一の解決策は以下のとおりです。

<mapping type="one-way"> 
    <class-a>...ClientBo</class-a> 
    <class-b>...ClientVo</class-b> 
    <field> 
     <a>person[0]</a> 
     <b>person</b> 
    </field> 
</mapping> 
<mapping type="one-way"> 
    <class-a>...ClientVo</class-a> 
    <class-b>...ClientBo</class-b> 
    <field custom-converter="mapper.CustomObjectToList"> 
     <a>person</a> 
     <b>person</b> 
    </field> 
</mapping> 

public class CustomObjectToList implements CustomConverter{ 

     public Object convert(Object existingDestinationFieldValue, Object sourceFieldValue, Class<?> destinationClass, Class<?> sourceClass) { 
      if(sourceFieldValue==null) 
       return null; 

      if(sourceFieldValue instanceof List && ((List<?>) sourceFieldValue).size()>0){ 
       /* This if is an attempt to get the first element of the 
       list and return it as a single field, but id doesn't work*/ 
       Object o = ((List<?>)sourceFieldValue).get(0); 
       return o; 


      }else{ 
       /*Here a single field is put in a List and returned*/ 
       ArrayList<Object> result = new ArrayList<>(); 
       result.add(sourceFieldValue); 
       return result; 
      } 
     } 
    } 

ので、私は

<mapping type="one-way"> 
     <class-a>...ClientBo</class-a> 
     <class-b>...ClientVo</class-b> 
     <field> 
      <a>person[0]</a> 
      <b>person</b> 
     </field> 
    </mapping> 

を削除することができますし、仕事を得る方法はありますカスタムコンバータで?できるだけ汎用的でなければならないので、同様のコンテキストに収めることができます。

ありがとうございます!

答えて

1

1. CustomConverterをテストしましたか?

ので、あなたはこのように、ClassCastExceptionを持っているでしょう変数のいずれかをプリントアウトしようとした場合:

Exception in thread "main" java.lang.ClassCastException: beans.PersonVo cannot be cast to beans.PersonBo 
    at execute.Execute.main(Execute.java:37) 

はい、同じ名前のフィールドが自動的にマッピングされたのですか、しかし、あなたのケースであなたは、 CustomConverterを使用してマッピングを行います。言い換えれば、Dozerはあなたにそれを世話すると信じているので、ただ一つのClass変数(personVo)を別の無関係なClassインスタンス(personBo)に向けることはできません。上記の例外

に上記の例外を修正する最も簡単な方法の修正

2.あなたが希望のような任意の無関係なクラスに対して、setterメソッドとgetterメソッドを使用することです:

public class CustomObjectToList implements CustomConverter{ 

public Object convert(Object existingDestinationFieldValue, Object sourceFieldValue, Class<?> destinationClass, Class<?> sourceClass) { 
    if(sourceFieldValue==null) 
     return null; 

    if(sourceFieldValue instanceof List && ((List<?>) sourceFieldValue).size()>0){ 
     /* This if is an attempt to get the first element of the 
     list and return it as a single field, but id doesn't work*/ 
     Object o = ((List<?>)sourceFieldValue).get(0); 
     return o; 


    }else{ 
     /*Updated: using a setter and getter*/ 
     PersonVo source = (PersonVo) sourceFieldValue; 
     List<PersonBo> dest = new ArrayList<PersonBo>(); 

     PersonBo bo = new PersonBo(); 
     bo.setName(source.getName()); 
     dest.add(bo); 
     return dest; 
    } 
} 
} 

3.質問への回答

一方向マッピングを廃止してCustomConverterのみを使用するには、次のようにします。

ドーザXML:

<!-- <mapping type="one-way"> 
    <class-a>beans.ClientBo</class-a> 
    <class-b>beans.ClientVo</class-b> 
    <field> 
     <a>person[0]</a> 
     <b>person</b> 
    </field> 
</mapping> --> 
<mapping> 
    <class-a>beans.ClientVo</class-a> 
    <class-b>beans.ClientBo</class-b> 
    <field custom-converter="converter.CustomObjectToList"> 
     <a>person</a> 
     <b>person</b> 
    </field> 
</mapping> 

CustomConverter:

public class CustomObjectToList implements CustomConverter{ 

public Object convert(Object existingDestinationFieldValue, Object sourceFieldValue, Class<?> destinationClass, Class<?> sourceClass) { 
     if(sourceFieldValue==null) 
      return null; 

     if(sourceFieldValue instanceof PersonVo){ 
      PersonVo source = (PersonVo) sourceFieldValue; 
      List<PersonBo> dest = new ArrayList<PersonBo>(); 

      PersonBo bo = new PersonBo(); 
      bo.setName(source.getName()); 
      dest.add(bo); 
      return dest; 

     }else if (sourceFieldValue instanceof List<?>){ 
      List<PersonBo> source = (List<PersonBo>) sourceFieldValue; 

      PersonVo dest = new PersonVo(); 
      dest.setName(source.get(0).getName()); 
      return dest; 
     } 
     else { 
      throw new MappingException("Converter TestCustomConverter " 
       + "used incorrectly. Arguments passed in were:" 
       + existingDestinationFieldValue + " and " + sourceFieldValue); 
      } 
    } 
} 
関連する問題