【从零构建Spring|第三节】  JDK和Cglib动态代理实例化策略
日志
在上一节中,出现了一个小问题:没法实例化有参构造对象
本章节有以下变动:
- 使用Cglib字节码方式、JDK内部方式进行有参对象的实例化
 
- 后续章节可采用策略模式优化策略的选择
 

这里不小心把下一节的 UML 画了。。。
因为比较简单,就只展示 Cglib 字节码和 JDK 两种实例化对象的代码了
Cglib方式:
@SuppressWarnings({"rawtypes"}) public class CglibSubclassingInstantiationStrategy implements InstantiationStrategy {
      @Override     public Object instantiate(BeanDefinition beanDefinition, String beanName, Constructor ctor, Object[] args) throws BeansException {         Enhancer enhancer = new Enhancer();         enhancer.setSuperclass(beanDefinition.getBeanClass());         enhancer.setCallback(new NoOp() {             @Override             public int hashCode() {                 return super.hashCode();             }         });         if (null == ctor) {             return enhancer.create();         }         assert ctor != null;         return enhancer.create(ctor.getParameterTypes(), args);     }
  }
  | 
 
JDK方式:
@SuppressWarnings({"rawtypes"}) public class SimpleInstantiationStrategy implements InstantiationStrategy {
      @Override     public Object instantiate(BeanDefinition beanDefinition, String beanName, Constructor ctor, Object[] args) throws BeansException {         Class clazz = beanDefinition.getBeanClass();
          try {             if (args != null) {                                  return clazz.getDeclaredConstructor(ctor.getParameterTypes()).newInstance(args);             } else {                                  return clazz.getDeclaredConstructor().newInstance();             }         } catch (InstantiationException | IllegalAccessException | InvocationTargetException | NoSuchMethodException e) {             throw new BeansException("Failed to instantiate [" + clazz.getName() + "]"                     + " -- [" + clazz.getName() + "] 实例化失败", e);         }     }
  }
  | 
 
- 核心方法:getDeclaredConstructor(…)
 
具体的调用在 AbstractAutowrieCapableBeanFactory
测试
@Test public void test_BeanFactory() {          DefaultListableBeanFactory beanFactory = new DefaultListableBeanF         actory();
           BeanDefinition beanDefinition = new BeanDefinition(UserService.class);     beanFactory.registerBeanDefinition("userService", beanDefinition);
           UserService userService = (UserService) beanFactory.getBean("userService");     userService.queryUserInfo();
           UserService userService_args = (UserService) beanFactory.getBean("userService", "半糖");     userService_args.queryUserInfo(); }
   | 
 
_dnsauth
202405010000001c5kq42954wu3x1udfifby92t5uw4pfdnl57d3lkwi0zz6p5ur