gnodet commented on code in PR #12694:
URL: https://github.com/apache/maven/pull/12694#discussion_r3879510044


##########
impl/maven-core/src/main/java/org/apache/maven/internal/impl/DefaultLog.java:
##########
@@ -18,149 +18,251 @@
  */
 package org.apache.maven.internal.impl;
 
+import java.lang.StackWalker.StackFrame;
 import java.util.function.Supplier;
 
 import org.apache.maven.api.plugin.Log;
 import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
 
 import static java.util.Objects.requireNonNull;
 
 public class DefaultLog implements Log {
+
+    /**
+     * Metadata captured from Log API calls, mirroring the JUL metadata
+     * pattern in {@code MavenJulHandler}.
+     *
+     * @param sourceClassName  the fully qualified class name of the caller
+     * @param sourceMethodName the method that issued the log call
+     * @param threadId         the originating thread ID
+     */
+    public record LogApiMetadata(String sourceClassName, String 
sourceMethodName, long threadId) {}
+
+    private static final ThreadLocal<LogApiMetadata> LOG_API_METADATA = new 
ThreadLocal<>();
+    private static final StackWalker WALKER = StackWalker.getInstance();
+    private static final String THIS_CLASS = DefaultLog.class.getName();
+
+    /**
+     * Returns the Log API metadata for the current log event being processed,
+     * or {@code null} if the current event did not originate from the Log API.
+     * <p>
+     * Called from {@code ProjectBuildLogAppender.accept()} to populate
+     * {@code LogEvent.sourceClassName()} and {@code 
LogEvent.sourceMethodName()}.
+     *
+     * @return the current Log API metadata, or {@code null}
+     */
+    public static LogApiMetadata getLogApiMetadata() {
+        return LOG_API_METADATA.get();
+    }
+
     private final Logger logger;
 
     public DefaultLog(Logger logger) {
         this.logger = requireNonNull(logger);
     }
 
+    /**
+     * Wraps a logging call with Log API metadata: captures the caller's
+     * method name via {@link StackWalker}, sets the ThreadLocal, executes
+     * the actual SLF4J call, and clears the ThreadLocal.
+     * <p>
+     * The source class name is taken from the SLF4J logger name (which
+     * is the mojo implementation FQCN, set at injection time).  The
+     * source method name is resolved by walking the stack past this class
+     * to find the first external caller frame.
+     */
+    private void withMetadata(Runnable logAction) {

Review Comment:
   Fixed — StackWalker is now conditional: `if 
(ProjectBuildLogAppender.hasReportCapture())` before walking. The ~1-5μs 
per-call cost is only paid when build report capture is actually active. During 
normal builds, `withMetadata()` just sets the ThreadLocal with the logger name 
and thread ID (no stack walking).



##########
impl/maven-core/src/main/java/org/apache/maven/logging/ProjectBuildLogAppender.java:
##########
@@ -52,6 +72,31 @@ public static void setProjectId(String projectId) {
         }
     }
 
+    public static String getMojoId() {
+        return MOJO_ID.get();
+    }
+
+    /**
+     * Sets or clears the mojo execution identifier in both the thread-local
+     * and the SLF4J MDC.  The value is available to any SLF4J appender via
+     * the MDC key {@code maven.mojo.id} and to JUL-bridged messages through
+     * the same MDC path.
+     * <p>
+     * Format: {@code "prefix:goal@executionId"}
+     * (e.g. {@code "compiler:compile@default-compile"}).
+     *
+     * @param mojoId the mojo identifier, or {@code null} to clear
+     */
+    public static void setMojoId(String mojoId) {

Review Comment:
   Fixed — added `FORKING_MOJO_ID` ThreadLocal mirroring the existing 
`FORKING_PROJECT_ID` pattern. `LoggingExecutionListener.forkStarted()` saves 
the current mojoId via `setForkingMojoId()`, and 
`forkSucceeded()`/`forkFailed()` clear it. Also fixed the cleanup ordering: 
`setMojoId(null)` now runs *after* `delegate.mojoSucceeded`/`mojoFailed` so the 
mojo context is available during the delegate callback, and `setMojoId(null)` 
restores the forking mojo's ID if one was saved.



-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: [email protected]

For queries about this service, please contact Infrastructure at:
[email protected]

Reply via email to