2016-01-10 16 views
0

我需要編寫代碼來處理帶有JSON消息正文的REST請求,如下所示。EclipseLink MOXy JSON提供程序給ClassCastException

[ 
    { 
    "name": "Foo", 
    "description": "An entity" 
    }, 
    { 
    "name": "Bar", 
    "description": "Another entity" 
    } 
] 

這在下面的類的實例的JSON陣列,也就是被序列化。處理請求路徑的方法(使用@Path註解)需要一個數組參數。方法簽名是:public Response update(MyClass[] objects)

@XmlRootElement 
public class MyClass { 

    @XmlAttribute 
    String name; 

    @XmlAttribute 
    String description; 

    // getters & setters 
} 

我在服務器上使用澤西2.6 MOXyJsonProvider(與MoxyJsonFeature註冊),但我得到一個ClassCastException:

java.lang.ClassCastException: MyClass cannot be cast to javax.xml.bind.JAXBElement 
    org.eclipse.persistence.jaxb.rs.MOXyJsonProvider.readFrom(MOXyJsonProvider.java:598) 
    org.glassfish.jersey.message.internal.ReaderInterceptorExecutor$TerminalReaderInterceptor.invokeReadFrom(ReaderInterceptorExecutor.java:251) 
    .... 

建議的修復在很多職位是添加@XmlRootElement註解,但我已經有了。有人可以幫我做這個工作嗎?非常感謝。

編輯:追加其他信息,以防萬一。

通過其中發生異常的代碼步進,我看到的是,在org.eclipse.persistence.jaxb.rs.MOXyJsonProvider::readFrom方法,所述unmarshaller.unmarshal(....)呼叫(在下面的代碼提取第一行)返回一個JAXBElement對象與value字段是包含2個MyClass實例的ArrayList我想要的。下一行的條件if評估爲false,因此執行進入else子句。由於jaxbElement.getValue()ArrayList,因此投射到ArrayList<JAXBElement>。最終它會在下面摘錄結尾處進入for-loop,並且在arrayList的每個項目上調用getValue(),期望每個項目都是JAXBElement。但是列表中的實際項目是MyClass個實例,並且在第一個項目上調用getValue()將引發ClassCastException

我懷疑修補程序會在我的MyClass定義中的註釋中發生一些變化。

 .... 
     JAXBElement<?> jaxbElement = unmarshaller.unmarshal(jsonSource, domainClass); 
     if(type.isAssignableFrom(JAXBElement.class)) { 
      return jaxbElement; 
     } else { 
      Object value = jaxbElement.getValue(); 
      if(value instanceof ArrayList) { 
       if(type.isArray()) { 
        ArrayList<JAXBElement> arrayList = (ArrayList<JAXBElement>) value; 
        int arrayListSize = arrayList.size(); 
        Object array; 
        if(genericType instanceof GenericArrayType) { 
         array = Array.newInstance(JAXBElement.class, arrayListSize); 
         for(int x=0; x<arrayListSize; x++) { 
          Array.set(array, x, arrayList.get(x)); 
         } 
        } else { 
         array = Array.newInstance(domainClass, arrayListSize); 
         for(int x=0; x<arrayListSize; x++) { 
          Array.set(array, x, arrayList.get(x).getValue()); 
         // ^^^^^^^ In the above line, arrayList.get(x) is a 
         // MyClass instance. It is not a JAXBElement 
         } 
        } 
      .... 

回答

0

現在工作後,我從改變方法的簽名:

public Response update(MyClass[] objects) 

到:

public Response update(List<MyClass> objects) 

一位同事告訴我要試試。希望我早點問過他。 :(

因此,這解決了我的問題,但我不知道MyClass一些不同的註釋是否會得到它的工作,併產生一個數組而不是一個列表;或者如果這是MOXyJsonProvider中的錯誤;或者如果有是使其與數組類型參數一起工作所需的自定義代碼。