1 /*
   2  * Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
   3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
   4  *
   5  * This code is free software; you can redistribute it and/or modify it
   6  * under the terms of the GNU General Public License version 2 only, as
   7  * published by the Free Software Foundation.
   8  *
   9  * This code is distributed in the hope that it will be useful, but WITHOUT
  10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  11  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  12  * version 2 for more details (a copy is included in the LICENSE file that
  13  * accompanied this code).
  14  *
  15  * You should have received a copy of the GNU General Public License version
  16  * 2 along with this work; if not, write to the Free Software Foundation,
  17  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  18  *
  19  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  20  * or visit www.oracle.com if you need additional information or have any
  21  * questions.
  22  */
  23 
  24 import java.io.ByteArrayOutputStream;
  25 import java.io.PrintStream;
  26 import java.io.PrintWriter;
  27 import java.lang.reflect.Method;
  28 import java.nio.file.Files;
  29 import java.nio.file.Path;
  30 import java.nio.file.Paths;
  31 import java.util.Arrays;
  32 import java.util.function.Consumer;
  33 import java.util.regex.Pattern;
  34 
  35 import static java.nio.charset.StandardCharsets.UTF_8;
  36 import static jdk.test.lib.Asserts.assertFalse;
  37 import static jdk.test.lib.Asserts.assertTrue;
  38 import static jdk.test.lib.Asserts.fail;
  39 
  40 /**
  41  * This class is intended to be a base class for classes which are about to test
  42  * command line interface of jimage.
  43  */
  44 public class JImageCliTest {
  45 
  46     private String bootImagePath;
  47 
  48     public JImageCliTest() {
  49         Path imagePath = Paths.get(System.getProperty("java.home"), "lib", "modules");
  50         if (Files.exists(imagePath)) {
  51             this.bootImagePath = imagePath.toAbsolutePath().toString();
  52         }
  53     }
  54 
  55     public void assertMatches(String regex, String output) {
  56         Pattern pattern = Pattern.compile(regex);
  57         if (!pattern.matcher(output).find()) {
  58             fail(String.format("Expected to find a string match for [%s] in output \n[\n%s\n]\n.",
  59                     pattern, output));
  60         }
  61     }
  62 
  63     /**
  64      * Returns a path to a tested image to share it across tests. By default it returns a path to the boot image
  65      * of tested JDK. This behavior can be redefined by descendants.
  66      */
  67     public String getImagePath() {
  68         return bootImagePath;
  69     }
  70 
  71     /**
  72      * Runs jimage task with the supplied arguments.
  73      */
  74     protected static JImageResult jimage(String... args) {
  75         ByteArrayOutputStream baos = new ByteArrayOutputStream();
  76         PrintStream ps = new PrintStream(baos);
  77         System.out.println("jimage " + Arrays.asList(args));
  78         int exitCode = jdk.tools.jimage.Main.run(args, new PrintWriter(ps));
  79         return new JImageResult(exitCode, new String(baos.toByteArray(), UTF_8));
  80     }
  81 
  82     protected static class JImageResult {
  83         final int exitCode;
  84         final String output;
  85 
  86         JImageResult(int exitCode, String output) {
  87             this.exitCode = exitCode;
  88             this.output = output;
  89         }
  90 
  91         JImageResult assertSuccess() { assertTrue(exitCode == 0, output); return this; }
  92         JImageResult assertFailure() { assertFalse(exitCode == 0, output); return this; }
  93 
  94         // a helper to ensure the error output doesn't exhibit implementation details
  95         JImageResult assertShowsError() {
  96             assertTrue(output.contains("Error"),
  97                     String.format("Output contains error, output=[%s]\n", output));
  98             assertFalse(output.contains("Exception"),
  99                     String.format("Output doesn't contain a stacktrace, output=[%s]\n", output));
 100             return this;
 101         }
 102 
 103         JImageResult resultChecker(Consumer<JImageResult> r) { r.accept(this); return this; }
 104     }
 105 
 106     protected final void runTests() throws Throwable {
 107         if (getImagePath() != null) {
 108             for (Method m : getClass().getDeclaredMethods()) {
 109                 if (m.getName().startsWith("test")) {
 110                     System.out.printf("Invoking %s\n", m.getName());
 111                     m.invoke(this);
 112                 }
 113             }
 114         } else {
 115             System.out.println("This is not an image build. Skipping.");
 116         }
 117     }
 118 
 119 }