[MNG-7899] Various memory usage improvements 5 (#1270)

Multiple optimizations :
- renderLevel() method use static constants instead of rebuilding the strings on each call
- replace + operator usage with more PrintStream.print() calls to reduce temporary strings creation
- reduce usage of MessageBuilder.a() method usage with more PrintStream.print() calls to reduce temporary strings creation
- replace the builder() method with a static import
- replace String.format with a simple string concat to reduce memory allocation (garbage)
- change static constants to class member in MavenSimpleLogger
- add a setLength(int) method in MessageBuilder to enable reuse
This commit is contained in:
sebastien-doyon 2023-10-20 16:30:44 +02:00 committed by GitHub
parent 68bbc8f393
commit d362690a82
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
5 changed files with 69 additions and 38 deletions

View File

@ -206,4 +206,11 @@ public interface MessageBuilder {
*/ */
@Nonnull @Nonnull
String build(); String build();
/**
* Set the buffer length.
*
* @param length the new length
*/
void setLength(int length);
} }

View File

@ -154,4 +154,9 @@ public String build() {
public String toString() { public String toString() {
return build(); return build();
} }
@Override
public void setLength(int length) {
buffer.setLength(length);
}
} }

View File

@ -497,19 +497,6 @@ void logging(CliRequest cliRequest) {
cliRequest.quiet = !cliRequest.verbose && commandLine.hasOption(CLIManager.QUIET); cliRequest.quiet = !cliRequest.verbose && commandLine.hasOption(CLIManager.QUIET);
cliRequest.showErrors = cliRequest.verbose || commandLine.hasOption(CLIManager.ERRORS); cliRequest.showErrors = cliRequest.verbose || commandLine.hasOption(CLIManager.ERRORS);
slf4jLoggerFactory = LoggerFactory.getILoggerFactory();
Slf4jConfiguration slf4jConfiguration = Slf4jConfigurationFactory.getConfiguration(slf4jLoggerFactory);
if (cliRequest.verbose) {
cliRequest.request.setLoggingLevel(MavenExecutionRequest.LOGGING_LEVEL_DEBUG);
slf4jConfiguration.setRootLoggerLevel(Slf4jConfiguration.Level.DEBUG);
} else if (cliRequest.quiet) {
cliRequest.request.setLoggingLevel(MavenExecutionRequest.LOGGING_LEVEL_ERROR);
slf4jConfiguration.setRootLoggerLevel(Slf4jConfiguration.Level.ERROR);
}
// else fall back to default log level specified in conf
// see https://issues.apache.org/jira/browse/MNG-2570
// LOG COLOR // LOG COLOR
String styleColor = cliRequest.getUserProperties().getProperty(STYLE_COLOR_PROPERTY, "auto"); String styleColor = cliRequest.getUserProperties().getProperty(STYLE_COLOR_PROPERTY, "auto");
styleColor = commandLine.getOptionValue(COLOR, styleColor); styleColor = commandLine.getOptionValue(COLOR, styleColor);
@ -528,6 +515,19 @@ void logging(CliRequest cliRequest) {
} }
} }
slf4jLoggerFactory = LoggerFactory.getILoggerFactory();
Slf4jConfiguration slf4jConfiguration = Slf4jConfigurationFactory.getConfiguration(slf4jLoggerFactory);
if (cliRequest.verbose) {
cliRequest.request.setLoggingLevel(MavenExecutionRequest.LOGGING_LEVEL_DEBUG);
slf4jConfiguration.setRootLoggerLevel(Slf4jConfiguration.Level.DEBUG);
} else if (cliRequest.quiet) {
cliRequest.request.setLoggingLevel(MavenExecutionRequest.LOGGING_LEVEL_ERROR);
slf4jConfiguration.setRootLoggerLevel(Slf4jConfiguration.Level.ERROR);
}
// else fall back to default log level specified in conf
// see https://issues.apache.org/jira/browse/MNG-2570
// LOG STREAMS // LOG STREAMS
if (commandLine.hasOption(CLIManager.LOG_FILE)) { if (commandLine.hasOption(CLIManager.LOG_FILE)) {
File logFile = new File(commandLine.getOptionValue(CLIManager.LOG_FILE)); File logFile = new File(commandLine.getOptionValue(CLIManager.LOG_FILE));

View File

@ -26,12 +26,16 @@
@Experimental @Experimental
public class JansiMessageBuilder implements MessageBuilder { public class JansiMessageBuilder implements MessageBuilder {
private final Ansi ansi; private final Ansi ansi;
private StringBuilder sb;
@SuppressWarnings("magicnumber")
public JansiMessageBuilder() { public JansiMessageBuilder() {
this.sb = new StringBuilder(80);
this.ansi = Ansi.ansi(); this.ansi = Ansi.ansi();
} }
public JansiMessageBuilder(StringBuilder sb) { public JansiMessageBuilder(StringBuilder sb) {
this.sb = sb;
this.ansi = Ansi.ansi(sb); this.ansi = Ansi.ansi(sb);
} }
@ -159,4 +163,9 @@ public String build() {
public String toString() { public String toString() {
return build(); return build();
} }
@Override
public void setLength(int length) {
sb.setLength(length);
}
} }

View File

@ -21,7 +21,8 @@
import java.io.PrintStream; import java.io.PrintStream;
import org.apache.maven.api.services.MessageBuilder; import org.apache.maven.api.services.MessageBuilder;
import org.apache.maven.cli.jansi.MessageUtils;
import static org.apache.maven.cli.jansi.MessageUtils.builder;
/** /**
* Logger for Maven, that support colorization of levels and stacktraces. This class implements 2 methods introduced in * Logger for Maven, that support colorization of levels and stacktraces. This class implements 2 methods introduced in
@ -30,6 +31,13 @@
* @since 3.5.0 * @since 3.5.0
*/ */
public class MavenSimpleLogger extends SimpleLogger { public class MavenSimpleLogger extends SimpleLogger {
private final String traceRenderedLevel = builder().trace("TRACE").build();
private final String debugRenderedLevel = builder().debug("DEBUG").build();
private final String infoRenderedLevel = builder().info("INFO").build();
private final String warnRenderedLevel = builder().warning("WARNING").build();
private final String errorRenderedLevel = builder().error("ERROR").build();
MavenSimpleLogger(String name) { MavenSimpleLogger(String name) {
super(name); super(name);
} }
@ -38,16 +46,16 @@ public class MavenSimpleLogger extends SimpleLogger {
protected String renderLevel(int level) { protected String renderLevel(int level) {
switch (level) { switch (level) {
case LOG_LEVEL_TRACE: case LOG_LEVEL_TRACE:
return builder().trace("TRACE").build(); return traceRenderedLevel;
case LOG_LEVEL_DEBUG: case LOG_LEVEL_DEBUG:
return builder().debug("DEBUG").build(); return debugRenderedLevel;
case LOG_LEVEL_INFO: case LOG_LEVEL_INFO:
return builder().info("INFO").build(); return infoRenderedLevel;
case LOG_LEVEL_WARN: case LOG_LEVEL_WARN:
return builder().warning("WARNING").build(); return warnRenderedLevel;
case LOG_LEVEL_ERROR: case LOG_LEVEL_ERROR:
default: default:
return builder().error("ERROR").build(); return errorRenderedLevel;
} }
} }
@ -56,24 +64,30 @@ protected void writeThrowable(Throwable t, PrintStream stream) {
if (t == null) { if (t == null) {
return; return;
} }
stream.print(builder().failure(t.getClass().getName())); MessageBuilder builder = builder().failure(t.getClass().getName());
if (t.getMessage() != null) { if (t.getMessage() != null) {
stream.print(": "); builder.a(": ").failure(t.getMessage());
stream.print(builder().failure(t.getMessage()));
} }
stream.println(); stream.println(builder);
printStackTrace(t, stream, ""); printStackTrace(t, stream, "");
} }
private void printStackTrace(Throwable t, PrintStream stream, String prefix) { private void printStackTrace(Throwable t, PrintStream stream, String prefix) {
MessageBuilder builder = builder();
for (StackTraceElement e : t.getStackTrace()) { for (StackTraceElement e : t.getStackTrace()) {
stream.print(prefix); builder.a(prefix);
stream.print(" "); builder.a(" ");
stream.print(builder().strong("at")); builder.strong("at");
stream.print(" " + e.getClassName() + "." + e.getMethodName()); builder.a(" ");
stream.print(builder().a(" (").strong(getLocation(e)).a(")")); builder.a(e.getClassName());
stream.println(); builder.a(".");
builder.a(e.getMethodName());
builder.a(" (");
builder.strong(getLocation(e));
builder.a(")");
stream.println(builder);
builder.setLength(0);
} }
for (Throwable se : t.getSuppressed()) { for (Throwable se : t.getSuppressed()) {
writeThrowable(se, stream, "Suppressed", prefix + " "); writeThrowable(se, stream, "Suppressed", prefix + " ");
@ -85,12 +99,12 @@ private void printStackTrace(Throwable t, PrintStream stream, String prefix) {
} }
private void writeThrowable(Throwable t, PrintStream stream, String caption, String prefix) { private void writeThrowable(Throwable t, PrintStream stream, String caption, String prefix) {
stream.print(builder().a(prefix).strong(caption).a(": ").a(t.getClass().getName())); MessageBuilder builder =
builder().a(prefix).strong(caption).a(": ").a(t.getClass().getName());
if (t.getMessage() != null) { if (t.getMessage() != null) {
stream.print(": "); builder.a(": ").failure(t.getMessage());
stream.print(builder().failure(t.getMessage()));
} }
stream.println(); stream.println(builder);
printStackTrace(t, stream, prefix); printStackTrace(t, stream, prefix);
} }
@ -103,13 +117,9 @@ protected String getLocation(final StackTraceElement e) {
} else if (e.getFileName() == null) { } else if (e.getFileName() == null) {
return "Unknown Source"; return "Unknown Source";
} else if (e.getLineNumber() >= 0) { } else if (e.getLineNumber() >= 0) {
return String.format("%s:%s", e.getFileName(), e.getLineNumber()); return e.getFileName() + ":" + e.getLineNumber();
} else { } else {
return e.getFileName(); return e.getFileName();
} }
} }
private MessageBuilder builder() {
return MessageUtils.builder();
}
} }