当前位置:  首页>> 技术小册>> Spring AOP 编程思想(下)

工厂方法模式(Factory Method)实现

在《Spring AOP 编程思想(下)》一书中,深入探讨Spring框架的高级特性及其背后的设计模式是不可或缺的章节。本章将聚焦于“工厂方法模式”(Factory Method Pattern)的实现与应用,该模式作为创建型设计模式的一种,旨在定义一个用于创建对象的接口,但让子类决定要实例化的类是哪一个。这种模式在Spring框架中得到了广泛的应用,特别是在Bean的创建和管理上,展现了其灵活性和解耦的优势。

一、工厂方法模式概述

1.1 定义与原理

工厂方法模式是一种创建型设计模式,其核心在于定义一个创建对象的接口,但让子类决定实例化哪一个类。工厂方法让类的实例化推迟到子类中进行。这样,一个类的实例化就不会在编译时就确定下来,而是由运行时决定,从而实现了类的解耦和灵活配置。

1.2 结构分析

  • Product(产品类):定义了产品的接口,是工厂方法模式所创建的对象的超类型,也就是产品对象的共同接口。
  • ConcreteProduct(具体产品类):实现了Product接口的具体类,被创建的对象,是此模式的核心。
  • Creator(创建者类):声明了工厂方法,该方法返回一个Product类型的对象。Creator也可以定义一个工厂方法的默认实现,用于创建Product类型对象的默认版本。
  • ConcreteCreator(具体创建者类):实现Creator接口,并具体实现工厂方法,返回一个ConcreteProduct实例。

1.3 优点与缺点

  • 优点

    • 用户只需要知道具体创建者的类名,就可以创建出所需的产品对象,而无须知道这些产品类是如何被创建、如何组织的。
    • 有利于产品族的扩展。增加一个新的产品类,只需要增加一个具体的产品类和对应的具体创建者类,原有系统无须做任何修改,符合开闭原则。
    • 提高了系统的灵活性和可扩展性。
  • 缺点

    • 在类的层次结构中增加了复杂性,因为需要增加抽象层和接口层。
    • 增加了系统的抽象性和理解难度。

二、Spring中的工厂方法模式

在Spring框架中,工厂方法模式的应用主要体现在Bean的创建和管理上,尤其是通过FactoryBean接口和@Bean注解来实现。

2.1 FactoryBean接口

FactoryBean是Spring提供的一个高级接口,允许用户自定义Bean的创建逻辑。当一个Bean实现了FactoryBean接口时,Spring容器不会直接返回该Bean的实例,而是返回该Bean的getObject()方法的返回值作为实际的Bean。

  1. public interface FactoryBean<T> {
  2. T getObject() throws Exception;
  3. Class<?> getObjectType();
  4. boolean isSingleton();
  5. }
  • getObject(): 返回由FactoryBean创建的Bean实例。
  • getObjectType(): 返回FactoryBean创建的Bean的类型。
  • isSingleton(): 返回FactoryBean创建的Bean是否为单例。

使用FactoryBean可以灵活地控制Bean的创建过程,实现复杂的依赖关系和初始化逻辑。

2.2 @Bean注解

在Spring的Java配置中,@Bean注解提供了一种声明Bean的方法,允许在配置类中直接定义Bean的创建逻辑。这实际上也是工厂方法模式的一种应用,因为配置类扮演了创建者的角色,而@Bean注解标记的方法则相当于工厂方法。

  1. @Configuration
  2. public class AppConfig {
  3. @Bean
  4. public MyBean myBean() {
  5. return new MyBean();
  6. }
  7. }

在上面的例子中,AppConfig类是一个配置类,它使用@Configuration注解标记。myBean()方法通过@Bean注解被声明为一个Bean的工厂方法,Spring容器在启动时会自动调用这个方法并注册返回的MyBean实例作为Bean。

三、工厂方法模式在Spring AOP中的应用

虽然工厂方法模式本身并不直接关联于AOP(面向切面编程),但Spring AOP的实现机制,特别是关于Advice(通知)、Pointcut(切入点)和Advisor(顾问)的创建和管理,都隐含了工厂方法模式的思想。

在Spring AOP中,AspectJAutoProxyCreator是一个关键的Bean后处理器(BeanPostProcessor),它负责为符合条件的Bean创建代理对象。这个过程可以看作是工厂方法模式的一个应用实例:

  • Product(产品类):在这里,可以看作是目标对象(即需要被增强的Bean)。
  • ConcreteProduct(具体产品类):目标对象的具体实现。
  • Creator(创建者类)AspectJAutoProxyCreator作为创建者,定义了如何为目标对象创建代理对象的接口(即BeanPostProcessor接口)。
  • ConcreteCreator(具体创建者类):虽然AspectJAutoProxyCreator本身已经足够具体,但我们可以将其看作是一个具体的创建者类,它根据目标对象的配置和切面的定义,动态地创建代理对象。

在这个过程中,AspectJAutoProxyCreator通过检查目标对象的配置和切面的定义,决定是否需要为目标对象创建代理,以及如何创建代理(例如,JDK动态代理或CGLIB代理)。这种动态决策和创建过程正是工厂方法模式所倡导的。

四、实践案例:自定义FactoryBean

为了更深入地理解工厂方法模式在Spring中的应用,我们可以实现一个简单的FactoryBean来创建特定的Bean实例。

  1. public class MyFactoryBean implements FactoryBean<MyProduct> {
  2. @Override
  3. public MyProduct getObject() throws Exception {
  4. // 复杂的创建逻辑,如读取配置文件、进行依赖注入等
  5. return new MyProductImpl();
  6. }
  7. @Override
  8. public Class<?> getObjectType() {
  9. return MyProduct.class;
  10. }
  11. @Override
  12. public boolean isSingleton() {
  13. // 根据实际情况返回是否为单例
  14. return true;
  15. }
  16. }
  17. // 配置文件或Java配置类中使用
  18. @Bean
  19. public FactoryBean<MyProduct> myProductFactoryBean() {
  20. return new MyFactoryBean();
  21. }
  22. // 或者直接使用@Bean注解自动推断类型(需要Spring 4.3及以上版本)
  23. @Bean
  24. public MyProduct myProduct() {
  25. return new MyFactoryBean().getObject(); // 注意:这里通常不推荐直接调用getObject(),仅作为示例
  26. }
  27. // 更推荐的方式是让Spring管理FactoryBean,并通过FactoryBean的ID来获取Bean

在上面的例子中,我们定义了一个MyFactoryBean类来实现FactoryBean接口,用于创建MyProduct类型的Bean。然后,在配置类中,我们可以选择将MyFactoryBean本身注册为Bean,或者通过@Bean注解直接返回MyProduct实例(但这种方式通常不是FactoryBean的典型用法)。

五、总结

工厂方法模式在Spring框架中得到了广泛的应用,特别是在Bean的创建和管理上。通过FactoryBean接口和@Bean注解,Spring提供了灵活且强大的Bean创建机制,使得开发者可以轻松地控制Bean的创建过程,实现复杂的依赖关系和初始化逻辑。同时,Spring AOP的实现机制也隐含了工厂方法模式的思想,通过动态代理技术为目标对象创建代理对象,实现面向切面的编程。理解并掌握工厂方法模式在Spring中的应用,对于深入理解Spring框架的底层原理和提高Spring应用的开发效率具有重要意义。


该分类下的相关小册推荐: