4

I am refactoring a multimodule project that depends on one module -- shared-resources -- for both main and test resources.

parent |_ shared-resources |_ child 

Currently, a module includes the shared-resources by using the maven-resource-plugin.

current child/pom.xml:

... <resources> <resource> <directory>../shared-resources/src/main/resources</directory> </resource> </resources> <testResources> <testResource> <directory>../shared-resources/src/test/resources</directory> </testResource> </testResources> ... 

I would like to restructure the dependencies so that they are included via a jar and test-jar packaging of the shared-resources module, as some related questions (e.g. "Specify common resources in a multi-module maven project" and "Share test resources between maven projects") suggest.

new shared-resources/pom.xml:

... <build> <plugins> <plugin> <artifactId>maven-jar-plugin</artifactId> <executions> <execution> <goals> <goal>test-jar</goal> </goals> </execution> </executions> </plugin> </plugins> </build> ... 

new child/pom.xml:

... <dependency> <groupId>com.example</groupId> <artifactId>shared-resources</artifactId> <version>0.0.1</version> </dependency> <dependency> <groupId>com.example</groupId> <artifactId>shared-resources</artifactId> <version>0.0.1</version> <scope>test</scope> <type>test-jar</type> </dependency> ... 

When I run tests for child however, tests for lack of the resources.

I've run my build in a variety of ways:

maven clean test --projects child --also-make

maven clean install -DskipTests && mvn test --projects child

maven clean verify --projects child --also-make

My authoritative test has been mvn clean install -DskipTests -pl :child -am && mvn test -pl :child -Dtest='PropertiesAccessTest' where properties access test does:

 public class PropertiesAccessTest { @Test public void resourceAccessible() throws URISyntaxException, IOException { propertyExists( "abcdef=12345", "test.properties" ); } private void propertyExists(String string, String fileName) throws IOException, URISyntaxException { URL url = getClass().getClassLoader().getResource(fileName); assertNotNull(url); assertTrue("file should exist", new File(url.getFile()).exists()); assertTrue("file should contain property", Files.readAllLines(Paths.get(url.toURI())) .stream().anyMatch(l -> l.contains(string))); } } 

There is a corresponding test.properties in shared-resources/src/test/resources/ (which should be included as I understand the above config), but instead the test always fails with "file should exist."

I can verify that my local .m2 repository contains the test jar containing test resources as expected.

What am I doing wrong here?

8
  • What kind of resources are those shared-resource? I have the impression that those resource belong to the appropriate moduels? Commented Nov 27, 2017 at 9:35
  • What command do you run? Are you sure the shared-resources artifact is properly installed? Providing the entire POM for both project might help, art to said from the given elements. Commented Nov 27, 2017 at 11:41
  • @PierreB. I elaborated on my build commands above. For what it's worth, I can confirm that the contents of the share-resources jar and test jar are as expected. Commented Nov 27, 2017 at 14:12
  • @khmarbaise exploring the actual content of shared-resources seems off topic. No doubt it's not a perfect module structure and some stuff could be moved around, but it's out of scope for this question -- especially when, by all appearances, this is supported maven behavior. Commented Nov 27, 2017 at 14:15
  • Thanks. By When I run tests for child however, tests for lack of the resources. you mean the test lacks shared-resources, but the main app is able to access them properly? Or both main and tests lacks resources? Commented Nov 27, 2017 at 14:22

1 Answer 1

3

You placed your file into separate module. Which means that it's going to be embedded into JAR file now. You cannot create a File out of it anymore. But you can access it via URI and InputStream:

getClass().getClassLoader().getResource("test.properties").openStream() 

It's even more interesting with production resources though. Maven will use target/classes/test.properties if you run mvn test. And this will work with File. But if you run mvn package instead - it won't. Because after package Maven will put jar file into classpath instead of target/classes.

Sign up to request clarification or add additional context in comments.

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.