当前位置: 首页 > 面试题库 >

春季启动-@PostConstruct未在@Component上调用

左丘昊天
2023-03-14
问题内容

我是spring的新手,我使用https://start.spring.io/创建了一个新的spring
boot项目,没有更多依赖关系,解压缩了zip文件并在IntelliJ
IDEA中打开了该项目。我没有做任何进一步的配置。我现在正在尝试使用@PostConstruct方法设置bean-但是,该方法从未被spring调用。

这些是我的课程:

SpringTestApplication.java

package com.habichty.test.testspring;

import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.ConfigurableApplicationContext;

@SpringBootApplication
    public class SpringTestApplication {

        public static void main(String[] args) {
            ConfigurableApplicationContext context = SpringApplication.run(SpringTestApplication.class, args);
            context.getBean(TestBean.class).testMethod();
        }
    }

TestBean.java

package com.habichty.test.testspring;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Component;
import javax.annotation.PostConstruct;

@Component  
    public class TestBean {
            private final Logger log = LoggerFactory.getLogger(this.getClass());
            private int a = 1;

            public TestBean()
            {
                log.debug("Constructor of TestBean called.");
            }

            @PostConstruct
            public void init()
            {
                log.debug("init()-Method of TestBean called.");
                a = 2;
            }

            public void testMethod()
            {
                log.debug("Test Method of TestBean called. a=" + a);
            }

        }

当我启动应用程序时,这是我的输出:

 :: Spring Boot ::        (v1.5.9.RELEASE)

2018-01-22 13:15:57.960  INFO 12035 --- [           main] c.h.t.testspring.SpringTestApplication   : Starting SpringTestApplication on pbtp with PID 12035 (/home/pat/prj/testspring/testspring/target/classes started by pat in /home/pat/prj/testspring/testspring)
2018-01-22 13:15:57.962 DEBUG 12035 --- [           main] c.h.t.testspring.SpringTestApplication   : Running with Spring Boot v1.5.9.RELEASE, Spring v4.3.13.RELEASE
2018-01-22 13:15:57.962  INFO 12035 --- [           main] c.h.t.testspring.SpringTestApplication   : No active profile set, falling back to default profiles: default
2018-01-22 13:15:58.018  INFO 12035 --- [           main] s.c.a.AnnotationConfigApplicationContext : Refreshing org.springframework.context.annotation.AnnotationConfigApplicationContext@2931522b: startup date [Mon Jan 22 13:15:58 CET 2018]; root of context hierarchy
2018-01-22 13:15:58.510 DEBUG 12035 --- [           main] com.habichty.test.testspring.TestBean    : Constructor of TestBean called.
2018-01-22 13:15:58.793  INFO 12035 --- [           main] o.s.j.e.a.AnnotationMBeanExporter        : Registering beans for JMX exposure on startup
2018-01-22 13:15:58.822  INFO 12035 --- [           main] c.h.t.testspring.SpringTestApplication   : Started SpringTestApplication in 1.073 seconds (JVM running for 2.025)
2018-01-22 13:15:58.822 DEBUG 12035 --- [           main] com.habichty.test.testspring.TestBean    : Test Method of TestBean called. a=1
2018-01-22 13:15:58.826  INFO 12035 --- [       Thread-1] s.c.a.AnnotationConfigApplicationContext : Closing org.springframework.context.annotation.AnnotationConfigApplicationContext@2931522b: startup date [Mon Jan 22 13:15:58 CET 2018]; root of context hierarchy
2018-01-22 13:15:58.828  INFO 12035 --- [       Thread-1] o.s.j.e.a.AnnotationMBeanExporter        : Unregistering JMX-exposed beans on shutdown

如您所见,spring初始化了TestBean并执行了testMethod(),但是没有调用以@PostConstruct注释的init()-Method。

我究竟做错了什么?任何帮助都非常感谢。

更新1 在我的application.properties中,我已配置:

logging.level.com = DEBUG

将其更改为 logging.level.root = DEBUG会 导致更大的日志。但是,它仍然不包含我的init()方法的调试消息。

更新2 添加了package和import语句。

更新3
为了进一步说明这不是日志记录问题,我向应该由init()-Method更改的代码中添加了一个新的int。据我了解@PostConstruct批注的概念,应该在执行任何其他方法之前执行它。结果,testMethod()的输出现在应该包含
a = 2 。在更新的输出中,您可能会发现情况并非如此。

