I am writing an extension to a maven mojo (spring-cloud-skipper-maven-plugin) and I am now writing tests that interact with a skipper server.
However, getting the maven-plugin-testing-harness
to work was a pain and meant I had to include the dependency org.eclipse.sisu.plexus
.
In the end, it also meant I had to inject some fields manually using reflection because spring auto wiring was failing.
This is working perfectly now but it can definitely be improved with some tips about what should be fixed.
package io.switchbit;
import org.apache.maven.model.Model;
import org.apache.maven.model.io.xpp3.MavenXpp3Reader;
import org.apache.maven.plugin.AbstractMojo;
import org.apache.maven.plugin.testing.AbstractMojoTestCase;
import org.apache.maven.project.MavenProject;
import org.junit.Before;
import org.junit.Test;
import java.io.File;
import java.io.FileReader;
import java.lang.reflect.Field;
public class AUnitTest
extends AbstractMojoTestCase
{
private String SKIPPER_SERVER_URI = "http://SERVER:7577/api";
AbstractMojo step1SkipperPackage;
AbstractMojo step2SkipperUpload;
AbstractMojo step3SkipperInstall;
AbstractMojo step4SkipperDelete;
/**
* @see junit.framework.TestCase#setUp()
*/
@Before
protected void setUp() throws Exception
{
// required for step1SkipperPackage lookups to work
super.setUp();
File testPom = new File( getBasedir(),
"src/test/resources/testProject/testPom.xml" );
step1SkipperPackage = initializeMojo(testPom, "skipper-package");
step2SkipperUpload = initializeMojo(testPom, "skipper-upload");
step3SkipperInstall= initializeMojo(testPom, "skipper-install");
step4SkipperDelete = initializeMojoDelete(testPom, "skipper-delete");
}
private AbstractMojo initializeMojo(File testPom, String skipperPackage) throws Exception {
MavenProject mavenProject = readMavenModel(testPom);
AbstractMojo initMojo = (AbstractMojo) lookupMojo( skipperPackage , testPom );
initializeMojoFields(mavenProject, initMojo);
return initMojo;
}
private AbstractMojo initializeMojoDelete(File testPom, String skipperPackage) throws Exception {
MavenProject mavenProject = readMavenModel(testPom);
AbstractMojo initMojo = new SkipperDeleteMojo();
initializeMojoFields(mavenProject, initMojo);
return initMojo;
}
private void initializeMojoFields(MavenProject mavenProject, AbstractMojo mojo) throws NoSuchFieldException, IllegalAccessException {
File workDirectory = new File( getBasedir(),
"src/test/resources/testProject/target/skipper/");
File overrideDirectory = new File( getBasedir(),
"src/test/resources/testProject/target/classes/META-INF/skipper");
//Set the properties
setPrivateField(mojo, "project", mavenProject, false);
setPrivateField(mojo, "workDirectory", workDirectory, true);
setPrivateField(mojo, "overrideDirectory", overrideDirectory, true);
setPrivateField(mojo, "SUBSTRING_SKIPPER_SEPARATOR", "/skipper", true);
setPrivateField(mojo, "skipperServerUri", SKIPPER_SERVER_URI, true);
setPrivateField(mojo, "repoName", "local", true);
}
private void setPrivateField(Object objectInstance,String fieldName, Object fieldSetValue, boolean optional) throws NoSuchFieldException, IllegalAccessException {
try{
Field declaredField = objectInstance.getClass().getDeclaredField(fieldName);
declaredField.setAccessible(true);
declaredField.set(objectInstance, fieldSetValue);
}catch(java.lang.NoSuchFieldException e){
if(!optional){
throw e;
}
}
}
private MavenProject readMavenModel(File testPom) {
Model model = null;
FileReader reader = null;
MavenXpp3Reader mavenreader = new MavenXpp3Reader();
try {
reader = new FileReader(testPom);
model = mavenreader.read(reader);
model.setPomFile(testPom);
}catch(Exception ex){}
return new MavenProject(model);
}
/**
* @throws Exception
*/
@Test
public void testSimpleStep1to3PackageToDelete() throws Exception
{
step1SkipperPackage.execute();
step2SkipperUpload.execute();
step3SkipperInstall.execute();
Thread.sleep(10000);
//TODO: Log message here
step4SkipperDelete.execute();
}
@Test
public void testStep4Delete() throws Exception
{
try{
step4SkipperDelete.execute();
}catch (Exception e){
if(!e.getMessage().contains("404")){ //Allow this to be run even if steps 1 to 3 are not
throw e;
}
}
}
}
And I have added the following two dependencies to my maven pom.xml:
<dependency>
<groupId>org.eclipse.sisu</groupId>
<artifactId>org.eclipse.sisu.plexus</artifactId>
<version>0.3.3</version>
</dependency>
<dependency>
<groupId>org.apache.maven.plugin-testing</groupId>
<artifactId>maven-plugin-testing-harness</artifactId>
<version>3.3.0</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.eclipse.sisu</groupId>
<artifactId>org.eclipse.sisu.plexus</artifactId>
<version>0.3.3</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.12</version>
</dependency>
So things that I am feeling are wrong but I don't know how to fix easily right now are and are in need of review:
- I thought the
maven testing harness
andAbstractMojoTestCase
should help with the mavenProject but I ended up needing to useMavenXpp3Reader
. - It was bit annoying using reflection to set private fields within the MOJOs... I expected that everything would function like when the MOJOs are executed from
mvn
using e.g.mvn deploy
ormvn skipper:skipper-install
.
The original code I have forked locally is @: https://github.com/donovanmuller/spring-cloud-skipper-maven-plugin/blob/master/src/main/java/io/switchbit/SkipperPackageMojo.java