From 8f1647fe09e5a8193db23fa5c8316a4eef1be9e0 Mon Sep 17 00:00:00 2001 From: Stuart Douglas Date: Thu, 26 Jul 2018 10:06:59 +1000 Subject: [PATCH] Move responsibility for generating native images to a maven plugin To test the native image you now need to add -Dnative to the command line --- examples/everything/pom.xml | 64 +++++++---- examples/strict/pom.xml | 54 ++++++--- .../jaxrs/JaxrsScanningProcessor.java | 5 +- .../jboss/shamrock/maven/NativeImageMojo.java | 108 ++++++++++++++++++ .../jboss/shamrock/maven/ShamrockMojo.java | 2 +- .../org/jboss/shamrock/junit/GraalTest.java | 36 ------ 6 files changed, 198 insertions(+), 71 deletions(-) create mode 100644 maven/src/main/java/org/jboss/shamrock/maven/NativeImageMojo.java diff --git a/examples/everything/pom.xml b/examples/everything/pom.xml index 673a8a8a1..c3886a956 100644 --- a/examples/everything/pom.xml +++ b/examples/everything/pom.xml @@ -87,23 +87,6 @@ - - org.apache.maven.plugins - maven-failsafe-plugin - - - - integration-test - verify - - - - - - true - - - ${project.groupId} shamrock-maven-plugin @@ -111,7 +94,7 @@ - run + build @@ -155,10 +138,12 @@ - + org.jboss.shamrock.runner.Main - + @@ -187,5 +172,44 @@ + + + native-image + + + native + + + + + + org.apache.maven.plugins + maven-failsafe-plugin + + + + integration-test + verify + + + + + + ${project.groupId} + shamrock-maven-plugin + ${project.version} + + + native-image + + native-image + + + + + + + + \ No newline at end of file diff --git a/examples/strict/pom.xml b/examples/strict/pom.xml index e93c67c2a..b45cb9b31 100644 --- a/examples/strict/pom.xml +++ b/examples/strict/pom.xml @@ -78,18 +78,6 @@ - - org.apache.maven.plugins - maven-failsafe-plugin - - - - integration-test - verify - - - - ${project.groupId} shamrock-maven-plugin @@ -97,7 +85,7 @@ - run + build @@ -167,5 +155,45 @@ + + + native-image + + + native + + + + + + org.apache.maven.plugins + maven-failsafe-plugin + + + + integration-test + verify + + + + + + ${project.groupId} + shamrock-maven-plugin + ${project.version} + + + native-image + + native-image + + + + + + + + + \ No newline at end of file diff --git a/jaxrs/deployment/src/main/java/org/jboss/shamrock/jaxrs/JaxrsScanningProcessor.java b/jaxrs/deployment/src/main/java/org/jboss/shamrock/jaxrs/JaxrsScanningProcessor.java index c72f05ce4..c2c5d2ba1 100755 --- a/jaxrs/deployment/src/main/java/org/jboss/shamrock/jaxrs/JaxrsScanningProcessor.java +++ b/jaxrs/deployment/src/main/java/org/jboss/shamrock/jaxrs/JaxrsScanningProcessor.java @@ -190,7 +190,10 @@ public class JaxrsScanningProcessor implements ResourceProcessor { for (AnnotationInstance instance : instances) { MethodInfo method = instance.target().asMethod(); if (method.returnType().kind() == Type.Kind.CLASS) { - processorContext.addReflectiveClass(method.returnType().asClassType().name().toString()); + String className = method.returnType().asClassType().name().toString(); + if(!className.equals(String.class.getName())) { + processorContext.addReflectiveClass(className); + } } } } diff --git a/maven/src/main/java/org/jboss/shamrock/maven/NativeImageMojo.java b/maven/src/main/java/org/jboss/shamrock/maven/NativeImageMojo.java new file mode 100644 index 000000000..13ab5976d --- /dev/null +++ b/maven/src/main/java/org/jboss/shamrock/maven/NativeImageMojo.java @@ -0,0 +1,108 @@ +package org.jboss.shamrock.maven; + +import java.io.File; +import java.io.IOException; +import java.io.InputStream; +import java.util.ArrayList; +import java.util.List; + +import org.apache.maven.artifact.Artifact; +import org.apache.maven.plugin.AbstractMojo; +import org.apache.maven.plugin.MojoExecutionException; +import org.apache.maven.plugin.MojoFailureException; +import org.apache.maven.plugins.annotations.LifecyclePhase; +import org.apache.maven.plugins.annotations.Mojo; +import org.apache.maven.plugins.annotations.Parameter; +import org.apache.maven.plugins.annotations.ResolutionScope; +import org.apache.maven.project.MavenProject; + +@Mojo(name = "native-image", defaultPhase = LifecyclePhase.PACKAGE, requiresDependencyResolution = ResolutionScope.RUNTIME) +public class NativeImageMojo extends AbstractMojo { + + @Parameter(defaultValue = "${project}", readonly = true, required = true) + protected MavenProject project; + + /** + * The directory for compiled classes. + */ + @Parameter(readonly = true, required = true, defaultValue = "${project.build.outputDirectory}") + private File outputDirectory; + + @Parameter(defaultValue = "false") + private boolean reportErrorsAtRuntime; + + @Parameter(defaultValue = "false") + private boolean debugSymbols; + + @Parameter(readonly = true, required = true, defaultValue = "${project.build.finalName}") + private String finalName; + + @Override + public void execute() throws MojoExecutionException, MojoFailureException { + + String graal = System.getenv("GRAALVM_HOME"); + if (graal == null) { + throw new MojoFailureException("GRAALVM_HOME was not set"); + } + String nativeImage = graal + File.separator + "bin" + File.separator + "native-image"; + + StringBuilder cp = new StringBuilder(); + cp.append(outputDirectory); + for (Artifact dep : project.getArtifacts()) { + if (!dep.getScope().equals("test")) { + cp.append(File.pathSeparator); + cp.append(dep.getFile().getAbsolutePath()); + } + } + + try { + List command = new ArrayList<>(); + command.add(nativeImage); + command.add("--no-server"); + command.add("-cp"); + command.add(cp.toString()); + command.add("-H:IncludeResources=META-INF/.*"); + command.add("org.jboss.shamrock.runner.Main"); + if (reportErrorsAtRuntime) { + command.add("-H:+ReportUnsupportedElementsAtRuntime"); + } + if (debugSymbols) { + command.add("-g"); + } + command.add(finalName); + + System.out.println(command); + Process process = Runtime.getRuntime().exec(command.toArray(new String[0]), new String[]{}, new File(outputDirectory.getParent())); + new Thread(new ProcessReader(process.getInputStream())).start(); + new Thread(new ProcessReader(process.getErrorStream())).start(); + if (process.waitFor() != 0) { + throw new RuntimeException("Image generation failed"); + } + + } catch (Exception e) { + throw new MojoFailureException("Failed to build native image", e); + } + } + + private static final class ProcessReader implements Runnable { + + private final InputStream inputStream; + + private ProcessReader(InputStream inputStream) { + this.inputStream = inputStream; + } + + @Override + public void run() { + byte[] b = new byte[100]; + int i; + try { + while ((i = inputStream.read(b)) > 0) { + System.out.print(new String(b, 0, i)); + } + } catch (IOException e) { + e.printStackTrace(); + } + } + } +} diff --git a/maven/src/main/java/org/jboss/shamrock/maven/ShamrockMojo.java b/maven/src/main/java/org/jboss/shamrock/maven/ShamrockMojo.java index 0f1773538..2997dc036 100644 --- a/maven/src/main/java/org/jboss/shamrock/maven/ShamrockMojo.java +++ b/maven/src/main/java/org/jboss/shamrock/maven/ShamrockMojo.java @@ -14,7 +14,7 @@ import org.apache.maven.project.MavenProject; import org.jboss.shamrock.deployment.ClassOutput; import org.jboss.shamrock.deployment.Runner; -@Mojo(name = "run", defaultPhase = LifecyclePhase.PROCESS_CLASSES) +@Mojo(name = "build", defaultPhase = LifecyclePhase.PROCESS_CLASSES) public class ShamrockMojo extends AbstractMojo { /** diff --git a/test-framework/graal/src/main/java/org/jboss/shamrock/junit/GraalTest.java b/test-framework/graal/src/main/java/org/jboss/shamrock/junit/GraalTest.java index 062cbec72..f77226727 100644 --- a/test-framework/graal/src/main/java/org/jboss/shamrock/junit/GraalTest.java +++ b/test-framework/graal/src/main/java/org/jboss/shamrock/junit/GraalTest.java @@ -1,14 +1,8 @@ package org.jboss.shamrock.junit; -import java.io.ByteArrayOutputStream; -import java.io.File; import java.io.IOException; import java.io.InputStream; import java.net.URL; -import java.util.ArrayList; -import java.util.List; -import java.util.concurrent.CompletableFuture; -import java.util.function.BiConsumer; import org.junit.runner.Description; import org.junit.runner.Result; @@ -44,17 +38,8 @@ public class GraalTest extends BlockJUnit4ClassRunner { } private void runInternal(RunNotifier notifier) { - boolean reportAtRuntime = Boolean.getBoolean("graal.reportAtRuntime"); - boolean debugSymbols = Boolean.getBoolean("graal.debugSymbols"); if (first) { first = false; - String graal = System.getenv("GRAALVM_HOME"); - if (graal == null) { - notifier.fireTestFailure(new Failure(Description.createSuiteDescription(GraalTest.class), new RuntimeException("GRAALVM_HOME was not set"))); - return; - } - String nativeImage = graal + File.separator + "bin" + File.separator + "native-image"; - URL mainClassUri = getClass().getClassLoader().getResource("org/jboss/shamrock/runner/Main.class"); if (mainClassUri == null) { notifier.fireTestFailure(new Failure(Description.createSuiteDescription(GraalTest.class), new RuntimeException("Unable to find shamrock main class"))); @@ -69,27 +54,6 @@ public class GraalTest extends BlockJUnit4ClassRunner { String path = externalForm.substring(5, jar); try { - - List command = new ArrayList<>(); - command.add(nativeImage); - command.add("-jar"); - command.add(path); - command.add("-H:IncludeResources=META-INF/.*"); - if(reportAtRuntime) { - command.add("-H:+ReportUnsupportedElementsAtRuntime"); - } - if(debugSymbols) { - command.add("-g"); - } - command.add("--no-server"); - Process process = Runtime.getRuntime().exec(command.toArray(new String[0]), new String[]{}, new File(path.substring(0, path.lastIndexOf(File.separator)))); - new Thread(new ProcessReader(process.getInputStream())).start(); - new Thread(new ProcessReader(process.getErrorStream())).start(); - if (process.waitFor() != 0) { - notifier.fireTestFailure(new Failure(Description.createSuiteDescription(GraalTest.class), new RuntimeException("Image generation failed"))); - return; - } - String outputFile = path.substring(0, path.lastIndexOf('.')); System.out.println("Executing " + outputFile); final Process testProcess = Runtime.getRuntime().exec(outputFile);