Spring core post processor-BeanDefinitionRegistryPostProcessor

In the previous article, several ways to combine object->bean have been introduced

Then our post processor can also be implemented, we look at the code

public class User {

	public User(){
		System.out.println("init-user");
	};
}

@Component
public class TestBeanDefinitionRegistryPostProcessor implements BeanDefinitionRegistryPostProcessor {
	@Override
	public void postProcessBeanDefinitionRegistry(BeanDefinitionRegistry registry) throws BeansException {
		RootBeanDefinition userBean = new RootBeanDefinition(User.class);
		//新增Bean定义
		registry.registerBeanDefinition("userBo", userBean);
	}

	@Override
	public void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) throws BeansException {
		BeanDefinition beanDefinition = beanFactory.getBeanDefinition("userBo");
		beanDefinition.setScope("prototype");
		System.out.println("Scope:"+beanDefinition.getScope());
	}
}

This method of rewriting is familiar to the postProcessBeanFactory and the previous blog has already proved it. Mainly look at the first one

In postProcessBeanDefinitionRegistry (BeanDefinitionRegistry registry), a bd registrar is passed in.

RootBeanDefinition is a word class of BeanDefinition, and all beans in spring use this object to root the object into a bean

So now that there is a bd registrar. Can we root a proxy class?

Let's continue testing with another post above that turned the interface into a bean

Let's change the blog of the previous article and change this interface ImportBeanDefinitionRegistrar to our interface BeanDefinitionRegistryPostProcessor 

Please see the code

public class TestBeanDefinitionRegistryPostProcessor implements BeanDefinitionRegistryPostProcessor {
	@Override
	public void postProcessBeanDefinitionRegistry(BeanDefinitionRegistry registry) throws BeansException {
		//扫描TestMapper这个接口
		BeanDefinitionBuilder builder = BeanDefinitionBuilder.genericBeanDefinition(TestMapper.class);
		GenericBeanDefinition beanDefinition =(GenericBeanDefinition) builder.getBeanDefinition();
		beanDefinition.setBeanClass(TestFactoryBean.class);
		beanDefinition.getConstructorArgumentValues().addGenericArgumentValue("org.springframework.spring.mybatis.mapper.TestMapper");
beanDefinition.setScope("singleton");//定义作用域
		registry.registerBeanDefinition("testMapper",beanDefinition);
	}

	@Override
	public void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) throws BeansException {
		BeanDefinition beanDefinition = beanFactory.getBeanDefinition("testMapper");
		System.out.println("setScope before:"+beanDefinition.getScope());//很尴尬这儿也是空的,因为是代理对象的原因吗?/需要先定义作用域,已解决
		beanDefinition.setScope("prototype");
		System.out.println("setScope after:"+beanDefinition.getScope());
	}
}

Custom annotation replacement configuration, replaced with our current interface

@Retention(RetentionPolicy.RUNTIME)
//@Import(TestImportBeanDifinitionRegistrar.class)
@Import(TestBeanDefinitionRegistryPostProcessor.class)
public @interface TestScanMapper {
}

Add the open annotation to the configuration class @TestScanMapper

test

public class MainDemo {
		public static void main(String[] args) {
			AnnotationConfigApplicationContext ac = new AnnotationConfigApplicationContext(AppConfig.class);
			TestMapper bean =(TestMapper) ac.getBean("testMapper");
			System.out.println("TestMapper hashcode():"+bean.hashCode());//很尴尬是空的
		}

}

The program is very friendly, no errors are reported when running............

Then our interface can not only change the original annotation properties of the bean in the beanFactory, but also hand over the object to spring management, and also hand over the proxy object to spring management

Guess you like

Origin blog.csdn.net/qq_38108719/article/details/100593855