設定しますlogback.xml
完全に機能しますが、logback-access.xml
うまくいかない。
mavenでpom.xml
<dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-access</artifactId>
</dependency>
src/main/resource
logback.xml
logback-access.xml
アクセスログを設定する方法はありますか?
サーバーコンテナに関連する機能を含める必要があります。例えば。 Tomcatの場合、LogbackValve
BeanにEmbeddedServletContainerCustomizer
を追加します。 TomcatEmbeddedServletContainerFactory
には、この目的のためのaddContextValves
メソッドがあります。
組み込みJettyの場合、SpringBoot構成の一部としてこれを記述することもできます。
@Bean
public EmbeddedServletContainerFactory jettyConfigBean() {
JettyEmbeddedServletContainerFactory jef = new JettyEmbeddedServletContainerFactory();
jef.addServerCustomizers(new JettyServerCustomizer() {
public void customize(Server server) {
HandlerCollection handlers = new HandlerCollection();
for (Handler handler : server.getHandlers()) {
handlers.addHandler(handler);
}
RequestLogHandler reqLogs = new RequestLogHandler();
NCSARequestLog reqLogImpl = new NCSARequestLog("./logs/access-yyyy_mm_dd.log");
reqLogImpl.setRetainDays(30);
reqLogImpl.setAppend(true);
reqLogImpl.setExtended(false);
reqLogImpl.setLogTimeZone("GMT");
reqLogs.setRequestLog(reqLogImpl);
handlers.addHandler(reqLogs);
server.setHandler(handlers);
// For Jetty 9.3+, use the following
//RequestLogHandler reqLogs = new RequestLogHandler();
//reqLogs.setServer(server);
//RequestLogImpl rli = new RequestLogImpl();
//rli.setResource("/logback-access.xml");
//rli.setQuiet(false);
//rli.start();
//reqLogs.setRequestLog(rli);
//handlers.addHandler(reqLogs);
//server.setHandler(handlers);
}
});
return jef;
}
SpringBoot 1.4 + Jetty + Logback-accessで動作するソリューションを何時間も試した後、私はついに自分の悩みに対する答えを見つけました。
JettyのAPIインターフェースはv9.3で変更され、Logback-accessは機能しなくなりました。
Logbackプロジェクトで、再度機能させるためのプルリクエストがありました。
https://github.com/qos-ch/logback/pull/269
上記のプルリクエストに記載されている解決策がいくつかあります。
オプション1。
Org.Eclipse.jetty.server.Slf4jRequestLog実装を使用して、ロギング構成を従来のLogbackにルーティングします。
JettyConfiguration @Bean
RequestLogHandler requestLogsHandler = new RequestLogHandler();
requestLogsHandler.setServer(server);
Slf4jRequestLog log = new Slf4jRequestLog();
log.setLoggerName("com.example.accesslog");
requestLogsHandler.setRequestLog(log);
handlers.addHandler(requestLogsHandler);
server.setHandler(handlers);
logback.xml
<appender name="FILE-ACCESS" class="ch.qos.logback.core.rolling.RollingFileAppender">
<file>${LOG_PATH}/main.log</file>
<encoder>
<!-- You'll have to work this out -->
</encoder>
<rollingPolicy class="ch.qos.logback.core.rolling.TimeBasedRollingPolicy">
<fileNamePattern>${LOG_PATH}/main.%d{yyyy-MM-dd}-%i.log
</fileNamePattern>
<timeBasedFileNamingAndTriggeringPolicy
class="ch.qos.logback.core.rolling.SizeAndTimeBasedFNATP">
<maxFileSize>20MB</maxFileSize>
</timeBasedFileNamingAndTriggeringPolicy>
<maxHistory>14</maxHistory>
</rollingPolicy>
</appender>
<logger name="com.example.accesslog">
<appender-ref ref="FILE-ACCESS" />
</logger>
これは機能しますが、Logback-accessで使用できるカスタムPatternLayoutのアクセスログ固有のパラメーターはすべて失われます。おそらく、独自のパターンクラスをロールする必要があります。
これはうまくいくかもしれないと思ったが、うまくいかなかった(または私が正しくやらなかった)。
<encoder class="ch.qos.logback.core.encoder.LayoutWrappingEncoder">
<layout class="ch.qos.logback.access.PatternLayout">
<pattern>%h %l %u [%t] "%r" %s %b "%i{Referer}" "%i{User-Agent}"</pattern>
</layout>
</encoder>
オプション2
また、上記のプルリクエストで言及されているのは、ソートされるまで使用できる問題の修正です。
不足しているインターフェイスを追加するクラスを作成し、RequestLogImplの代わりにそれを使用します。
新しいクラス
package com.example.ch.qos.logback.access.jetty;
import ch.qos.logback.access.jetty.RequestLogImpl;
import org.Eclipse.jetty.util.component.LifeCycle;
public class LogbackAccessRequestLogImplFix1052 extends RequestLogImpl implements LifeCycle {
}
Jetty構成@Bean
RequestLogHandler requestLogs = new RequestLogHandler();
requestLogs.setServer(server);
LogbackAccessRequestLogImplFix1052 rli = new LogbackAccessRequestLogImplFix1052();
rli.setResource("/logback-access.xml");
rli.setQuiet(false);
requestLogs.setRequestLog(rli);
handlers.addHandler(requestLogs);
server.setHandler(handlers);
私は両方を試しましたが、すでにこれに長い間toooooooooを費やしてきたため、今のところオプション2を使用することになりました。ただし、すべてのログ設定を同じファイルに保持できるように、オプション1を使用したいと思います。
幸運を。
プログラムのこのバージョン logback-access用のTomcatバルブの追加 作成者の元のソリューションを少し改善します。
そのためのwacaiに感謝します。これが私のバージョンです
:
を${logback.access.config.path:}
から削除しますsrc/main/resources/logback-access.xml
を想定logback-access.xml
の名前を変更するための構成オプションを削除します注:リソースから構成をロードするには、logback-access1.1.6が必要です-リソースでlogback-access.xml
を自動的に検索します。
import ch.qos.logback.access.Tomcat.LogbackValve;
import org.Apache.catalina.Context;
import org.springframework.boot.context.embedded.ConfigurableEmbeddedServletContainer;
import org.springframework.boot.context.embedded.EmbeddedServletContainerCustomizer;
import org.springframework.boot.context.embedded.Tomcat.TomcatContextCustomizer;
import org.springframework.boot.context.embedded.Tomcat.TomcatEmbeddedServletContainerFactory;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
@Configuration
public class LogbackAccessEventConfiguration {
@Bean
public EmbeddedServletContainerCustomizer containerCustomizer() {
return new EmbeddedServletContainerCustomizer() {
@Override
public void customize(ConfigurableEmbeddedServletContainer container) {
if (container instanceof TomcatEmbeddedServletContainerFactory) {
((TomcatEmbeddedServletContainerFactory) container)
.addContextCustomizers(new TomcatContextCustomizer() {
@Override
public void customize(Context context) {
LogbackValve logbackValve = new LogbackValve();
logbackValve.setFilename("logback-access.xml");
context.getPipeline().addValve(logbackValve);
}
});
}
}
};
}
}
この例では、このスレッドで前述したように、ログバックアクセスログの生成を中断するJetty v9.x +に付属するプロジェクトをSpringBoot1.3.0から1.5.16.RELEASEに更新しました。この問題を修正するために、次の手順を実行しました-
@Bean
RequestLog makeRequestLog() {
RequestLog requestLog = new Jetty93RequestLogImpl()
requestLog.resource = '/logback-access.xml'
requestLog
}
// Jetty 9.x
private static class Jetty93RequestLogImpl extends RequestLogImpl implements LifeCycle {
}
Spring boot 2(2.1.4.RELEASE)を使用した例。私にとってはうまくいきます。
@Component
public class JettyCustomizationConfig implements WebServerFactoryCustomizer<ConfigurableJettyWebServerFactory> {
@Override
public void customize(ConfigurableJettyWebServerFactory server) {
server.addServerCustomizers(customJettyServer());
}
private JettyServerCustomizer customJettyServer() {
return server -> {
HandlerCollection handlers = new HandlerCollection();
RequestLogHandler requestLogHandler = new RequestLogHandler();
requestLogHandler.setServer(server);
RequestLogImpl requestLog = new RequestLogImpl();
requestLog.setResource("/logback-access.xml");
requestLog.setQuiet(false);
requestLog.start();
requestLogHandler.setRequestLog(requestLog);
handlers.addHandler(server.getHandler());
handlers.addHandler(requestLogHandler);
server.setHandler(handlers);
};
}
}
logback-access.xml
<?xml version="1.0" encoding="UTF-8"?>
<configuration>
<statusListener class="ch.qos.logback.core.status.OnConsoleStatusListener" />
<property name="log.path" value="logs" />
<appender name="FILE" class="ch.qos.logback.core.rolling.RollingFileAppender">
<rollingPolicy class="ch.qos.logback.core.rolling.TimeBasedRollingPolicy">
<fileNamePattern>${log.path}/requests/seastar_request_%d{yyyy-MM-dd}.log</fileNamePattern>
</rollingPolicy>
</appender>
<appender-ref ref="FILE"/>
</configuration>
別の方法は、サーブレットフィルタを登録し、通常のログに書き込むことです。
アクセスイベントが他のイベントと混在しないようにするには、additivity
を無効にします。
<appender name="ACCESS-LOG"
class="ch.qos.logback.core.rolling.RollingFileAppender">
<file>./log/evilAccess.log</file>
<encoder class="ch.qos.logback.classic.encoder.PatternLayoutEncoder">
<Pattern>
%d{yyyy-MM-dd HH:mm:ss} %msg ip=%mdc{ip} session=%mdc{session} user=%mdc{user}%n
</Pattern>
</encoder>
<rollingPolicy class="ch.qos.logback.core.rolling.SizeAndTimeBasedRollingPolicy">
<fileNamePattern>./log/evilAccess-%d{yyyy-MM-dd}.%i.log</fileNamePattern>
<maxFileSize>5MB</maxFileSize>
<maxHistory>30</maxHistory>
</rollingPolicy>
</appender>
<logger name="com.evil.web.log.MyAccessLogFilter" level="debug" additivity="false">
<appender-ref ref="ACCESS-LOG" />
</logger>
<logger name="com.evil.web.log.MyAccessLogFilter" level="debug" additivity="false">
<appender-ref ref="ACCESS-LOG" />
</logger>
LoggingFilter
は通常のサーブレットフィルターであり、@ServletComponentScan
クラスの@Configuration
+ @WebFilter
のimplements javax.servlet.Filter
またはBean構成を介してSpringBootアプリに簡単に登録できます。
@Bean
myAccessLogFilter myAccessLogFilter() {
SaAccessLogFilter filter = new MyAccessLogFilter();
// filter.setMaxPayloadLength(100);
return filter;
}
@Bean
FilterRegistrationBean registration() {
FilterRegistrationBean registration = new FilterRegistrationBean(myAccessLogFilter());
registration.setOrder(1);
registration.setEnabled(true);
return registration;
}
少なくともGenericFilterBean
以上のOncePerRequestFilter
を使用することをお勧めします。 org.springframework.web.filter
パッケージ内でSpringWebによってすでに提供されているいくつかのロギングフィルター:
AbstractRequestLoggingFilter
CommonsRequestLoggingFilter
ServletContextRequestLoggingFilter
OncePerRequestFilter
に基づいて独自の実装を定義し、Slf4jMDCコンテキストにIPアドレスやその他の情報を入力します。
現在受け入れられている回答 の実装、 Ego Slayer の提供、コミュニティwikiとして投稿:
私は http://spring.io/guides/gs/rest-service/ から始めます
ここにファイルを作成するだけですsrc/main/Java/hello/MyConfig.Java
package hello;
import org.Apache.catalina.valves.AccessLogValve;
import org.springframework.boot.context.embedded.ConfigurableEmbeddedServletContainerFactory;
import org.springframework.boot.context.embedded.EmbeddedServletContainerCustomizer;
import org.springframework.boot.context.embedded.Tomcat.TomcatEmbeddedServletContainerFactory;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import ch.qos.logback.access.Tomcat.LogbackValve;
@Configuration
public class MyConfig {
@Bean
public EmbeddedServletContainerCustomizer containerCustomizer(){
return new EmbeddedServletContainerCustomizer() {
@Override
public void customize(ConfigurableEmbeddedServletContainerFactory factory) {
if(factory instanceof TomcatEmbeddedServletContainerFactory){
TomcatEmbeddedServletContainerFactory containerFactory = (TomcatEmbeddedServletContainerFactory) factory;
LogbackValve logbackValve = new LogbackValve();
logbackValve.setFilename("src/main/resources/logback-access.xml");
containerFactory.addContextValves(logbackValve);
}
}
};
}
}
そして、Mavenにlogback-access
を追加しますpom.xml
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.Apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.Apache.org/POM/4.0.0 http://maven.Apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>org.springframework</groupId>
<artifactId>gs-rest-service</artifactId>
<version>0.1.0</version>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>0.5.0.M6</version>
</parent>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-databind</artifactId>
</dependency>
<dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-access</artifactId>
<version>1.0.13</version>
</dependency>
</dependencies>
<properties>
<start-class>hello.Application</start-class>
</properties>
<build>
<plugins>
<plugin>
<artifactId>maven-compiler-plugin</artifactId>
<version>2.3.2</version>
</plugin>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
<repositories>
<repository>
<id>spring-snapshots</id>
<url>http://repo.spring.io/libs-snapshot</url>
<snapshots><enabled>true</enabled></snapshots>
</repository>
</repositories>
<pluginRepositories>
<pluginRepository>
<id>spring-snapshots</id>
<url>http://repo.spring.io/libs-snapshot</url>
<snapshots><enabled>true</enabled></snapshots>
</pluginRepository>
</pluginRepositories>
</project>