Websphere: общие библиотеки в общем загрузчике классов раньше на пути к классам, чем модули приложений, даже с родительской последней политикой
Предыстория: у меня следующая проблема: у меня есть несколько файлов WAR, которые необходимо развернуть на одном сервере Websphere. В файлах WAR используются библиотеки, которые зависят от наличия определенной версии XMLSec, зарегистрированной в качестве поставщика подписи XML (с классом безопасности Java). В настоящее время я связываю эту библиотеку с каждым файлом WAR (поскольку файлы WAR также должны работать автономно и на Tomcat без какой-либо специальной конфигурации совместно используемой библиотеки и т. Д.). Каждый WAR-файл регистрирует провайдера с помощью Security.addProvider () в ServerContextListener. Но это вызывает проблемы в настройке нескольких WAR, потому что, если один WAR-файл выполняет регистрацию с помощью Security.addProvider), а другой WAR-файл пытается извлечь его с помощью класса XML SignatureFactory (который на самом деле является классом javax. *, Содержащимся в XMLSec JAR сам, но который в конечном счете вызывает обратно к глобальному списку провайдеров, настроенному с помощью Security.addProvider), то он вызывает ClassCastException внутри XML SignatureFactory, потому что этот класс выполняет приведение того, что он получает от Security, к его собственной версии классов провайдеров, которая не работает Точная трассировка стека выглядит следующим образом:
Вызывается: java.lang.ClassCastException: org.apache.jcp.xml.dsig.internal.dom.DOMXMLSignatureFactory несовместимо с javax.xml.crypto.dsig.XMLSignatureFactory в javax.xml.crypto.dsig.XactactignFatureFignFignSignFignature Java:202) в javax.xml.crypto.dsig.XMLSignatureFactory.getInstance(XMLSignatureFactory.java:292)
Кстати, это не тот случай, когда разные версии XMLSec находятся в игре или конфликтуют с собственной версией Websphere. Существует только одна версия, хотя она загружена из разных WAR.
Конечно, решение состоит в том, чтобы загрузить библиотеку xmlsec с общим загрузчиком классов, чтобы была загружена только одна версия классов, которую видят все файлы WAR, что позволило бы избежать ClassCastExceptions и т. Д. Но вот в чем проблема: мне также нужно иметь каждое приложение загружено политикой "родительский последний", или, точнее, мне нужны файлы JAR внутри каждого приложения, чтобы иметь приоритет над встроенной версией библиотек Websphere (например, Axis2, которую я также включаю в набор файлов WAR). Более того, я бы предпочел, чтобы я мог хранить библиотеку xmlsec в папке WEB-INF/lib каждого файла WAR, чтобы файлы WAR могли работать автономно (т. Е. В других средах, в которых не может быть настроена общая библиотека и т. Д.).).
В общем, я хочу иметь общий загрузчик классов, загружающий библиотеку XMLSec, скажем, где-нибудь с диска. Давайте обозначим это [SHARED XMLSEC]. Затем я хочу, чтобы каждый путь к классу приложения в конечном итоге выглядел так:
App1: [SHARED XMLSEC][App1 WEB-inf / lib][библиотеки Websphere][библиотеки JDK]
App2: [SHARED XMLSEC][App2 WEB-inf / lib][библиотеки Websphere][библиотеки JDK]
и т.п.
В такой конфигурации не имеет значения, содержат ли сами App1+App2 библиотеку XMLSec, поскольку общая будет иметь приоритет, поэтому они будут использовать общую. В то же время App1+App2 по-прежнему могут переопределять другие встроенные библиотеки Websphere (Axis2).
Можно ли реализовать эту конфигурацию и какие опции мне нужно установить? Видите ли вы альтернативные способы достижения той же цели?
1 ответ
Поскольку у вас есть конфликт между классами, я бы предложил использовать для каждого приложения загрузчики изолированных классов. На стороне сервера установка политики загрузчика классов на "Несколько" должна обеспечивать изоляцию между приложениями.
Если у вас есть этот набор, настройте загрузку классов на уровне приложения для конфигурации "Родитель последний" для обоих приложений.
Следующая ссылка на Центр знаний содержит соответствующие инструкции [шаги 2,3 и 4 в разделе "Процедура"]: http://www.ibm.com/support/knowledgecenter/en/SSAW57_8.5.5/com.ibm.websphere.nd.multiplatform.doc/ae/trun_classload.html
[Примечание: используемая версия WAS не указана в вопросе. Ссылка на Центр знаний относится к версии 8.5.5.]