4

我正在尝试配置LogbackValve获取访问日志,以防我的基于 Spring Boot 的 Web 应用程序从嵌入式 Tomcat 运行。以下是配置代码:

import javax.servlet.Servlet;

import org.apache.catalina.startup.Tomcat;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.autoconfigure.condition.ConditionalOnClass;
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
import org.springframework.boot.autoconfigure.condition.ConditionalOnBean;
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 EmbeddedTomcatConfigurator {

    @Bean
    @ConditionalOnClass({ Servlet.class, Tomcat.class })
    @ConditionalOnBean(value = LogbackValve.class)
    public TomcatEmbeddedServletContainerFactory tomcatEmbeddedServletContainerFactory(LogbackValve logbackValve) {
        TomcatEmbeddedServletContainerFactory factory = new TomcatEmbeddedServletContainerFactory();
        factory.addContextValves(logbackValve);
        return factory;
    }

    @Bean
    @ConditionalOnProperty(name = "embedded.tomcat.logback.access.config.path")
    public LogbackValve logbackValve(@Value("${embedded.tomcat.logback.access.config.path:}") String fileName) {
        LogbackValve logbackValve = new LogbackValve();
        logbackValve.setFilename(fileName);
        return logbackValve;
    }
}

但是,每次我在调试模式下使用“mvn spring-boot:run”启动应用程序时,我都会在尝试创建“tomcatEmbeddedServletContainerFactory”bean 的实例时看到日志显示“找不到 LogbackValve”。但是,另一个日志语句表明创建了这个 bean。因此,它总是初始化自动配置类“org.springframework.boot.autoconfigure.web.EmbeddedServletContainerAutoConfiguration”中定义的bean。

现在,我已将我的课程修改为:

import javax.servlet.Servlet;

import org.apache.catalina.startup.Tomcat;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.autoconfigure.condition.ConditionalOnClass;
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
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 EmbeddedTomcatConfigurator {

    @Bean
    @ConditionalOnClass({ Servlet.class, Tomcat.class })
    @ConditionalOnProperty(name = "embedded.tomcat.logback.access.config.path")
    public TomcatEmbeddedServletContainerFactory tomcatEmbeddedServletContainerFactory(@Value("${embedded.tomcat.logback.access.config.path:}") String logbackAccessPath) {
        TomcatEmbeddedServletContainerFactory factory = new TomcatEmbeddedServletContainerFactory();
        factory.addContextValves(getLogbackValve(logbackAccessPath));
        return factory;
    }

    private LogbackValve getLogbackValve(String fileName) {
        LogbackValve logbackValve = new LogbackValve();
        logbackValve.setFilename(fileName);
        return logbackValve;
    }

}

我已经在Git上问过这个问题,并且已经解决。但是,在这里,我要提出的一点是,为什么 @ConditionalOnBean(value = LogbackValve.class) 没有检测到也已定义的 bean。

4

0 回答 0