2021-04-14

Spring工程搭建

spring基础包:1.spring-core:Core模块主要包含Spring框架基本的核心工具类,Spring的其他组件要都要使用到这个包里的类,Core模块是其他组件的基本核心
2.spring-beans:包含访问配置文件、创建和管理bean以及进行IOC/DI操作相关的所有类
3.spring-context:Spring的上下文即IOC容器,通过上下文可以获得容器中的Bean
4.spring-expression:EL表达式语言用于在运行时查询和操纵对象 <!-https://mvnrepository.com/artifact/org.springframework/spring-core --> org.springframework spring-core 5.2.13.RELEASE <!-https://mvnrepository.com/artifact/org.springframework/spring-beans --> org.springframework spring-beans 5.2.13.RELEASE org.springframework spring-context 5.2.13.RELEASE org.springframework spring-expression 5.2.13.RELEASE

核心配置文件
1.:spring的核心配置文件中的各种配置。
spring的核心配置文件的名字 叫做 applicationContext.xml,后期也可以通过配置文件中的配置修改名称,在web.xml中进行如下配置:
contextConfigLocation classpath:spring/applicationContext*.xml

2:核心配置文件中关于dao层的配置。
(1):首先准备db.properties 配置文件,最简单的配置如下。 jdbc.driver=com.mysql.jdbc.Driverjdbc.url=jdbc:mysql://127.0.0.1:3306/demo?characterEncoding=utf-8jdbc.username=rootjdbc.password=123456
(2):然后加载在核心配置文件中加载数据库文件. <context:property-placeholder location="/>

(3):配置数据库连接池,配置类可以用BasicDatasource,也可以用阿里巴巴的配置核心类 DruidDataSource。
后期需要可以在其中添加多个属性配置。
(4):spring和hibernate,和mybatis的整合主要是整合sessionFactory. 和hibernate的一个整合。
和mybatis的一个整合.
(5):配置文件中关于事务的配置。< !-- 事务管理器 --> !-- 事务管理器 -->
配置通知 <tx:advice id=“txAdvice” transaction-manager=“transactionManager”> tx:attributes <tx:method name=“save*” propagation=“REQUIRED” /> <tx:method name=“insert*” propagation=“REQUIRED” /> <tx:method name=“add*” propagation=“REQUIRED” /> <tx:method name=“create*” propagation=“REQUIRED” /> <tx:method name=“delete*” propagation=“REQUIRED” /> <tx:method name=“update*” propagation=“REQUIRED” /> <tx:method name=“find*” propagation=“SUPPORTS” read-only=“true” /> <tx:method name=“select*” propagation=“SUPPORTS” read-only=“true” /> <tx:method name=“get*” propagation=“SUPPORTS” read-only=“true” /> </tx:attributes> </tx:advice>
关于切面的配置。 aop:config <aop:advisor advice-ref=“txAdvice” pointcut=“execution(* com.store.service..(…))” /> </aop:config>
关于配置文件中的service层的配置。 扫描包下面所有的service层。 <context:component-scan base-package=“com.xiaoao.service”/>
关于注解注入的配置
<mvc:annotation-driven />
(6):在进行配置的时候所需要引入的命名空间。

编写代码测试

package com.sjh;

import com.sjh.service.UserService;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;

public class test01 {
public static void main(String[] args) {
// 获取Spring上下⽂环境 (加载配置⽂件)
ApplicationContext ac = new ClassPathXmlApplicationContext(“spring.xml”);
// 通过getBean⽅法得到Spring容器中实例化好的Bean对象 (实例化Bean对象)
// userService代表的是配置⽂件中bean标签的id属性值
UserService userService = (UserService)ac.getBean(“userService”);
// 调⽤⽅法 (使⽤实例化对象)
userService.test();
}
}

执行过程分析

拦截器执行
org.springframework.transaction.interceptor.TransactionInterceptor用的是cglib代理,因为我没有实现接口,所以使用的是CGLIB代理,在目标方法被调用的的时候,是会调用到

org.springframework.aop.framework.CglibAopProxy.DynamicAdvisedInterceptor#intercept; 然后会调用到
org.springframework.transaction.interceptor.TransactionInterceptor#invoke
org.springframework.transaction.interceptor.TransactionAspectSupport#invokeWithinTransaction
1
2
3
1
2
3
这个方法我删减了一部分,区分了声明式事务和编程式事务,这里我们只关注声明式事务

