feat(system)!: change logger name and disable flow logger by default

Change system logger name:
- execution -> executor
- trigger -> scheduler
- task -> worker

Add tenant and namespace in the name of loggers.

Disable by default the flow execution logger.
This commit is contained in:
Loïc Mathieu
2025-12-15 11:21:05 +01:00
parent ba1d6b2232
commit c0f6298484
4 changed files with 91 additions and 24 deletions

View File

@@ -55,11 +55,11 @@ public class RunContextLogger implements Supplier<org.slf4j.Logger> {
public RunContextLogger(QueueInterface<LogEntry> logQueue, LogEntry logEntry, org.slf4j.event.Level loglevel, boolean logToFile) { public RunContextLogger(QueueInterface<LogEntry> logQueue, LogEntry logEntry, org.slf4j.event.Level loglevel, boolean logToFile) {
if (logEntry.getTaskId() != null) { if (logEntry.getTaskId() != null) {
this.loggerName = "flow." + logEntry.getFlowId() + "." + logEntry.getTaskId(); this.loggerName = baseLoggerName(logEntry) + "." + logEntry.getTaskId();
} else if (logEntry.getTriggerId() != null) { } else if (logEntry.getTriggerId() != null) {
this.loggerName = "flow." + logEntry.getFlowId() + "." + logEntry.getTriggerId(); this.loggerName = baseLoggerName(logEntry) + "." + logEntry.getTriggerId();
} else { } else {
this.loggerName = "flow." + logEntry.getFlowId(); this.loggerName = baseLoggerName(logEntry);
} }
this.logQueue = logQueue; this.logQueue = logQueue;
@@ -68,6 +68,10 @@ public class RunContextLogger implements Supplier<org.slf4j.Logger> {
this.logToFile = logToFile; this.logToFile = logToFile;
} }
private String baseLoggerName(LogEntry logEntry) {
return "flow." + logEntry.getTenantId() + "." + logEntry.getNamespace() + "." + logEntry.getFlowId();
}
private static List<LogEntry> logEntry(ILoggingEvent event, String message, org.slf4j.event.Level level, LogEntry logEntry) { private static List<LogEntry> logEntry(ILoggingEvent event, String message, org.slf4j.event.Level level, LogEntry logEntry) {
Iterable<String> split; Iterable<String> split;

View File

@@ -10,7 +10,7 @@ import org.slf4j.LoggerFactory;
import org.slf4j.event.Level; import org.slf4j.event.Level;
/** /**
* Utility class for logging * Utility class for server logging
*/ */
public final class Logs { public final class Logs {
@@ -18,7 +18,7 @@ public final class Logs {
private static final String EXECUTION_PREFIX_WITH_TENANT = FLOW_PREFIX_WITH_TENANT + "[execution: {}] "; private static final String EXECUTION_PREFIX_WITH_TENANT = FLOW_PREFIX_WITH_TENANT + "[execution: {}] ";
private static final String TRIGGER_PREFIX_WITH_TENANT = FLOW_PREFIX_WITH_TENANT + "[trigger: {}] "; private static final String TRIGGER_PREFIX_WITH_TENANT = FLOW_PREFIX_WITH_TENANT + "[trigger: {}] ";
private static final String TASKRUN_PREFIX_WITH_TENANT = FLOW_PREFIX_WITH_TENANT + "[task: {}] [execution: {}] [taskrun: {}] "; private static final String TASKRUN_PREFIX_WITH_TENANT = FLOW_PREFIX_WITH_TENANT + "[task: {}] [execution: {}] [taskrun: {}] ";
private Logs() {} private Logs() {}
public static void logExecution(FlowId flow, Logger logger, Level level, String message, Object... args) { public static void logExecution(FlowId flow, Logger logger, Level level, String message, Object... args) {
@@ -29,7 +29,7 @@ public final class Logs {
} }
/** /**
* Log an {@link Execution} via the execution logger named: 'execution.{flowId}'. * Log an {@link Execution} via the executor logger named: 'executor.{tenantId}.{namespace}.{flowId}'.
*/ */
public static void logExecution(Execution execution, Level level, String message, Object... args) { public static void logExecution(Execution execution, Level level, String message, Object... args) {
Logger logger = logger(execution); Logger logger = logger(execution);
@@ -43,7 +43,7 @@ public final class Logs {
} }
/** /**
* Log a {@link TriggerContext} via the trigger logger named: 'trigger.{flowId}.{triggereId}'. * Log a {@link TriggerContext} via the scheduler logger named: 'trigger.{tenantId}.{namespace}.{flowId}.{triggerId}'.
*/ */
public static void logTrigger(TriggerContext triggerContext, Level level, String message, Object... args) { public static void logTrigger(TriggerContext triggerContext, Level level, String message, Object... args) {
Logger logger = logger(triggerContext); Logger logger = logger(triggerContext);
@@ -57,7 +57,7 @@ public final class Logs {
} }
/** /**
* Log a {@link TaskRun} via the taskRun logger named: 'task.{flowId}.{taskId}'. * Log a {@link TaskRun} via the worker logger named: 'worker.{tenantId}.{namespace}.{flowId}.{taskId}'.
*/ */
public static void logTaskRun(TaskRun taskRun, Level level, String message, Object... args) { public static void logTaskRun(TaskRun taskRun, Level level, String message, Object... args) {
String prefix = TASKRUN_PREFIX_WITH_TENANT; String prefix = TASKRUN_PREFIX_WITH_TENANT;
@@ -73,19 +73,19 @@ public final class Logs {
private static Logger logger(TaskRun taskRun) { private static Logger logger(TaskRun taskRun) {
return LoggerFactory.getLogger( return LoggerFactory.getLogger(
"task." + taskRun.getFlowId() + "." + taskRun.getTaskId() "worker." + taskRun.getTenantId() + "." + taskRun.getNamespace() + "." + taskRun.getFlowId() + "." + taskRun.getTaskId()
); );
} }
private static Logger logger(TriggerContext triggerContext) { private static Logger logger(TriggerContext triggerContext) {
return LoggerFactory.getLogger( return LoggerFactory.getLogger(
"trigger." + triggerContext.getFlowId() + "." + triggerContext.getTriggerId() "scheduler." + triggerContext.getTenantId() + "." + triggerContext.getNamespace() + "." + triggerContext.getFlowId() + "." + triggerContext.getTriggerId()
); );
} }
private static Logger logger(Execution execution) { private static Logger logger(Execution execution) {
return LoggerFactory.getLogger( return LoggerFactory.getLogger(
"execution." + execution.getFlowId() "executor." + execution.getTenantId() + "." + execution.getNamespace() + "." + execution.getFlowId()
); );
} }
} }

View File

@@ -9,10 +9,14 @@
<property name="pattern" value="%date{HH:mm:ss}.%ms %highlight(%-5.5level) %magenta(%-12.36thread) %cyan(%-12.36logger{36}) %msg%n" /> <property name="pattern" value="%date{HH:mm:ss}.%ms %highlight(%-5.5level) %magenta(%-12.36thread) %cyan(%-12.36logger{36}) %msg%n" />
<logger name="io.kestra" level="INFO" /> <logger name="io.kestra" level="INFO" />
<logger name="flow" level="INFO" />
<logger name="task" level="INFO" /> <!-- Flow execution logs - disabled by default -->
<logger name="execution" level="INFO" /> <logger name="flow" level="OFF" />
<logger name="trigger" level="INFO" />
<!-- Server loggers -->
<logger name="worker" level="INFO" />
<logger name="executor" level="INFO" />
<logger name="scheduler" level="INFO" />
<logger name="io.kestra.ee.runner.kafka.services.KafkaConsumerService" level="WARN" /> <logger name="io.kestra.ee.runner.kafka.services.KafkaConsumerService" level="WARN" />
<logger name="io.kestra.ee.runner.kafka.services.KafkaProducerService" level="WARN" /> <logger name="io.kestra.ee.runner.kafka.services.KafkaProducerService" level="WARN" />

View File

@@ -1,48 +1,107 @@
package io.kestra.core.utils; package io.kestra.core.utils;
import ch.qos.logback.classic.Logger;
import ch.qos.logback.classic.LoggerContext;
import ch.qos.logback.classic.spi.ILoggingEvent;
import ch.qos.logback.core.AppenderBase;
import io.kestra.core.models.executions.Execution; import io.kestra.core.models.executions.Execution;
import io.kestra.core.models.executions.TaskRun; import io.kestra.core.models.executions.TaskRun;
import io.kestra.core.models.flows.Flow; import io.kestra.core.models.flows.Flow;
import io.kestra.core.models.triggers.TriggerContext; import io.kestra.core.models.triggers.TriggerContext;
import lombok.extern.slf4j.Slf4j; import lombok.extern.slf4j.Slf4j;
import org.junit.jupiter.api.AfterEach;
import org.junit.jupiter.api.BeforeAll;
import org.junit.jupiter.api.Test; import org.junit.jupiter.api.Test;
import org.slf4j.LoggerFactory;
import org.slf4j.event.Level; import org.slf4j.event.Level;
import java.util.List;
import java.util.concurrent.CopyOnWriteArrayList;
import static org.assertj.core.api.Assertions.assertThat;
@Slf4j @Slf4j
class LogsTest { class LogsTest {
private static final InMemoryAppender MEMORY_APPENDER = new InMemoryAppender();
@BeforeAll
static void setupLogger() {
Logger logger = (Logger) LoggerFactory.getLogger(Logger.ROOT_LOGGER_NAME);
MEMORY_APPENDER.setContext((LoggerContext) LoggerFactory.getILoggerFactory());
MEMORY_APPENDER.start();
logger.addAppender(MEMORY_APPENDER);
}
@AfterEach
void clearLogs() {
MEMORY_APPENDER.clear();
}
@Test @Test
void logFlow() { void logFlow() {
var flow = Flow.builder().namespace("namespace").id("flow").build(); var flow = Flow.builder().tenantId("tenant").namespace("namespace").id("flow").build();
Logs.logExecution(flow, log, Level.INFO, "Some log"); Logs.logExecution(flow, log, Level.INFO, "Some log");
Logs.logExecution(flow, log, Level.INFO, "Some log with an {}", "attribute"); Logs.logExecution(flow, log, Level.INFO, "Some log with an {}", "attribute");
Logs.logExecution(flow, log, Level.ERROR, "Some log with an {} and an error", "attribute", new RuntimeException("Test Exception")); Logs.logExecution(flow, log, Level.ERROR, "Some log with an {} and an error", "attribute", new RuntimeException("Test Exception"));
List<ILoggingEvent> logs = MEMORY_APPENDER.getLogs();
assertThat(logs).hasSize(3);
} }
@Test @Test
void logExecution() { void logExecution() {
var execution = Execution.builder().namespace("namespace").flowId("flow").id("execution").build(); var execution = Execution.builder().tenantId("tenant").namespace("namespace").flowId("flow").id("execution").build();
Logs.logExecution(execution, log, Level.INFO, "Some log");
Logs.logExecution(execution, log, Level.INFO, "Some log with an {}", "attribute");
Logs.logExecution(execution, Level.INFO, "Some log"); Logs.logExecution(execution, Level.INFO, "Some log");
Logs.logExecution(execution, Level.INFO, "Some log with an {}", "attribute");
Logs.logExecution(execution, Level.INFO, "Some log");
List<ILoggingEvent> logs = MEMORY_APPENDER.getLogs();
assertThat(logs).hasSize(3);
assertThat(logs.getFirst().getLoggerName()).isEqualTo("executor.tenant.namespace.flow");
} }
@Test @Test
void logTrigger() { void logTrigger() {
var trigger = TriggerContext.builder().namespace("namespace").flowId("flow").triggerId("trigger").build(); var trigger = TriggerContext.builder().tenantId("tenant").namespace("namespace").flowId("flow").triggerId("trigger").build();
Logs.logTrigger(trigger, log, Level.INFO, "Some log");
Logs.logTrigger(trigger, log, Level.INFO, "Some log with an {}", "attribute");
Logs.logTrigger(trigger, Level.INFO, "Some log"); Logs.logTrigger(trigger, Level.INFO, "Some log");
Logs.logTrigger(trigger, Level.INFO, "Some log with an {}", "attribute");
Logs.logTrigger(trigger, Level.INFO, "Some log");
List<ILoggingEvent> logs = MEMORY_APPENDER.getLogs();
assertThat(logs).hasSize(3);
assertThat(logs.getFirst().getLoggerName()).isEqualTo("scheduler.tenant.namespace.flow.trigger");
} }
@Test @Test
void logTaskRun() { void logTaskRun() {
var taskRun = TaskRun.builder().namespace("namespace").flowId("flow").executionId("execution").taskId("task").id("taskRun").build(); var taskRun = TaskRun.builder().tenantId("tenant").namespace("namespace").flowId("flow").executionId("execution").taskId("task").id("taskRun").build();
Logs.logTaskRun(taskRun, Level.INFO, "Some log"); Logs.logTaskRun(taskRun, Level.INFO, "Some log");
Logs.logTaskRun(taskRun, Level.INFO, "Some log with an {}", "attribute"); Logs.logTaskRun(taskRun, Level.INFO, "Some log with an {}", "attribute");
taskRun = TaskRun.builder().namespace("namespace").flowId("flow").executionId("execution").taskId("task").id("taskRun").value("value").build(); taskRun = TaskRun.builder().namespace("namespace").flowId("flow").executionId("execution").taskId("task").id("taskRun").value("value").build();
Logs.logTaskRun(taskRun, Level.INFO, "Some log"); Logs.logTaskRun(taskRun, Level.INFO, "Some log");
Logs.logTaskRun(taskRun, Level.INFO, "Some log with an {}", "attribute"); Logs.logTaskRun(taskRun, Level.INFO, "Some log with an {}", "attribute");
List<ILoggingEvent> logs = MEMORY_APPENDER.getLogs();
assertThat(logs).hasSize(4);
assertThat(logs.getFirst().getLoggerName()).isEqualTo("worker.tenant.namespace.flow.task");
}
private static class InMemoryAppender extends AppenderBase<ILoggingEvent> {
private final List<ILoggingEvent> logs = new CopyOnWriteArrayList<>();
@Override
protected void append(ILoggingEvent event) {
logs.add(event);
}
public List<ILoggingEvent> getLogs() {
return logs;
}
public void clear() {
logs.clear();
}
} }
} }