更新4 这是我的POM

    <?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>com.habichty.test.testspring</groupId>
    <artifactId>springTest</artifactId>
    <version>0.0.1-SNAPSHOT</version>
    <packaging>jar</packaging>

    <name>springTest</name>
    <description>springTest</description>

    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>1.5.9.RELEASE</version>
        <relativePath/> <!-- lookup parent from repository -->
    </parent>

    <properties>
        <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
        <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
        <java.version>1.8</java.version>
    </properties>

    <dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter</artifactId>
        </dependency>

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
            <scope>test</scope>
        </dependency>
    </dependencies>

    <build>
        <plugins>
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
            </plugin>
        </plugins>
    </build>
</project>

输出java -version

java version "9.0.1"
Java(TM) SE Runtime Environment (build 9.0.1+11)
Java HotSpot(TM) 64-Bit Server VM (build 9.0.1+11, mixed mode)

问题答案:

由于Java9中的新模块系统SpringBoot-1.5.9无法处理,@PostConstruct因为注释类不在类路径中。问题(或类似问题)在此处和此处进行描述。有几种解决方法:

  • 使用Java8运行该应用程序,
    或者如果仍在Java9上运行该应用程序:

  • javax.annotation:javax.annotation-api向POM 添加依赖项,或

  • 升级到更新的2.0.0+版本的Spring-Boot(在撰写本文时仍为PRERELEASE),其中包含该依赖项;


 类似资料:
  • 问题内容: 我的Maven依赖项出了什么问题。当我包含JPA时,我会列出pf例外 这是我的Maven依赖项 我的例外 和我的源代码 因此,我没有任何想法(不幸的是,没有示例)如何运行Spring boot和休眠两者。 问题答案: 您是否为数据源设置了或?这是一个例子: 有关可以在何处放置配置文件以及如何配置应用程序以处理任何目录中的属性文件的说明,请参阅此链接以获取更多信息。

  • 问题内容: 我已经拥有一个Azure Web App服务和一个SQL数据库。我正在使用Azures Intellij插件来“在Web App上运行”。问题是,它什么也没运行,但是确实将罐子放在文件夹中: 然后,我使用控制台尝试通过使用来运行,但收到错误消息 Java不被识别为内部命令或外部命令 在webapp应用程序设置中,我假设它可以让我运行Java,但这只是让我怀疑我的操作方式。我部署应用程序

  • 问题内容: 我目前正在使用Spring编写API后端,我想使用Spring Boot部署到生产服务器上。 如果我在Eclipse中运行后端以编译为War(在Maven中指定),并使用Tomcat 7,则它可以正常运行。 但是,当我想部署到服务器时,我正在使用Spring Boot。 应用程序 pom.xml 当我将整个项目复制到Linux服务器上并运行 maven package时 ,代码可以毫无

  • 问题内容: 我试图将Spring集成到具有数千个类的大型应用程序中,并且由于组件扫描,我在启动容器时遇到了巨大的延迟。 我已经将“基本软件包”中指定的目录数量缩小到最小,以减少扫描无关目录所浪费的时间,但是初始化的类路径扫描部分仍然需要大约1-2分钟。 那么,有没有一种方法可以优化扫描过程?我曾考虑过将候选类路径存储在文件中,然后使容器从文件中获取,而不是每次启动时都扫描类路径,但是我真的不知道从

  • 问题内容: 我有以下Spring Security配置: 我期望以下逻辑:未经身份验证的用户将被重定向到。Spring会显示默认的Tomcat 403页面,而不是该页面。我也尝试过自定义,尽管没有成功。 如何在访问失败时实施自定义逻辑? 问题答案: AccessDeniedHandler仅适用于经过身份验证的用户。未经身份验证的用户的默认行为是重定向到登录页面(或适用于所使用的身份验证机制的任何内

  • 问题内容: 我正在使用logback库在spring boot项目中实现日志记录。我想根据我的spring配置文件(属性“ spring.pofiles.active”)加载不同的日志记录配置文件。我有3个文件:logback-dev.xml,logback- inte.xml和logback-prod.xml。我正在使用Spring Boot版本1.2.2.RELEASE。 如您在Spring