Эта проблема очень хорошо решается Logback . Я предлагаю выбрать его, если у вас есть свобода.
Если вы можете, то вам нужно будет использовать SiftingAppender . Это позволяет вам разделять файлы журналов в соответствии с некоторым значением времени выполнения. Это означает, что у вас есть широкий выбор вариантов разделения файлов журнала.
Чтобы разделить ваши файлы на requestId
, вы можете сделать что-то вроде этого:
logback.xml
<configuration>
<appender name="SIFT" class="ch.qos.logback.classic.sift.SiftingAppender">
<discriminator>
<key>requestId</key>
<defaultValue>unknown</defaultValue>
</discriminator>
<sift>
<appender name="FILE-${requestId}" class="ch.qos.logback.core.FileAppender">
<file>${requestId}.log</file>
<append>false</append>
<layout class="ch.qos.logback.classic.PatternLayout">
<pattern>%d [%thread] %level %mdc %logger{35} - %msg%n</pattern>
</layout>
</appender>
</sift>
</appender>
<root level="DEBUG">
<appender-ref ref="SIFT" />
</root>
</configuration>
Как видите (внутри элемента discriminator
), вы собираетесь различать файлы, используемые для записи журналов в requestId
. Это означает, что каждый запрос будет идти к файлу, который соответствует requestId
. Следовательно, если у вас есть два запроса, где requestId=1
, и один запрос, где requestId=2
, у вас будет 2 файла журнала: 1.log
(2 записи) и 2.log
(1 запись).
В этот момент вы можете задаться вопросом, как установить key
. Это делается путем помещения пар ключ-значение в MDC (обратите внимание, что ключ соответствует ключу, определенному в файле logback.xml
):
RequestProcessor.java
public class RequestProcessor {
private static final Logger log = LoggerFactory.getLogger(RequestProcessor.java);
public void process(Request request) {
MDC.put("requestId", request.getId());
log.debug("Request received: {}", request);
}
}
И это в основном все для простого варианта использования. Теперь каждый раз, когда поступает запрос с другим (еще не встреченным) идентификатором, для него создается новый файл.