@Nullable
protected Object invokeWithinTransaction(Method method, @Nullable Class<?> targetClass,
final InvocationCallback invocation) throws Throwable {

// If the transaction attribute is null, the method is non-transactional.
TransactionAttributeSource tas = getTransactionAttributeSource();
//获取事务属性
final TransactionAttribute txAttr = (tas != null ? tas.getTransactionAttribute(method, targetClass) : null);
//获取事务管理器
final PlatformTransactionManager tm = determineTransactionManager(txAttr);
final String joinpointIdentification = methodIdentification(method, targetClass, txAttr);

//下面是声明式事务的处理逻辑
if (txAttr == null || !(tm instanceof CallbackPreferringPlatformTransactionManager)) {
	// Standard transaction demarcation with getTransaction and commit/rollback calls.
	//看是否有必要创建一个事务,根据事务的传播行为做判断
	TransactionInfo txInfo = createTransactionIfNecessary(tm, txAttr, joinpointIdentification);
	Object retVal = null;
	try {
		// This is an around advice: Invoke the next interceptor in the chain.
		// This will normally result in a target object being invoked.
		//执行目标方法
		retVal = invocation.proceedWithInvocation();
	}
	catch (Throwable ex) {
		// target invocation exception
		//如果有异常就回滚事务,回滚时,根据配置的rollbackFor进行判断
		completeTransactionAfterThrowing(txInfo, ex);
		throw ex;
	}
	finally {
		//清除事务信息
		cleanupTransactionInfo(txInfo);
	}
	//提交事务
	commitTransactionAfterReturning(txInfo);
	return retVal;
}

}

spring IOC&ID

引入IOC之前

User模块实体类:User.javaDao层实现类:UserDaoImpl.javaUser模块视图类:UserVo.javaUser模块Service层实现类:UserServiceImpl.javaUser模块Controller层:UserController.javaUserService.java:User模块测试类:UserTest.java引入IOC(XML) <bean id=“userController” class="controlleXML改注解由XML向注解方式改造工程时,主要的改造点有三处mybatis-config.xmlmapper.xmlmapper Java映射类mybatis-config.xml改造点 mapper.xml改造点这里比较方便了,因为要改造为注解方式,mapper.xml文件直接不需要了 mapper Java映射类改造点XML方式时,mapper接口主要用于进行接口映射,可以通过SQLSession来获取mapper接口,通过mapper接口调用方法public interface CountryMapper { List selectAll(); Country selectCountryById(Long id); /** * 添加国家/地区 * @param country * @return 影响的数据条数 / int addCountry(Country country); /* * 通过主键删除国家/地区 * @param id * @return 影响数据条数 / int deleteCountryById(Long id); /* * 修改国家信息 * @param country * @return / int updateCountry(Country country);}改造后public interface CountryMapper { @Select({“select * from country”}) List selectAll(); @Select({"select id, countryname, countrycode " + "from country " + “where id = #{id}”}) Country selectCountryById(Long id); /* * 添加国家/地区 * @param country * @return 影响的数据条数 / @Insert({“insert into country(id, countryname, countrycode) values(#{id}, #{countryname}, #{countrycode})”}) int addCountry(Country country); /* * 通过主键删除国家/地区 * @param id * @return 影响数据条数 / @Delete({“delete from country where id = #{id}”}) int deleteCountryById(Long id); /* * 修改国家信息 * @param country * @return / @Update({“update country set countryname = #{countryname}, countrycode = #{countrycode} where id = #{id}”}) int updateCountry(Country country);}引入ID依赖注入(DI)背后的基本原理是对象之间的依赖关系(即一起工作的其它对象)只会通过以下几种方式来实现:构造器的参数、工厂方法的参数,或给由构造函数或者工厂方法创建的对象设置属性。因此,容器的工作就是创建bean时注入那些依赖关系。相对于由bean自己来控制其实例化、直接在构造器中指定依赖关系或者类似服务定位器(Service Locator)模式这3种自主控制依赖关系注入的方法来说,控制从根本上发生了倒转,这也正是控制反转(Inversion of Control, IoC) 名字的由来。 应用DI原则后,代码将更加清晰。而且当bean自己不再担心对象之间的依赖关系(甚至不知道依赖的定义指定地方和依赖的实际类)之后,实现更高层次的松耦合将易如反掌。DI主要有两种注入方式,即Setter注入和构造器注入。 Setter注入: public class ExampleBean { private AnotherBean beanOne; private YetAnotherBean beanTwo; private int i; public void setBeanOne(AnotherBean beanOne) { this.beanOne = beanOne; } public void setBeanTwo(YetAnotherBean beanTwo) { this.beanTwo = beanTwo; } public void setI(int i) { this.i = i; }} bean类中的setter方法与xml文件中配置的属性是一一对应的. 构造器注入: public class ExampleBean { private AnotherBean beanOne; private YetAnotherBean beanTwo; private int i; public ExampleBean( AnotherBean anotherBean, YetAnotherBean yetAnotherBean, int i) { this.beanOne = anotherBean; this.beanTwo = yetAnotherBean; this.i = i; } } 在xml bean定义中指定的构造器参数将被用来作为传递给类ExampleBean构造器的参数。 采用static工厂方法返回对象实例,来替代构造器的方法: public class ExampleBean { // a private constructor private ExampleBean(…) { … } / a static factory method; the arguments to this method can be considered the dependencies of the bean that is returned, regardless of how those arguments are actually used. */ public static ExampleBean createInstance ( AnotherBean anotherBean, YetAnotherBean yetAnotherBean, int i) { ExampleBean eb = new ExampleBean (…); // some other operations… return eb; } }

