当前位置: 首页 > news >正文

wordpress内置播放器百度搜索seo

wordpress内置播放器,百度搜索seo,新建的网站需要维护吗,论坛申请网站备案前置审批InitializingBean 记住一点:InitializingBean接口为bean提供了初始化方法的方式,它只包括afterPropertiesSet方法,凡是继承该接口的子类,在初始化bean的时候会执行该方法。 下面看下简单的例子:(环境是用…

InitializingBean

记住一点:InitializingBean接口为bean提供了初始化方法的方式,它只包括afterPropertiesSet方法,凡是继承该接口的子类,在初始化bean的时候会执行该方法。

下面看下简单的例子:(环境是用Spring Boot搭建,直接用SpringtestApplication启动即可)

<bean id="myInitializingBean" class="com.paic.phssp.springtest.init.MyInitializingBean" init-method="testInit"></bean>
package com.paic.phssp.springtest.init;import org.springframework.beans.factory.InitializingBean;
import org.springframework.stereotype.Component;import javax.annotation.PostConstruct;/*** 继承InitializingBean接口的类,在初始化bean的时候会执行该方法*/
//@Component
public class MyInitializingBean implements InitializingBean {public MyInitializingBean() {System.out.println("MyInitializingBean....");}@Overridepublic void afterPropertiesSet() throws Exception {System.out.println("ceshi MyInitializingBean>>>>>>>>>>>>>>>>>>>");}@PostConstruct  //功能上近似init-method,但加载时机不同public void test(){System.out.println("PostConstruct >>>>>>>>>>>>");}public void testInit(){System.out.println("ceshi init-method");}
}

结果:

MyInitializingBean…
PostConstruct >>>>>>>>>>>>
ceshi MyInitializingBean>>>>>>>>>>>>>>>>>>>
ceshi init-method

说明:

通过上述输出结果,三者的先后顺序也就一目了然了:

Constructor > @PostConstruct > InitializingBean > init-method

(1)通过查看spring的加载bean的源码类(AbstractAutowireCapableBeanFactory)可看出其中奥妙:

AbstractAutowireCapableBeanFactory.invokeInitMethods

protected void invokeInitMethods(String beanName, Object bean, @Nullable RootBeanDefinition mbd) throws Throwable {boolean isInitializingBean = bean instanceof InitializingBean;if (isInitializingBean && (mbd == null || !mbd.isExternallyManagedInitMethod("afterPropertiesSet"))) {if (this.logger.isTraceEnabled()) {this.logger.trace("Invoking afterPropertiesSet() on bean with name '" + beanName + "'");}if (System.getSecurityManager() != null) {try {AccessController.doPrivileged(() -> {((InitializingBean)bean).afterPropertiesSet();return null;}, this.getAccessControlContext());} catch (PrivilegedActionException var6) {throw var6.getException();}} else {((InitializingBean)bean).afterPropertiesSet();}}if (mbd != null && bean.getClass() != NullBean.class) {String initMethodName = mbd.getInitMethodName();if (StringUtils.hasLength(initMethodName) && (!isInitializingBean || !"afterPropertiesSet".equals(initMethodName)) && !mbd.isExternallyManagedInitMethod(initMethodName)) {this.invokeCustomInitMethod(beanName, bean, mbd);}}}

说明:

a、spring为bean提供了两种初始化bean的方式,实现InitializingBean接口,实现afterPropertiesSet方法,或者在配置文件中同过init-method指定,两种方式可以同时使用
b、实现InitializingBean接口是直接调用afterPropertiesSet方法,比通过反射调用init-method指定的方法效率相对来说要高点。但是init-method方式消除了对spring的依赖
c、如果调用afterPropertiesSet方法时出错,则不调用init-method指定的方法。
d、@PostConstruct注解后的方法在BeanPostProcessor前置处理器中就被执行了,所以当然要先于InitializingBean和init-method执行了。

下面看@PostConstruct加载过程,主要看CommonAnnotationBeanPostProcessor.class。看下面UML图:
在这里插入图片描述

看下源码:InitDestroyAnnotationBeanPostProcessor.class

public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {InitDestroyAnnotationBeanPostProcessor.LifecycleMetadata metadata = this.findLifecycleMetadata(bean.getClass());try {//利用反射,执行注解方法metadata.invokeInitMethods(bean, beanName);return bean;} catch (InvocationTargetException var5) {throw new BeanCreationException(beanName, "Invocation of init method failed", var5.getTargetException());} catch (Throwable var6) {throw new BeanCreationException(beanName, "Failed to invoke init method", var6);}}private InitDestroyAnnotationBeanPostProcessor.LifecycleMetadata findLifecycleMetadata(Class<?> clazz) {if (this.lifecycleMetadataCache == null) {return this.buildLifecycleMetadata(clazz);} else {InitDestroyAnnotationBeanPostProcessor.LifecycleMetadata metadata = (InitDestroyAnnotationBeanPostProcessor.LifecycleMetadata)this.lifecycleMetadataCache.get(clazz);if (metadata == null) {Map var3 = this.lifecycleMetadataCache;synchronized(this.lifecycleMetadataCache) {metadata = (InitDestroyAnnotationBeanPostProcessor.LifecycleMetadata)this.lifecycleMetadataCache.get(clazz);if (metadata == null) {metadata = this.buildLifecycleMetadata(clazz);this.lifecycleMetadataCache.put(clazz, metadata);}return metadata;}} else {return metadata;}}
}private InitDestroyAnnotationBeanPostProcessor.LifecycleMetadata buildLifecycleMetadata(Class<?> clazz) {List<InitDestroyAnnotationBeanPostProcessor.LifecycleElement> initMethods = new ArrayList();List<InitDestroyAnnotationBeanPostProcessor.LifecycleElement> destroyMethods = new ArrayList();Class targetClass = clazz;do {List<InitDestroyAnnotationBeanPostProcessor.LifecycleElement> currInitMethods = new ArrayList();List<InitDestroyAnnotationBeanPostProcessor.LifecycleElement> currDestroyMethods = new ArrayList();ReflectionUtils.doWithLocalMethods(targetClass, (method) -> {//判断是否是指定的注解类型if (this.initAnnotationType != null && method.isAnnotationPresent(this.initAnnotationType)) {InitDestroyAnnotationBeanPostProcessor.LifecycleElement element = new InitDestroyAnnotationBeanPostProcessor.LifecycleElement(method);currInitMethods.add(element);if (this.logger.isTraceEnabled()) {this.logger.trace("Found init method on class [" + clazz.getName() + "]: " + method);}}if (this.destroyAnnotationType != null && method.isAnnotationPresent(this.destroyAnnotationType)) {currDestroyMethods.add(new InitDestroyAnnotationBeanPostProcessor.LifecycleElement(method));if (this.logger.isTraceEnabled()) {this.logger.trace("Found destroy method on class [" + clazz.getName() + "]: " + method);}}});initMethods.addAll(0, currInitMethods);destroyMethods.addAll(currDestroyMethods);targetClass = targetClass.getSuperclass();} while(targetClass != null && targetClass != Object.class);return new InitDestroyAnnotationBeanPostProcessor.LifecycleMetadata(clazz, initMethods, destroyMethods);
}

方法:buildLifecycleMetadata(),判断是否是指定的注解类型,而这个属性,在CommonAnnotationBeanPostProcessor.class构造方法中被初始化为PostConstruct。

public CommonAnnotationBeanPostProcessor() {this.setOrder(2147483644);this.setInitAnnotationType(PostConstruct.class);this.setDestroyAnnotationType(PreDestroy.class);this.ignoreResourceType("javax.xml.ws.WebServiceContext");}

那么问题来了,以上只能说明实现了BeanPostProcessor的postProcessBeforeInitialization()方法,不足说明@PostConstruct 先InitializingBean 。

再看AbstractAutowireCapableBeanFactory.class 的initializeBean()方法。

protected Object initializeBean(String beanName, Object bean, @Nullable RootBeanDefinition mbd) {if (System.getSecurityManager() != null) {AccessController.doPrivileged(() -> {this.invokeAwareMethods(beanName, bean);return null;}, this.getAccessControlContext());} else {this.invokeAwareMethods(beanName, bean);}Object wrappedBean = bean;if (mbd == null || !mbd.isSynthetic()) {wrappedBean = this.applyBeanPostProcessorsBeforeInitialization(bean, beanName);}try {this.invokeInitMethods(beanName, wrappedBean, mbd);} catch (Throwable var6) {throw new BeanCreationException(mbd != null ? mbd.getResourceDescription() : null, beanName, "Invocation of init method failed", var6);}if (mbd == null || !mbd.isSynthetic()) {wrappedBean = this.applyBeanPostProcessorsAfterInitialization(wrappedBean, beanName);}return wrappedBean;}

这下明显了,下面小结下:

BeanPostProcessor的实现类注册到Spring IOC容器后,对于该Spring IOC容器所创建的每个bean实例在初始化方法(如afterPropertiesSet和任意已声明的init方法)调用前,将会调用BeanPostProcessor中的postProcessBeforeInitialization方法,而在bean实例初始化方法调用完成后,则会调用BeanPostProcessor中的postProcessAfterInitialization方法,整个调用顺序可以简单示意如下:
–> Spring IOC容器实例化Bean
–> 调用BeanPostProcessor的postProcessBeforeInitialization方法 (@PostConstruct在此)
–> 调用bean实例的初始化方法(invokeInitMethods-> InitializingBean->init-method)
–> 调用BeanPostProcessor的postProcessAfterInitialization方法

参考:https://blog.csdn.net/zl834205311/article/details/78802584

DisposableBean
在Bean生命周期结束前调用destory()方法做一些收尾工作,亦可以使用destory-method。
前者与Spring耦合高,使用类型强转.方法名(),效率高
后者耦合低,使用反射,效率相对低

首先看下入口代码结构:
在这里插入图片描述

其中AbstractApplicationContext.refresh()

@Overridepublic void refresh() throws BeansException, IllegalStateException {synchronized (this.startupShutdownMonitor) {// Prepare this context for refreshing.// 为刷新工作做一些当前上下文 context 上的准备工作prepareRefresh();// Tell the subclass to refresh the internal bean factory.// ApplicationContext 实现了 BeanFactory 接口,但是并非直接作为 Bean 容器。// ApplicationContext 中真正直接作为 Bean 容器的是一个内部Bean工厂 BeanFactory,// 通过其方法 getBeanFactory() 得到,此方法在 AbstractApplicationContext 中// 被声明为 abstract, 其实现要求由实现子类提供。下面的语句 obtainFreshBeanFactory()// 内部就是通过调用 getBeanFactory() 获得这个内部 Bean 工厂的。ConfigurableListableBeanFactory beanFactory = obtainFreshBeanFactory();// Prepare the bean factory for use in this context.// 准备当前上下文使用的Bean容器 BeanFactory,设置其标准上下文特征,比如类加载器等// 1. BeanFactory 的类加载器设置为当前上下文的类加载器// 2. BeanFactory 的Bean表达式解析器设置为 new StandardBeanExpressionResolver()// 3. BeanFactory 增加 BeanPostProcessror new ApplicationListenerDetector(this)// 4.三个单例Bean被注册 : environment,systemProperties,systemEnvironmentprepareBeanFactory(beanFactory);try {// Allows post-processing of the bean factory in context subclasses.// 在当前上下文使用的Bean容器BeanFactory的标准初始化完成后对其做一些修改。此时// 所有的Bean definition都已经加载但是还没有 Bean 被创建。// 当前上下文使用的Bean容器 BeanFactory 的 post process// 1.当前上下文是 EmbeddedWebApplicationContext 时,// 这个步骤中会对 beanFactory 注册一个 BeanPostProcessor :// WebApplicationContextServletContextAwareProcessor// 2.当前上下文是 AnnotationConfigEmbeddedWebApplicationContext 时,// 如果设置了 basePackages,// 这里会使用 AnnotatedBeanDefinitionReader扫描basePackages;// 如果设置了 annotatedClasses,// 这里会使用 ClassPathBeanDefinitionScanner登记annotatedClasses;postProcessBeanFactory(beanFactory);// Invoke factory processors registered as beans in the context.// 在 beanFactory 上调用 BeanFactoryPostProcessors, // 当前上下文可能会有多个 BeanFactoryPostProcessor 需要应用在 beanFactory 上// ****************************************************************// 这里需要尤其注意区别 BeanFactoryPostProcessor 和 BeanPostProcessor// BeanFactoryPostProcessor : 作用在 Bean定义 上,用来定制修改 Bean定义// BeanPostProcessor :作用在 Bean实例 上,用来修改或者包装 Bean实例// ****************************************************************// 该方法实际上将实现委托出去 : // PostProcessorRegistrationDelegate.invokeBeanFactoryPostProcessors()invokeBeanFactoryPostProcessors(beanFactory);// Register bean processors that intercept bean creation.// 注册 BeanPostProcessor// 该步骤实际工作委托给工具类 PostProcessorRegistrationDelegate 的静态方法// void registerBeanPostProcessors(//   ConfigurableListableBeanFactory beanFactory, //   AbstractApplicationContext applicationContext)registerBeanPostProcessors(beanFactory);// Initialize message source for this context.initMessageSource();// Initialize event multicaster for this context.// 初始化当前上下文ApplicationContext要使用的 事件多播器 // ApplicationEventMulticaster applicationEventMulticaster。// // 如果容器中已经注册类型为ApplicationEventMulticaster并且名称为// applicationEventMulticaster 的Bean,则直接使用;否则,// 新建一个SimpleApplicationEventMulticaster实例并注册到// Bean容器,Bean名称使用 applicationEventMulticaster。initApplicationEventMulticaster();// Initialize other special beans in specific context subclasses.// AbstractApplicationContext 中 onRefresh() 方法实现为空,其目的就是// 留给实现子类一个机会做一些上下文相关的刷新工作。在一些特殊Bean初始化时,单// 例 singleton Bean 初始化之前该方法被调用。// 1. 当前上下文是 EmbeddedWebApplicationContext 时,该步骤会创建一个// 内置的 Servlet 容器, 具体参考 EmbeddedWebApplicationContext 的// 方法 void createEmbeddedServletContainer() onRefresh();// Check for listener beans and register them.// 1. 将外部指定到当前上下文的 ApplicationListener 实例关联到上下文多播器//    Q : 什么时候外部给当前上下文指定 ApplicationListener ?//    A : 举例说明,Springboot 应用 SpringApplication 的情况下,是在//        prepareContext()结尾时SpringApplicationRunListeners的//        contextLoaded() 调用中发生的,此时正在广播事件//        ApplicationPreparedEvent // 2. 将实现了 ApplicationListener 接口的所有 Bean 关联到上下文多播器// 3. 如果上下文属性earlyApplicationEvents中有要通知的事件,广播出去registerListeners();// Instantiate all remaining (non-lazy-init) singletons.// 完成 BeanFactory 的初始化工作// 1.BeanFactory冻结所有的Bean定义:不再可以修改或者做post process操作// 2.确保所有的non-lazy-init单例Bean被初始化,也包括FactoryBean// 3.如果所初始化的单例Bean实现了接口SmartInitializingSingleton,调用//   其方法 afterSingletonsInstantiated()finishBeanFactoryInitialization(beanFactory);// Last step: publish corresponding event.// 1. 初始化生命周期处理器 LifecycleProcessor, 使用已经存在的Bean或者//    一个新的DefaultLifecycleProcessor实例;// 2. 生命周期处理器 LifecycleProcessor 上传播 refresh 事件// 3. 发布事件 ContextRefreshedEvent// 4. 如果存在 LiveBeansView MBean 的话,关联到当前上下文// 当前上下文是EmbeddedWebApplicationContext的情况下,还会:// 5. 启动EmbeddedServletContainer,比如启动内置 tomcat容器// 6. 发布事件 EmbeddedServletContainerInitializedEventfinishRefresh();}catch (BeansException ex) {if (logger.isWarnEnabled()) {logger.warn("Exception encountered during context initialization - " +"cancelling refresh attempt: " + ex);}// Destroy already created singletons to avoid dangling resources.destroyBeans();// Reset 'active' flag.cancelRefresh(ex);// Propagate exception to caller.throw ex;}finally {// Reset common introspection caches in Spring's core, since we// might not ever need metadata for singleton beans anymore...resetCommonCaches();}}}

org.springframework.context.support.AbstractApplicationContext#refresh的这一行代码

protected ConfigurableListableBeanFactory obtainFreshBeanFactory() {refreshBeanFactory();ConfigurableListableBeanFactory beanFactory = getBeanFactory();if (logger.isDebugEnabled()) {logger.debug("Bean factory for " + getDisplayName() + ": " + beanFactory);}return beanFactory;
}

org.springframework.context.support.AbstractRefreshableApplicationContext#refreshBeanFactory

 protected final void refreshBeanFactory() throws BeansException {if (this.hasBeanFactory()) {this.destroyBeans();this.closeBeanFactory();}try {DefaultListableBeanFactory beanFactory = this.createBeanFactory();beanFactory.setSerializationId(this.getId());this.customizeBeanFactory(beanFactory);this.loadBeanDefinitions(beanFactory);Object var2 = this.beanFactoryMonitor;synchronized(this.beanFactoryMonitor) {this.beanFactory = beanFactory;}} catch (IOException var5) {throw new ApplicationContextException("I/O error parsing bean definition source for " + this.getDisplayName(), var5);}}

进入到这个方法org.springframework.context.support.AbstractApplicationContext#destroyBeans

protected void destroyBeans() {
this.getBeanFactory().destroySingletons();
}
org.springframework.beans.factory.support.DefaultListableBeanFactory#destroySingletons

@Overridepublic void destroySingletons() {super.destroySingletons();
//    清除记录的单例beanName的缓存this.manualSingletonNames.clear();clearByTypeCache();}

org.springframework.beans.factory.support.DefaultSingletonBeanRegistry#destroySingletons
View Code
bean可以实现DisposableBean这个接口,重写父类的bean destory的方法
注意:此处destroyBean将会被字类重写,用适配器模式销毁
org.springframework.beans.factory.support.DisposableBeanAdapter#destroy
View Code

具体结构如下:

在这里插入图片描述

参考:
https://my.oschina.net/u/3775437/blog/1810419

http://www.lbrq.cn/news/2778571.html

相关文章:

  • 中国进出口贸易官网网站建设优化哪家公司好
  • 营销网站建站公司转让如何进行app推广
  • 做教案找资料有哪些网站站长之家关键词查询
  • wordpress会员制网站自己开一个培训机构流程
  • 网站开发主管岗位职责说明书福州网站优化公司
  • 国家查企业信息查询平台移动网站优化排名
  • 做毕设的网站如何在外贸平台推广
  • 做网站的厉害还是黑网站的厉害拼多多代运营一般多少钱
  • 莞城网站推广自助建站系统代理
  • 河北建设集团有限公司 信息化网站网络营销软文范文
  • 蓝鸟E4A做网站程序网页制作官方网站
  • 佛山java web网站开发营销型网站建设专家
  • 百浪科技做网站怎么样html网页制作软件有哪些
  • 企业网站的建立联系方式东莞有哪些做推广的网站
  • 成品网站价格表b2b平台有哪些平台
  • 哈尔滨网站建设模板策划电商运营培训课程
  • 男科免费咨询短视频搜索优化
  • 网站数据统计怎么做搜索引擎营销方法
  • 免费建设个人手机网站系统优化工具
  • 做网站用什么字体比较好企业网站seo推广
  • 做网站能赚钱吗知乎网络营销推广平台有哪些
  • 成都有哪些网站建设的公司网推技巧
  • 网站建设协议需要注意的问题百度广告优化师
  • php动态网站怎么做的如何注册网站平台
  • 库尔勒网站全免费建立自己的网站
  • 手机装修设计软件app云南seo网络优化师
  • 如何选择网站建设企业网络推广软件
  • 做网站 过程长沙的seo网络公司
  • 南山区做网站公司宁波seo教程网
  • 做赚钱的网站今日国际军事新闻最新消息
  • 自建开发工具IDE(一)之拖找排版—仙盟创梦IDE
  • 关于物理世界、感知世界、认知世界与符号世界统一信息结构的跨领域探索
  • RH134 运行容器知识点
  • 源代码安装部署lamp
  • 【前端面试题】JavaScript 核心知识点解析(第一题到第十三题)
  • 关系型数据库与非关系型数据库