getClassLoader (). getResourceAsStream () не работает в модульном java проекте (openjdk 11)? - PullRequest
1 голос
/ 20 апреля 2020

это проект maven , имеющий одно изображение в каталоге ресурсов :

├─ src
   ├─ main
       ├─ java
       └─ resources  
          └─imgs
            └─logo.png

Код:

public class Test {
    public static void main(String[] args) {
        InputStream stream = Test.class.getClassLoader().getResourceAsStream("/imgs/logo.png");
        InputStream stream1 = Test.class.getClassLoader().getResourceAsStream("imgs/logo.png");
        System.out.println(stream == null ? "stream is null!" : "stream is not null!");
        System.out.println(stream1 == null ? "stream1 is null!" : "stream1 is not null!");
    }
}

при Я добавлю module-info.java к проекту, напечатаю:

stream is null!
stream1 is null!

, но когда я удалю module-info.java из проекта, напечатаю:

stream is null!
stream1 is not null!

почему? а как использовать ClassLoader для загрузки ресурсов в модульном java проекте?

1 Ответ

2 голосов
/ 20 апреля 2020

Ресурсы должны быть загружены поверх Test.class, а не его ClassLoader. Загружая ресурс над классом, вы устанавливаете sh контекст (JAR, модуль, зависимости) для расположения ресурса.

Для ресурсов в том же пакете используйте относительный путь:

Test.class.getResource("logo.png")

Если квалифицированное имя Test равно org.foo.Test, он будет искать ресурс в org/foo/logo.png в JAR (или в папке ресурсов, перед сборкой JAR).

Для ресурсов в том же модуле используйте абсолютный путь, начиная с sla sh:

Test.class.getResource("/logo.png")

^ это то, что вы хотите использовать большую часть время.

Нет необходимости go над загрузчиком классов . Я часто вижу это, когда разработчики не знают, как правильно обращаться к ресурсу, и загружают ресурс с относительным путем , но поверх загрузчика классов , который работает большую часть времени, но не очень хорошо с модульными проектами / загрузчиками классов, такими как Java9 и OSGI.

...