#java #jboss #jar #classloader
#java #jboss #jar #classloader
Вопрос:
Я пытаюсь загрузить ресурс, который содержится во встроенном файле JAR. Проект фактически развернут в JBoss с использованием файла EAR со следующей структурой:
deploy.ear
|
|-> project.sar
|
|-> sub_project.jar
| |
| |-> settings.xml
|
|-> com/path/project/
|
|-> main.class
От main.java
я хотел бы получить InputStream
for settings.xml
. Каков правильный способ сделать это?
Насколько я понимаю, следующий код должен работать, но он возвращает null
:
this.getClass().getResourceAsStream("settings.xml");
Обновить
После некоторых проб и ошибок работают следующие инструкции:
getClass().getResourceAsStream("/settings.xml");
getClass().getResourceAsStream("/sub_project.jar/settings.xml");
getClass().getClassLoader().getResourceAsStream("/settings.xml");
getClass().getClassLoader().getResourceAsStream("settings.xml");
getClass().getClassLoader().getResourceAsStream("sub_project.jar/settings.xml");
getClass().getClassLoader().getResourceAsStream("/sub_project.jar/settings.xml");
Комментарии:
1. загрузчик классов Java не может загружать ресурсы из встроенных файлов jar, поэтому ваша настройка не будет работать. Решение one jar решает эту проблему, см. Ответ Эрана.
2. Не уверен, что /sub_project.jar/settings.xml это стандартная нотация. Может быть расширением JBoss.
3. Я был удивлен, почему «settings.xml «сбой, пока»/settings.xml » сработало, но затем я прочитал документацию: если имя ресурса начинается с «/», оно остается неизменным; в противном случае имя пакета добавляется к имени ресурса после преобразования «.» в «/». Class.class делает это, но ClassLoader.class не работает. Сегодня узнал кое-что новое…
Ответ №1:
Это может быть хорошим ресурсом: http://one-jar.sourceforge.net/version-0.95 /
Основная идея заключается в том, что внутренний JAR не загружается загрузчиком классов, который автоматически загрузил внешний JAR, вам нужно сделать это вручную, например, с помощью StreamClassLoader
для загрузки внутреннего jar
Только тогда из вашего собственного ClassLoader вы сможете получить этот ресурс с помощью getResourceAsStream(...)
Комментарии:
1. Вы указываете использовать One-Jar или просто используете его для справки о том, как получить доступ к внутреннему содержимому jar?
2. Обратите внимание, что верхний файл — это не JAR, а EAR; это означает, что он имеет более сложный загрузчик классов, чем стандартный. Загрузчики классов EAR обрабатывают загрузку ресурсов из вложенных JAR и WARs на основе содержимого META-INF.
3. @Vladimir: в исходном вопросе этого не было указано. В OP не была учтена эта важная деталь в исходном вопросе. Нажмите на
edited [time]
ссылку под вопросом для получения подробной информации.