Problème
Lorsque vous utilisez des bibliothèques tierces dans un regroupement OSGi, vous obtenez des problèmes de chargement de classe tels que les suivants :
Le mypackage.FooBar d'usine demandé est introuvable. Classloader =java.net.URLClassLoader@6aa8d01c
Note: cette erreur est juste un exemple de message d'erreur. Le problème réside dans le fait que les classes chargées par des bibliothèques tierces sont introuvables, même si la classe correspondante est définitivement importée.
Exemple réel.
Apache Axis2 pourrait lancer la trace d'appels (stacktrace) suivante, sans raison spécifique :
18.02.2010 17:04:30.153 *INFO* [10.43.97.19 [1266509048609] POST /path/to/servlet HTTP/1.1] org.apache.axis2.transport.http.HTTPSender Unable to sendViaPost to url[xy] org.apache.axis2.AxisFault: Requested factory com.ctc.wstx.stax.WstxOutputFactory cannot be located. Classloader =java.net.URLClassLoader@6aa8d01c at org.apache.axis2.AxisFault.makeFault(AxisFault.java:430) at org.apache.axis2.transport.http.AxisRequestEntity.writeRequest(AxisRequestEntity.java:96) at org.apache.commons.httpclient.methods.EntityEnclosingMethod.writeRequestBody(EntityEnclosingMethod.java:499) ...
Solution
Vous ne pouvez pas définir la façon dont les bibliothèques tierces chargent leurs classes. Dans la plupart des cas, cela fonctionne, si la bibliothèque tierce utilise le chargeur de classe normal du lot. Mais parfois une bibliothèque, comme Apache Axis2, peut tenter de charger une classe similaire à ce qui suit :
Thread.currentThread().getContextClassLoader().loadClass("mypackage.FooBar");
Par défaut, le chargeur de classes de contexte Thread ne connaît pas OSGi et ne voit donc aucune des classes importées dans le lot. C’est pourquoi le chargement de la classe échoue.
Dans votre code, avant que le code tiers ne soit exécuté, vous pouvez indiquer au thread en cours d'utiliser le chargeur de classe à partir du lot. Procédez ainsi temporairement pour le code tiers qui ne charge pas certaines classes :
ClassLoader tccl = Thread.currentThread().getContextClassLoader(); Thread.currentThread().setContextClassLoader(this.getClass().getClassLoader()); try { // execute 3rd party code } finally { Thread.currentThread().setContextClassLoader(tccl); }
S’applique à
CQ5.x, AEM6.x.
Accéder à votre compte