Spring学习日记——DAY04(复杂对象创建,AOP静态代理)

1 复杂对象的创建

在 Spring 中,除了管理自己编写的 JavaBean,对于数据库连接、SqlSessionFactory 这类复杂对象,无法直接通过 new 或简单反射创建,需要用工厂方式管理,Spring 提供 FactoryBean、实例工厂、静态工厂 三种方案。

1.1 FactoryBean 接口

FactoryBean 是 Spring 提供的工厂接口,专门用于创建复杂对象,实现该接口需重写 3 个方法:

  • T getObject():创建并返回最终的复杂对象
  • Class<?> getObjectType():返回复杂对象的 Class 类型
  • boolean isSingleton():默认返回 true,标识对象是单例
使用规则
  • 直接根据 id 获取:拿到的是 getObject() 返回的对象

  • id 前加 & 获取:拿到的是 FactoryBean 实现类本身

    // 获取复杂对象
    Connection conn = (Connection) context.getBean("connection");
    // 获取工厂本身
    MyConnectionFactoryBean factory = (MyConnectionFactoryBean) context.getBean("&connection");

1.2 自定义 FactoryBean 原理

底层通过反射调用 FactoryBean 实现类的 getObject () 完成对象创建:

  1. 解析 XML 获取 FactoryBean 实现类全类名
  2. 反射创建工厂实例
  3. 调用 getObject() 得到复杂对象
  4. 根据 isSingleton() 决定是否缓存

1.3 普通工厂方式创建

1.3.1 实例工厂

先创建工厂实例,再调用工厂的非静态方法创建对象:

复制代码
<!-- 配置工厂实例 -->
<bean id="instanceFactory" class="com.xzit.factory.InstanceFactory"/>
<!-- 工厂创建对象 -->
<bean id="conn" factory-bean="instanceFactory" factory-method="getConnection"/>
1.3.2 静态工厂

直接调用工厂类的静态方法创建对象,无需创建工厂实例:

复制代码
<bean id="staticConn" class="com.xzit.factory.StaticFactory" factory-method="getConnection"/>

2 类型转换器

Spring 内置基础类型转换器,但日期、自定义类型等复杂转换需要手动配置。

2.1 自定义转换器步骤

  1. 实现 Converter<S, T> 接口,重写 convert 方法

    • S:源类型
    • T:目标类型

    public class DateConverter implements Converter<String, LocalDate> {
    private String pattern;
    @Override
    public LocalDate convert(String source) {
    DateTimeFormatter df = DateTimeFormatter.ofPattern(pattern);
    return LocalDate.parse(source, df);
    }
    // setter 注入格式
    public void setPattern(String pattern) {
    this.pattern = pattern;
    }
    }

  2. 注册转换器(id 固定为 conversionService







  3. 使用:配置后 Spring 可自动将字符串转为指定日期类型


3 AOP 面向切面编程

3.1 AOP 简介

AOP(Aspect Oriented Programming):面向切面编程 ,核心是横向抽取重复代码,在不修改原业务代码的前提下,统一添加功能(权限、日志、事务、性能监控),实现解耦。

3.2 代理模式

AOP 底层基于动态代理实现,分为静态代理、JDK 动态代理、CGLIB 动态代理。

3.2.1 静态代理
  • 定义:代理类与目标类实现相同接口,代理类持有目标对象,在调用目标方法前后增强
  • 优点:简单直观
  • 缺点:耦合高、一个接口需一个代理类,不符合开闭原则
java 复制代码
// 共同接口
public interface Service { void save(); }
// 目标类
public class UserService implements Service {
    public void save() { System.out.println("保存用户"); }
}
// 代理类
public class ServiceProxy implements Service {
    private UserService target;
    public ServiceProxy(UserService target) { this.target = target; }
    public void save() {
        System.out.println("开启事务");
        target.save();
        System.out.println("提交事务");
    }
}
相关推荐
「QT(C++)开发工程师」1 小时前
C++ 11 常用for循环
开发语言·c++
我还记得那天1 小时前
0 初识C++
开发语言·c++
FfHUCisI2 小时前
Go 编译过程全景
开发语言·后端·golang
FfHUCisI2 小时前
Golang 语法分析与 AST:Parser 与 go/ast
开发语言·后端·golang
秋饼2 小时前
JDK 27 企业级 AI 服务落地实战:G1 默认、紧凑对象头、后量子 TLS 与 JFR 脱敏全解析
java·ai·技术分享·后端开发
卓怡学长3 小时前
w176基于SpringBoot的医院管理系统
java·spring boot·spring·maven·intellij-idea
lemon_sjdk3 小时前
ObjectProperty
java·开发语言·算法
大模型码小白3 小时前
Spring AI Tool 实现自然语言操作 MySQL 数据库详解
服务器·开发语言·数据库·人工智能·python·mysql·spring
hh9503 小时前
Agent Plan x DeepSeek Harness:Agent 供应链安全与第三方插件审计
java·开发语言·安全·agent plan·adg成都社区·adg社区