Provide more verbose docker compose logging

Update `up` and `start` operations so that real-time logging is
provided. Prior to this commit, lengthy pull operations were not
logged which gave the impression that the application had
crashed.

Closes gh-34994
This commit is contained in:
Phillip Webb
2023-04-15 21:25:49 -07:00
parent 7728488541
commit 3657f73b9a
13 changed files with 149 additions and 66 deletions

View File

@@ -27,6 +27,7 @@ import org.springframework.boot.docker.compose.core.DockerCliInspectResponse.Con
import org.springframework.boot.docker.compose.core.DockerCliInspectResponse.ExposedPort;
import org.springframework.boot.docker.compose.core.DockerCliInspectResponse.HostConfig;
import org.springframework.boot.docker.compose.core.DockerCliInspectResponse.NetworkSettings;
import org.springframework.boot.logging.LogLevel;
import static org.assertj.core.api.Assertions.assertThat;
import static org.assertj.core.api.Assertions.entry;
@@ -50,8 +51,8 @@ class DefaultDockerComposeTests {
@Test
void upRunsUpCommand() {
DefaultDockerCompose compose = new DefaultDockerCompose(this.cli, HOST);
compose.up();
then(this.cli).should().run(new DockerCliCommand.ComposeUp());
compose.up(LogLevel.OFF);
then(this.cli).should().run(new DockerCliCommand.ComposeUp(LogLevel.OFF));
}
@Test
@@ -65,8 +66,8 @@ class DefaultDockerComposeTests {
@Test
void startRunsStartCommand() {
DefaultDockerCompose compose = new DefaultDockerCompose(this.cli, HOST);
compose.start();
then(this.cli).should().run(new DockerCliCommand.ComposeStart());
compose.start(LogLevel.OFF);
then(this.cli).should().run(new DockerCliCommand.ComposeStart(LogLevel.OFF));
}
@Test

View File

@@ -21,6 +21,8 @@ import java.util.List;
import org.junit.jupiter.api.Test;
import org.springframework.boot.logging.LogLevel;
import static org.assertj.core.api.Assertions.assertThat;
/**
@@ -66,9 +68,10 @@ class DockerCliCommandTests {
@Test
void composeUp() {
DockerCliCommand<?> command = new DockerCliCommand.ComposeUp();
DockerCliCommand<?> command = new DockerCliCommand.ComposeUp(LogLevel.INFO);
assertThat(command.getType()).isEqualTo(DockerCliCommand.Type.DOCKER_COMPOSE);
assertThat(command.getCommand()).containsExactly("up", "--no-color", "--quiet-pull", "--detach", "--wait");
assertThat(command.getLogLevel()).isEqualTo(LogLevel.INFO);
assertThat(command.getCommand()).containsExactly("up", "--no-color", "--detach", "--wait");
assertThat(command.deserialize("[]")).isNull();
}
@@ -82,9 +85,10 @@ class DockerCliCommandTests {
@Test
void composeStart() {
DockerCliCommand<?> command = new DockerCliCommand.ComposeStart();
DockerCliCommand<?> command = new DockerCliCommand.ComposeStart(LogLevel.INFO);
assertThat(command.getType()).isEqualTo(DockerCliCommand.Type.DOCKER_COMPOSE);
assertThat(command.getCommand()).containsExactly("start", "--no-color", "--quiet-pull", "--detach", "--wait");
assertThat(command.getLogLevel()).isEqualTo(LogLevel.INFO);
assertThat(command.getCommand()).containsExactly("start", "--no-color", "--detach", "--wait");
assertThat(command.deserialize("[]")).isNull();
}

View File

@@ -41,6 +41,13 @@ class ProcessRunnerTests {
assertThat(out).isNotEmpty();
}
@Test
void runWhenHasOutputConsumer() {
StringBuilder output = new StringBuilder();
this.processRunner.run(output::append, "docker", "--version");
assertThat(output.toString()).isNotEmpty();
}
@Test
void runWhenProcessDoesNotStart() {
assertThatExceptionOfType(ProcessStartException.class)

View File

@@ -43,7 +43,6 @@ import org.springframework.util.FileCopyUtils;
import static org.assertj.core.api.Assertions.assertThat;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.ArgumentMatchers.isA;
import static org.mockito.BDDMockito.given;
import static org.mockito.BDDMockito.then;
import static org.mockito.Mockito.mock;
@@ -132,10 +131,10 @@ class DockerComposeLifecycleManagerTests {
this.lifecycleManager.startup();
assertThat(listener.getEvent()).isNull();
then(this.dockerCompose).should().hasDefinedServices();
then(this.dockerCompose).should(never()).up();
then(this.dockerCompose).should(never()).start();
then(this.dockerCompose).should(never()).down(isA(Duration.class));
then(this.dockerCompose).should(never()).stop(isA(Duration.class));
then(this.dockerCompose).should(never()).up(any());
then(this.dockerCompose).should(never()).start(any());
then(this.dockerCompose).should(never()).down(any());
then(this.dockerCompose).should(never()).stop(any());
}
@Test
@@ -147,10 +146,10 @@ class DockerComposeLifecycleManagerTests {
this.lifecycleManager.startup();
this.shutdownHandlers.run();
assertThat(listener.getEvent()).isNotNull();
then(this.dockerCompose).should().up();
then(this.dockerCompose).should(never()).start();
then(this.dockerCompose).should().down(isA(Duration.class));
then(this.dockerCompose).should(never()).stop(isA(Duration.class));
then(this.dockerCompose).should().up(any());
then(this.dockerCompose).should(never()).start(any());
then(this.dockerCompose).should().down(any());
then(this.dockerCompose).should(never()).stop(any());
}
@Test
@@ -162,10 +161,10 @@ class DockerComposeLifecycleManagerTests {
this.lifecycleManager.startup();
this.shutdownHandlers.run();
assertThat(listener.getEvent()).isNotNull();
then(this.dockerCompose).should(never()).up();
then(this.dockerCompose).should(never()).start();
then(this.dockerCompose).should(never()).down(isA(Duration.class));
then(this.dockerCompose).should(never()).stop(isA(Duration.class));
then(this.dockerCompose).should(never()).up(any());
then(this.dockerCompose).should(never()).start(any());
then(this.dockerCompose).should(never()).down(any());
then(this.dockerCompose).should(never()).stop(any());
}
@Test
@@ -177,10 +176,10 @@ class DockerComposeLifecycleManagerTests {
this.lifecycleManager.startup();
this.shutdownHandlers.run();
assertThat(listener.getEvent()).isNotNull();
then(this.dockerCompose).should(never()).up();
then(this.dockerCompose).should(never()).start();
then(this.dockerCompose).should(never()).down(isA(Duration.class));
then(this.dockerCompose).should(never()).stop(isA(Duration.class));
then(this.dockerCompose).should(never()).up(any());
then(this.dockerCompose).should(never()).start(any());
then(this.dockerCompose).should(never()).down(any());
then(this.dockerCompose).should(never()).stop(any());
}
@Test
@@ -192,10 +191,10 @@ class DockerComposeLifecycleManagerTests {
this.lifecycleManager.startup();
this.shutdownHandlers.run();
assertThat(listener.getEvent()).isNotNull();
then(this.dockerCompose).should().up();
then(this.dockerCompose).should(never()).start();
then(this.dockerCompose).should(never()).down(isA(Duration.class));
then(this.dockerCompose).should(never()).stop(isA(Duration.class));
then(this.dockerCompose).should().up(any());
then(this.dockerCompose).should(never()).start(any());
then(this.dockerCompose).should(never()).down(any());
then(this.dockerCompose).should(never()).stop(any());
this.shutdownHandlers.assertNoneAdded();
}
@@ -209,10 +208,10 @@ class DockerComposeLifecycleManagerTests {
this.lifecycleManager.startup();
this.shutdownHandlers.run();
assertThat(listener.getEvent()).isNotNull();
then(this.dockerCompose).should(never()).up();
then(this.dockerCompose).should().start();
then(this.dockerCompose).should().down(isA(Duration.class));
then(this.dockerCompose).should(never()).stop(isA(Duration.class));
then(this.dockerCompose).should(never()).up(any());
then(this.dockerCompose).should().start(any());
then(this.dockerCompose).should().down(any());
then(this.dockerCompose).should(never()).stop(any());
}
@Test
@@ -225,10 +224,10 @@ class DockerComposeLifecycleManagerTests {
this.lifecycleManager.startup();
this.shutdownHandlers.run();
assertThat(listener.getEvent()).isNotNull();
then(this.dockerCompose).should().up();
then(this.dockerCompose).should(never()).start();
then(this.dockerCompose).should(never()).down(isA(Duration.class));
then(this.dockerCompose).should().stop(isA(Duration.class));
then(this.dockerCompose).should().up(any());
then(this.dockerCompose).should(never()).start(any());
then(this.dockerCompose).should(never()).down(any());
then(this.dockerCompose).should().stop(any());
}
@Test

View File

@@ -19,6 +19,7 @@ package org.springframework.boot.docker.compose.lifecycle;
import org.junit.jupiter.api.Test;
import org.springframework.boot.docker.compose.core.DockerCompose;
import org.springframework.boot.logging.LogLevel;
import static org.mockito.BDDMockito.then;
import static org.mockito.Mockito.mock;
@@ -36,14 +37,14 @@ class StartupCommandTests {
@Test
void applyToWhenUp() {
StartupCommand.UP.applyTo(this.dockerCompose);
then(this.dockerCompose).should().up();
StartupCommand.UP.applyTo(this.dockerCompose, LogLevel.INFO);
then(this.dockerCompose).should().up(LogLevel.INFO);
}
@Test
void applyToWhenStart() {
StartupCommand.START.applyTo(this.dockerCompose);
then(this.dockerCompose).should().start();
StartupCommand.START.applyTo(this.dockerCompose, LogLevel.INFO);
then(this.dockerCompose).should().start(LogLevel.INFO);
}
}