Respuestas:
No, prácticamente no creo que haya ninguna diferencia, pero hay prioridades en la forma en que funcionan. @PostConstruct, init-methodson BeanPostProcessors.
@PostConstructes una anotación JSR-250 mientras que init-methodes la forma en que Spring tiene un método de inicialización.@PostConstructmétodo, se llamará primero antes de llamar a los métodos de inicialización.afterPropertiesSet, primero @PostConstructse llama, luego afterPropertiesSety luego init-method.Para obtener más información, puede consultar la documentación de referencia de Spring .
Antes de las especificaciones JSR 250, el uso del método init en xml era la forma preferida, ya que desacopla las clases Java (beans) de cualquier clase / anotaciones específicas de Spring. Entonces, si está construyendo una biblioteca que no necesita depender de los beans de infraestructura de Spring luego se prefirió el uso del método init.Durante el método de creación, puede especificar el método que debe llamarse como método de inicialización.
Ahora, con la introducción de las especificaciones JSR 250 en Java EE y el soporte de primavera de estas anotaciones, la dependencia del marco de primavera se ha reducido hasta cierto punto.
Pero tengo que admitir que la adición de estas cosas aumenta la legibilidad del código, por lo que existen ventajas y desventajas en ambos enfoques.
No hay ninguna diferencia real. Depende de cómo prefiera configurar su sistema, y eso es una cuestión de elección personal. Yo mismo, prefiero usar @PostConstructanotaciones para mi propio código (ya que el bean solo está configurado correctamente después de que se llama al método) y lo uso init-methodal crear instancias de beans de bibliotecas que no son compatibles con Spring (¡no se pueden aplicar anotaciones allí, por supuesto!) pero puedo entender totalmente que la gente quiera hacerlo todo de una forma u otra.
@postconstruct no es parte de la primavera. Es parte del paquete javax. Ambos son iguales. usando el método init debemos agregarlo en el archivo xml. Si usa @postconstruct, no es necesario agregar en xml. Consulte el artículo a continuación.
Como puede ver en el siguiente diagrama de devolución de llamada del ciclo de vida de la creación de Bean .
Este 3 paso ocurre en la devolución de llamada del ciclo de vida de la creación de Bean:
@PostConstructse llamará.InitializingBeanse implementa, entonces afterPropertiesSet()se llamará.init-methodo @Bean(initmethod="..")entonces llama al método init.Este diagrama es de Pro Spring 5: una guía detallada del marco de Spring y sus herramientas
No puede haber diferencia entre @PostConstructy init-methodporque @PostConstructse maneja en la postProcessAfterInitializationfase de inicialización del frijol ( AbstractAutowireCapableBeanFactory.initializeBean()método) por CommonAnnotationBeanPostProcessor, mientras que initel método es llamado después de la finalización de la postProcessBeforeInitializationfase (y, por este asunto, antes del comienzo de postProcessAfterInitializationla fase).
EDITAR : Entonces, la secuencia es: 1) postProcessBeforeInitializationfase, 2) initse llama al método, 3) postProcessAfterInitializationfase, que llama al @PostConstructmétodo
(Como nota al margen, una declaración de la respuesta aceptada
@PostConstruct, init-method son BeanPostProcessors
no es del todo correcto: @PostConstructes manejado por a BeanPostProcessor, el initmétodo no lo es.)
Habrá una diferencia si alguno (potencialmente personalizado) BeanPostProcessor, que está configurado con ( Ordered.getOrder()) para ejecutarse después CommonAnnotationBeanPostProcessor, está haciendo algo serio en su postProcessBeforeInitializationmétodo.
No hay ninguna diferencia con la configuración predeterminada de Spring BeanPostProcessorsporque todos los BeanPostProcessorsque están configurados para ejecutarse después CommonAnnotationBeanPostProcessor, no hacen nada en el postProcessBeforeInitializationmétodo.
En conclusión, la respuesta aceptada y similares son correctas ... en el 99% de los casos, y esta publicación es solo para rendir homenaje a un concepto "el diablo está en los detalles"
Código completo aquí: https://github.com/wkaczurba/so8519187 ( spring-boot )
Usando anotaciones:
@Slf4j
@Component
public class MyComponent implements InitializingBean {
@Value("${mycomponent.value:Magic}")
public String value;
public MyComponent() {
log.info("MyComponent in constructor: [{}]", value); // (0) displays: Null
}
@PostConstruct
public void postConstruct() {
log.info("MyComponent in postConstruct: [{}]", value); // (1) displays: Magic
}
@Override // init-method; overrides InitializingBean.afterPropertiesSet()
public void afterPropertiesSet() {
log.info("MyComponent in afterPropertiesSet: [{}]", value); // (2) displays: Magic
}
@PreDestroy
public void preDestroy() {
log.info("MyComponent in preDestroy: [{}]", value); // (3) displays: Magic
}
}
Nos consigue:
Actualizando org.springframework.context ...
MyComponent en el constructor: [nulo]
MyComponent en postConstruct: [Magic]
MyComponent en afterPropertiesSet: [Magic]
...
Registrando beans para la exposición JMX al inicio
Comenzó la DemoApplication en 0.561 segundos (JVM ejecutándose para 1.011)
Cerrando org.springframework.context .. . Eliminando el registro de beans expuestos a JMX al apagar
...
MyComponent en preDestroy: [Magic]