Read PID and version used in startup logging from the environment

See gh-41604
This commit is contained in:
Moritz Halbritter 2024-08-01 15:49:19 +02:00
parent 7920e371fa
commit 166926881f
3 changed files with 77 additions and 22 deletions

View File

@ -336,7 +336,7 @@ public class SpringApplication {
afterRefresh(context, applicationArguments);
startup.started();
if (this.logStartupInfo) {
new StartupInfoLogger(this.mainApplicationClass).logStarted(getApplicationLog(), startup);
new StartupInfoLogger(this.mainApplicationClass, environment).logStarted(getApplicationLog(), startup);
}
listeners.started(context, startup.timeTakenToStarted());
callRunners(context, applicationArguments);
@ -404,6 +404,7 @@ public class SpringApplication {
bootstrapContext.close(context);
if (this.logStartupInfo) {
logStartupInfo(context.getParent() == null);
logStartupInfo(context);
logStartupProfileInfo(context);
}
// Add boot specific singleton beans
@ -633,14 +634,27 @@ public class SpringApplication {
/**
* Called to log startup information, subclasses may override to add additional
* logging.
* @param isRoot true if this application is the root of a context hierarchy
* @param context the application context
* @since 3.4.0
*/
protected void logStartupInfo(boolean isRoot) {
protected void logStartupInfo(ConfigurableApplicationContext context) {
boolean isRoot = context.getParent() == null;
if (isRoot) {
new StartupInfoLogger(this.mainApplicationClass).logStarting(getApplicationLog());
new StartupInfoLogger(this.mainApplicationClass, context.getEnvironment()).logStarting(getApplicationLog());
}
}
/**
* Called to log startup information, subclasses may override to add additional
* logging.
* @param isRoot true if this application is the root of a context hierarchy
* @deprecated since 3.4.0 for removal in 3.6.0 in favor of
* {@link #logStartupInfo(ConfigurableApplicationContext)}
*/
@Deprecated(since = "3.4.0", forRemoval = true)
protected void logStartupInfo(boolean isRoot) {
}
/**
* Called to log active profile information.
* @param context the application context

View File

@ -1,5 +1,5 @@
/*
* Copyright 2012-2023 the original author or authors.
* Copyright 2012-2024 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@ -23,8 +23,8 @@ import org.apache.commons.logging.Log;
import org.springframework.aot.AotDetector;
import org.springframework.boot.SpringApplication.Startup;
import org.springframework.boot.system.ApplicationHome;
import org.springframework.boot.system.ApplicationPid;
import org.springframework.context.ApplicationContext;
import org.springframework.core.env.Environment;
import org.springframework.core.log.LogMessage;
import org.springframework.util.Assert;
import org.springframework.util.ClassUtils;
@ -41,8 +41,11 @@ class StartupInfoLogger {
private final Class<?> sourceClass;
StartupInfoLogger(Class<?> sourceClass) {
private final Environment environment;
StartupInfoLogger(Class<?> sourceClass, Environment environment) {
this.sourceClass = sourceClass;
this.environment = environment;
}
void logStarting(Log applicationLog) {
@ -62,7 +65,7 @@ class StartupInfoLogger {
message.append("Starting");
appendAotMode(message);
appendApplicationName(message);
appendVersion(message, this.sourceClass);
appendApplicationVersion(message);
appendJavaVersion(message);
appendPid(message);
appendContext(message);
@ -106,8 +109,12 @@ class StartupInfoLogger {
append(message, "v", () -> source.getPackage().getImplementationVersion());
}
private void appendApplicationVersion(StringBuilder message) {
append(message, "v", () -> this.environment.getProperty("spring.application.version"));
}
private void appendPid(StringBuilder message) {
append(message, "with PID ", ApplicationPid::new);
append(message, "with PID ", () -> this.environment.getProperty("spring.application.pid"));
}
private void appendContext(StringBuilder message) {

View File

@ -1,5 +1,5 @@
/*
* Copyright 2012-2023 the original author or authors.
* Copyright 2012-2024 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@ -17,10 +17,11 @@
package org.springframework.boot;
import org.apache.commons.logging.Log;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Test;
import org.springframework.boot.SpringApplication.Startup;
import org.springframework.boot.system.ApplicationPid;
import org.springframework.mock.env.MockEnvironment;
import static org.assertj.core.api.Assertions.assertThat;
import static org.mockito.ArgumentMatchers.assertArg;
@ -39,15 +40,48 @@ class StartupInfoLoggerTests {
private final Log log = mock(Log.class);
private MockEnvironment environment;
@BeforeEach
void setUp() {
this.environment = new MockEnvironment();
this.environment.setProperty("spring.application.version", "1.2.3");
this.environment.setProperty("spring.application.pid", "42");
}
@Test
void startingFormat() {
given(this.log.isInfoEnabled()).willReturn(true);
new StartupInfoLogger(getClass()).logStarting(this.log);
new StartupInfoLogger(getClass(), this.environment).logStarting(this.log);
then(this.log).should()
.info(assertArg((message) -> assertThat(message.toString())
.contains("Starting " + getClass().getSimpleName() + " using Java " + System.getProperty("java.version")
+ " with PID " + new ApplicationPid() + " (started by " + System.getProperty("user.name")
+ " in " + System.getProperty("user.dir") + ")")));
.info(assertArg(
(message) -> assertThat(message.toString()).contains("Starting " + getClass().getSimpleName()
+ " v1.2.3 using Java " + System.getProperty("java.version") + " with PID 42 (started by "
+ System.getProperty("user.name") + " in " + System.getProperty("user.dir") + ")")));
}
@Test
void startingFormatWhenVersionIsNotAvailable() {
this.environment.setProperty("spring.application.version", "");
given(this.log.isInfoEnabled()).willReturn(true);
new StartupInfoLogger(getClass(), this.environment).logStarting(this.log);
then(this.log).should()
.info(assertArg(
(message) -> assertThat(message.toString()).contains("Starting " + getClass().getSimpleName()
+ " using Java " + System.getProperty("java.version") + " with PID 42 (started by "
+ System.getProperty("user.name") + " in " + System.getProperty("user.dir") + ")")));
}
@Test
void startingFormatWhenPidIsNotAvailable() {
this.environment.setProperty("spring.application.pid", "");
given(this.log.isInfoEnabled()).willReturn(true);
new StartupInfoLogger(getClass(), this.environment).logStarting(this.log);
then(this.log).should()
.info(assertArg(
(message) -> assertThat(message.toString()).contains("Starting " + getClass().getSimpleName()
+ " v1.2.3 using Java " + System.getProperty("java.version") + " (started by "
+ System.getProperty("user.name") + " in " + System.getProperty("user.dir") + ")")));
}
@Test
@ -55,11 +89,11 @@ class StartupInfoLoggerTests {
System.setProperty("spring.aot.enabled", "true");
try {
given(this.log.isInfoEnabled()).willReturn(true);
new StartupInfoLogger(getClass()).logStarting(this.log);
new StartupInfoLogger(getClass(), this.environment).logStarting(this.log);
then(this.log).should()
.info(assertArg((message) -> assertThat(message.toString())
.contains("Starting AOT-processed " + getClass().getSimpleName() + " using Java "
+ System.getProperty("java.version") + " with PID " + new ApplicationPid() + " (started by "
.contains("Starting AOT-processed " + getClass().getSimpleName() + " v1.2.3 using Java "
+ System.getProperty("java.version") + " with PID 42 (started by "
+ System.getProperty("user.name") + " in " + System.getProperty("user.dir") + ")")));
}
@ -71,7 +105,7 @@ class StartupInfoLoggerTests {
@Test
void startedFormat() {
given(this.log.isInfoEnabled()).willReturn(true);
new StartupInfoLogger(getClass()).logStarted(this.log, new TestStartup(1345L, "Started"));
new StartupInfoLogger(getClass(), this.environment).logStarted(this.log, new TestStartup(1345L, "Started"));
then(this.log).should()
.info(assertArg((message) -> assertThat(message.toString()).matches("Started " + getClass().getSimpleName()
+ " in \\d+\\.\\d{1,3} seconds \\(process running for 1.345\\)")));
@ -80,7 +114,7 @@ class StartupInfoLoggerTests {
@Test
void startedWithoutUptimeFormat() {
given(this.log.isInfoEnabled()).willReturn(true);
new StartupInfoLogger(getClass()).logStarted(this.log, new TestStartup(null, "Started"));
new StartupInfoLogger(getClass(), this.environment).logStarted(this.log, new TestStartup(null, "Started"));
then(this.log).should()
.info(assertArg((message) -> assertThat(message.toString())
.matches("Started " + getClass().getSimpleName() + " in \\d+\\.\\d{1,3} seconds")));
@ -89,7 +123,7 @@ class StartupInfoLoggerTests {
@Test
void restoredFormat() {
given(this.log.isInfoEnabled()).willReturn(true);
new StartupInfoLogger(getClass()).logStarted(this.log, new TestStartup(null, "Restored"));
new StartupInfoLogger(getClass(), this.environment).logStarted(this.log, new TestStartup(null, "Restored"));
then(this.log).should()
.info(assertArg((message) -> assertThat(message.toString())
.matches("Restored " + getClass().getSimpleName() + " in \\d+\\.\\d{1,3} seconds")));