7

マーシャリングされていないオブジェクトのリストを反復処理しようとするとClassCastExceptions が発生することがあり、追跡が非常に困難な問題が発生しています。重要なビットは時々、再起動後に特定のコードが正常に動作することです。これは、同時実行/タイミング/競合状態の方向を示しているようです。JAXBContext も、マーシャラーとアンマーシャラーも同時に使用されていないことを確認できます。ロックによってそれらへのアクセスをシリアル化するところまで行きました。

ただし、Spring DM を介して個々のバンドルが非同期に初期化される OSGi プラットフォームで実行しているため、2 つの異なるバンドルが同時に JAXBContext を作成している可能性があります。

いずれにせよ、これらの断続的なClassCastExceptions を引き起こす可能性のある原因についての説明へのポインタをいただければ幸いです。コード自体は正常に動作しているが、何らかの外部要因が動作に影響を与えているように見えることを示すため、断続的であることが重要です。

例外の具体例を次に示します (会社固有のものを削除したことに注意してください)。

Caused by: java.lang.ClassCastException: com.sun.org.apache.xerces.internal.dom.ElementNSImpl cannot be cast to com.foobar.TunnelType
    at com.foobar.NetMonitorImpl.getVpnStatus(NetMonitorImpl.java:180)

180行目のそのメソッドは、アンマーシャリングされたオブジェクト内のTunnelTypeオブジェクトのコレクションをループするfor()コンストラクトです(アンマーシャリングは問題なく機能します)。

実際のオブジェクトのアンマーシャリングが正常に行われたとすると、JAXB が ElementNSImpl オブジェクトをネストされたコレクション内に残すことは物理的に可能でしょうか?

実行時環境:

  • JAXB2.1
  • OSGi
  • 春のDM
  • JAXBContext は、整列化/非整列化されるクラスを含むバンドルの ClassLoader で初期化されます
4

4 に答える 4

4

この例外が発生するのは、JAXBContext が扱う可能性のあるマーシャリングされるすべての型について JAXBContext に伝えるのを忘れた場合のみです。

JAXBContext.newInstance(MyClass1.class,MyClass2.class, [...]);
于 2009-03-22T01:49:33.957 に答える
2

ここで提案されているアプローチはどちらも私には役に立ちませんでした。しかし、これは私の問題を解決しました

@XmlAnyElement(lax = true)
public List<Foo> foos;
于 2012-01-10T13:02:34.420 に答える
0

The synchronized clause above resolved the issue for me as well, but it seems like the context should not be a local variable. Instead it should be an instance variable, or a static. I wasn't able to refactor my code how I'd like it, so instead I moved the context into a static initializer, which isn't perfect, but seems to work:

 private static Unmarshaller um;

  static{
    try {
      final JAXBContext ctx = JAXBContext.newInstance(ObjectFactory.class.getPackage().getName());
      um = ctx.createUnmarshaller();
    } catch (final JAXBException e) {
      e.printStackTrace();
    }
  }
于 2011-02-22T17:07:46.390 に答える
0

絶望から、JAXBContext.classオブジェクトの同期に目を向けました。これが何らかの競合状態の唯一の残りの可能性であり、少なくともこの問題を再現することはできませんでした。重要なコードは次のとおりです。

synchronized (JAXBContext.class) {
    context = JAXBContext.newInstance(packageList, classLoader);
}
于 2009-07-21T11:53:21.463 に答える