Repository: GoogleContainerTools/jib
File: jib-cli/src/integration-test/java/com/google/cloud/tools/jib/cli/cli2/JarCommandTest.java (Java)

Code before:
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.PrintStream;
import java.net.URISyntaxException;
import java.nio.file.Path;
import java.nio.file.Paths;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;
import picocli.CommandLine;

public class JarCommandTest {

  private static final Integer SUCCESS_CODE = 0;
  private static final Integer FAILURE_CODE = 1;

  private final PrintStream originalOut = System.out;
  private final PrintStream originalErr = System.err;
  private final ByteArrayOutputStream out = new ByteArrayOutputStream();
  private final ByteArrayOutputStream err = new ByteArrayOutputStream();

  @Before
  public void setUp() {
    out.reset();
    err.reset();
    System.setOut(new PrintStream(out));
    System.setErr(new PrintStream(err));
  }

  @After
  public void tearDown() {
    System.setOut(originalOut);
    System.setErr(originalErr);
  }

  @Test
  public void testErrorLogging_fileDoesNotExist() {
    Integer actual =
        new CommandLine(new JibCli())
            .execute("--target", "docker://jib-cli-image", "jar", "unknown.jar");

    assertThat(actual).isEqualTo(FAILURE_CODE);
    assertThat(err.toString())
        .contains("[ERROR] The file path provided does not exist: unknown.jar");
  }

  @Test
  public void testErrorLogging_directoryGiven() throws URISyntaxException {
    Path jarFile = Paths.get(Resources.getResource("emptyDir").toURI());
    Integer actual =
        new CommandLine(new JibCli())

Review comment (bug):
This is a creative trick, but I feel it isn't really safe to replace stdout and stderr. For example, the unit framework depends on it, and I think we will not be able to see test failures.

I have been thinking of two options for verifying command output: run as a separate process, or refactor the code. I didn't really like refactoring code only to be able to check log messages. Eventually I think we will reach the point where we really need to check log messages. And we will eventually find a way to run Jib CLI as a standalone process. Maybe for now, if we can't easily find a way to check log messages, I'm fine punting it.

Code after:
import java.io.IOException;
import java.io.PrintWriter;
import java.io.StringWriter;
import java.net.URISyntaxException;
import java.nio.file.Path;
import java.nio.file.Paths;
import org.junit.Test;
import picocli.CommandLine;

public class JarCommandTest {

  @Test
  public void testErrorLogging_fileDoesNotExist() {
    CommandLine jibCli = new CommandLine(new JibCli());
    StringWriter stringWriter = new StringWriter();
    jibCli.setErr(new PrintWriter(stringWriter));

    Integer exitCode = jibCli.execute("--target", "docker://jib-cli-image", "jar", "unknown.jar");

    assertThat(exitCode).isEqualTo(1);
    assertThat(stringWriter.toString())
        .isEqualTo("[ERROR] The file path provided does not exist: unknown.jar\n");
  }

  @Test
  public void testErrorLogging_directoryGiven() throws URISyntaxException {
    CommandLine jibCli = new CommandLine(new JibCli());
    StringWriter stringWriter = new StringWriter();
    jibCli.setErr(new PrintWriter(stringWriter));

    Path jarFile = Paths.get("/");
    Integer exitCode =
        jibCli.execute("--target", "docker://jib-cli-image", "jar", jarFile.toString());

    assertThat(exitCode).isEqualTo(1);
    assertThat(stringWriter.toString())
        .isEqualTo(
            "[ERROR] The file path provided is for a directory. Please provide a path to a jar file: "
                + jarFile.toString()
                + "\n");
  }

  @Test
  public void testJar_toDocker() throws IOException, InterruptedException, URISyntaxException {
    Path jarFile = Paths.get(Resources.getResource("simpleJar.jar").toURI());
    Integer exitCode =
        new CommandLine(new JibCli())
            .execute("--target", "docker://jib-cli-image", "jar", jarFile.toString());
    String output = new Command("docker", "run", "--rm", "jib-cli-image").run();

    assertThat(exitCode).isEqualTo(0);