@Bean不加public修饰会生效吗?为什么?-灵析社区

我是张工你呢

@Bean不加public修饰会生效吗?为什么 @Bean RestTemplate restTemplate() { return new RestTemplate(); } 证明生效或者没生效

阅读量:14

点赞量:0

问AI
通常模式 Spring 对 "@Bean"注解的要求是必须是可重写,所以"public","protected","package"这几种修饰都是可以的。 简单验证: import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.web.client.RestTemplate; @Configuration public class Config { @Bean RestTemplate restTemplate() { return new RestTemplate(); } } import org.springframework.web.client.RestTemplate; public class MyService { RestTemplate restTemplate; public MyService(RestTemplate restTemplate) { this.restTemplate = restTemplate; } public String getHelloWorld() { return restTemplate.getForObject("http://httpbin.org/ip", String.class); } } import org.springframework.context.ApplicationContext; import org.springframework.web.client.RestTemplate; public class Main { public static void main(String[] args) { ApplicationContext context = new org.springframework.context.annotation.AnnotationConfigApplicationContext(Config.class); MyService myService = new MyService(context.getBean(RestTemplate.class)) ; System.out.println("Hello world from: "+myService.getHelloWorld() ); } } 运行输出: Hello world from: { "origin": "114.251.201.2" } 反过来说, "private" 是不可以的 https://wmlx-new-image.oss-cn-shanghai.aliyuncs.com/images/20241108/049f7618451a95687abc10de493cce41.png 另外, "static" 方法也是可以被 "@Bean" 修饰的。 摘一段源码文档: «Typically, @Bean methods are declared within @Configuration classes. In this case, bean methods may reference other @Bean methods in the same class by calling them directly. This ensures that references between beans are strongly typed and navigable. Such so-called 'inter-bean references' are guaranteed to respect scoping and AOP semantics, just like getBean() lookups would. These are the semantics known from the original 'Spring JavaConfig' project which require CGLIB subclassing of each such configuration class at runtime. As a consequence, @Configuration classes and their factory methods must not be marked as final or private in this mode.» 最后一句机翻一下: «这些是原始“Spring JavaConfig”项目中已知的语义,需要在运行时对每个此类配置类进行 CGLIB 子类化。因此,在此模式下,不得将@Configuration类及其工厂方法标记为最终或私有。» 所以通常模式 "final" 和 "private" 修饰是不可以的。 小模式(Lite Mode) "@Bean" 直接定义的 "@Component" \ "@Service" 里: import org.springframework.beans.factory.annotation.Autowired; import org.springframework.context.annotation.Bean; import org.springframework.stereotype.Component; import org.springframework.web.client.RestTemplate; @Component public class MyService { @Autowired RestTemplate restTemplate; public String getHelloWorld() { return restTemplate.getForObject("http://httpbin.org/ip", String.class); } @Bean private RestTemplate restTemplate() { return new RestTemplate(); } } import org.springframework.context.ApplicationContext; import org.springframework.context.annotation.AnnotationConfigApplicationContext; public class Main { public static void main(String[] args) { ApplicationContext context = new AnnotationConfigApplicationContext(MyService.class); MyService myService = context.getBean(MyService.class); System.out.println("Hello world from: "+myService.getHelloWorld() ); } } 这种情况下,定义成 "private" 是可以。 总结 小模式下可以为"private", 通常模式下不可以为"private", 限制更少的 "package" 都是可以的