引入IOC之前

User模块实体类:User.java
Dao层实现类:UserDaoImpl.java
User模块视图类:UserVo.java
User模块Service层实现类:UserServiceImpl.java
User模块Controller层:UserController.javaUserService.java:
User模块测试类:UserTest.java

引入IOC(XML)

<bean id=“userController” class="controlle

标题XML改注解

由XML向注解方式改造工程时,主要的改造点有三处mybatis-config.xmlmapper.xmlmapper Java映射类mybatis-config.xml改造点 mapper.xml改造点这里比较方便了,因为要改造为注解方式,mapper.xml文件直接不需要了 mapper Java映射类改造点XML方式时,mapper接口主要用于进行接口映射,可以通过SQLSession来获取mapper接口,通过mapper接口调用方法public interface CountryMapper { List selectAll(); Country selectCountryById(Long id); /** * 添加国家/地区 * @param country * @return 影响的数据条数 / int addCountry(Country country); /* * 通过主键删除国家/地区 * @param id * @return 影响数据条数 / int deleteCountryById(Long id); /* * 修改国家信息 * @param country * @return / int updateCountry(Country country);}改造后public interface CountryMapper { @Select({“select * from country”}) List selectAll(); @Select({"select id, countryname, countrycode " + "from country " + “where id = #{id}”}) Country selectCountryById(Long id); /* * 添加国家/地区 * @param country * @return 影响的数据条数 / @Insert({“insert into country(id, countryname, countrycode) values(#{id}, #{countryname}, #{countrycode})”}) int addCountry(Country country); /* * 通过主键删除国家/地区 * @param id * @return 影响数据条数 / @Delete({“delete from country where id = #{id}”}) int deleteCountryById(Long id); /* * 修改国家信息 * @param country * @return */ @Update({“update country set countryname = #{countryname}, countrycode = #{countrycode} where id = #{id}”}) int updateCountry(Country country);}

标题引入ID

依赖注入(DI)背后的基本原理是对象之间的依赖关系(即一起工作的其它对象)只会通过以下几种方式来实现:构造器的参数、工厂方法的参数,或给由构造函数或者工厂方法创建的对象设置属性。因此,容器的工作就是创建bean时注入那些依赖关系。相对于由bean自己来控制其实例化、直接在构造器中指定依赖关系或者类似服务定位器(Service Locator)模式这3种自主控制依赖关系注入的方法来说,控制从根本上发生了倒转,这也正是控制反转(Inversion of Control, IoC) 名字的由来。 应用DI原则后,代码将更加清晰。而且当bean自己不再担心对象之间的依赖关系(甚至不知道依赖的定义指定地方和依赖的实际类)之后,实现更高层次的松耦合将易如反掌。DI主要有两种注入方式,即Setter注入和构造器注入。 Setter注入: public class ExampleBean { private AnotherBean beanOne; private YetAnotherBean beanTwo; private int i; public void setBeanOne(AnotherBean beanOne) { this.beanOne = beanOne; } public void setBeanTwo(YetAnotherBean beanTwo) { this.beanTwo = beanTwo; } public void setI(int i) { this.i = i; }} bean类中的setter方法与xml文件中配置的属性是一一对应的. 构造器注入: public class ExampleBean { private AnotherBean beanOne; private YetAnotherBean beanTwo; private int i; public ExampleBean( AnotherBean anotherBean, YetAnotherBean yetAnotherBean, int i) { this.beanOne = anotherBean; this.beanTwo = yetAnotherBean; this.i = i; } } 在xml bean定义中指定的构造器参数将被用来作为传递给类ExampleBean构造器的参数。 采用static工厂方法返回对象实例,来替代构造器的方法: public class ExampleBean { // a private constructor private ExampleBean(…) { … } /* a static factory method; the arguments to this method can be considered the dependencies of the bean that is returned, regardless of how those arguments are actually used. */ public static ExampleBean createInstance ( AnotherBean anotherBean, YetAnotherBean yetAnotherBean, int i) { ExampleBean eb = new ExampleBean (…); // some other operations… return eb; } }

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值