FactoryBean作为Spring框架的重要接口,为开发者提供了自定义对象工厂的能力,本文将详细介绍其核心功能与典型应用场景。
作为Spring提供的特殊接口,FactoryBean允许开发者创建自定义对象工厂。当将其注入容器时,Spring会同时管理工厂实例及其创建的Bean对象。与普通工厂模式相比,主要区别在于管理方式不同:前者由Spring容器负责,后者需要开发者自行管理。
FactoryBean定义了三个核心方法:
public interface FactoryBean {
String OBJECT_TYPE_ATTRIBUTE = "factoryBeanObjectType";
@Nullable
T getObject() throws Exception;
@Nullable
Class<?> getObjectType();
default boolean isSingleton() {
return true;
}
}
FactoryBean通常需要与Spring其他接口配合使用,下面通过具体示例说明其实现过程。
首先定义目标Bean和对应的Builder类:
@Data
public class Customize {
private String id;
private String name;
private int age;
private String address;
private String phone;
}
public class CustomizeBuilder {
private Customize customize;
public CustomizeBuilder builder() {
customize = new Customize();
return this;
}
public CustomizeBuilder id(String id) {
customize.setId(id);
return this;
}
// 其他builder方法...
public Customize build() {
return customize;
}
}
实现InitializingBean接口,在属性加载完成后初始化目标对象:
@Component
public class CustomizeFactoryBean implements FactoryBean, InitializingBean {
private Customize customize;
@Override
public Customize getObject() throws Exception {
return customize;
}
@Override
public Class<?> getObjectType() {
return Customize.class;
}
@Override
public void afterPropertiesSet() throws Exception {
if (customize == null){
customize = new CustomizeBuilder().builder()
.id("1").name("sun").age(18)
.address("beijing").phone("123456789")
.build();
}
}
}
测试验证注入效果:
@SpringBootTest
class SpringBeanApplicationTests {
@Autowired
private Customize customize;
@Autowired
private CustomizeFactoryBean customizeFactoryBean;
@Test
public void contextLoads() throws Exception {
System.out.println(customizeFactoryBean);
System.out.println(customizeFactoryBean.getObject());
System.out.println(customize);
}
}
调试发现,Spring默认注入的是FactoryBean创建的对象,通过"&"+factoryBeanName可获取工厂实例本身。


虽然可以通过@Component注入FactoryBean,但官方更推荐通过配置方式注册。下面分析mybatis-spring如何通过FactoryBean实现整合。
MyBatis核心是SqlSession,由SqlSessionFactory创建。关键代码如下:
public SqlSessionFactory build(Reader reader, String environment, Properties properties) {
XMLConfigBuilder parser = new XMLConfigBuilder(reader, environment, properties);
return build(parser.parse());
}
mybatis-spring通过SqlSessionFactoryBean实现集成:
public class SqlSessionFactoryBean implements FactoryBean, InitializingBean {
private SqlSessionFactory sqlSessionFactory;
@Override
public void afterPropertiesSet() throws Exception {
this.sqlSessionFactory = buildSqlSessionFactory();
}
@Override
public SqlSessionFactory getObject() throws Exception {
return this.sqlSessionFactory;
}
}
通过XML或Java配置将SqlSessionFactoryBean加入容器,即可实现MyBatis与Spring的无缝整合。
FactoryBean作为Spring的扩展接口,主要用于在容器初始化阶段创建复杂对象,是实现第三方框架集成的优雅方案,具有重要的扩展价值。