Spring-Study
代碼:https://github.com/Donkequan/Spring-Studyphp
1. 簡介
spring理念:是現有的技術更加容易使用,自己是一個大雜燴。html
- SSH:Struct2 + Spring + Hibernate
- SSM: SpringMVC + Spring + Mybatis
官網: https://spring.io/projects/spring-framework#overviewjava
官方下載: https://repo.spring.io/release/org/springframework/spring/mysql
GitHub: https://github.com/spring-projects/spring-frameworkgit
Spring Web MVC » 5.2.5.RELEASE程序員
<!-- https://mvnrepository.com/artifact/org.springframework/spring-webmvc --> <dependency> <groupId>org.springframework</groupId> <artifactId>spring-webmvc</artifactId> <version>5.2.5.RELEASE</version> </dependency> <dependency> <groupId>org.springframework</groupId> <artifactId>spring-jdbc</artifactId> <version>5.2.3.RELEASE</version> </dependency>
- spring是開源的免費的容器。
- spring是一個輕量級的,非入侵式的。
- 控制反轉(IOC),面向切面編程 (AOP)。
- 支持事務處理,對框架整合的支持。
總結:spring是一個輕量級的控制反轉(IOC)和麪向切面編程(AOP)的框架。github
2.IOC理論
-
UserDaoweb
-
UserDaoImpspring
-
UserSevicesql
-
UserServiceImp
在以前,用戶的需求可能會影響原來的代碼。
使用一個set。
public void setUserDao(UserDao userDao){ this.userDao = userDao; }
-
以前是主動建立對象,控制權在程序員手上。
-
使用set以後,是被動接受對象。
3. Hello Spring
pojo中
package com.hou.pojo; public class Hello { private String name; public String getName() { return name; } public void setName(String name) { this.name = name; } @Override public String toString() { return "Hello{" + "name='" + name + '\'' + '}'; } }
resource種
<?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd"> <!--bean = 對象--> <!--id = 變量名--> <!--class = new的對象--> <!--property 至關於給對象中的屬性設值--> <bean id="hello" class="com.hou.pojo.Hello"> <property name="name" value="Spring"/> </bean> </beans>
test
import com.hou.pojo.Hello; import org.springframework.context.ApplicationContext; import org.springframework.context.support.ClassPathXmlApplicationContext; public class Mytest { public static void main(String[] args) { //獲取spring上下文對象 ApplicationContext context = new ClassPathXmlApplicationContext("beans.xml"); //咱們的對象下能在都在spring·中管理了,咱們要使用,直接取出來就能夠了 Hello hello = (Hello) context.getBean("hello"); System.out.println(hello.toString()); } }
bean = 對象
id = 變量名
class = new的對象
property 至關於給對象中的屬性設值
核心用set注入
第一個文件中
<?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd"> <bean id="userdaomysql" class="com.hou.dao.UserDaoMysqlImpl"></bean> <bean id="userServiceImpl" class="com.hou.service.UserServiceImp"> <!--ref引用spring中已經建立很好的對象--> <!--value是一個具體的值--> <property name="userDao" ref="userdaomysql"/> </bean> </beans>
4. IOC建立對象的方式
- 使用無參構造建立對象,默認。
- 使用有參構造
下標賦值
<?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd"> <bean id="user" class="com.hou.pojo.User"> <constructor-arg index="0" value="hou"/> </bean> </beans>
類型賦值(不建議使用)
<bean id="user" class="com.hou.pojo.User"> <constructor-arg type="java.lang.String" value="dong"/> </bean>
直接經過參數名
<bean id="user" class="com.hou.pojo.User"> <constructor-arg name="name" value="hou"></constructor-arg> </bean>
Spring相似於婚介網站!
你想不想要,對象都在裏面。註冊bean以後用不用被實例化。
5. Spring配置
別名
<bean id="user" class="com.hou.pojo.User"> <constructor-arg name="name" value="hou"></constructor-arg> </bean> <alias name="user" alias="user2aaa"/>
Bean的配置
- id:bean的id標識符
- class:bean對象所對應的類型
- name:別名,更高級,能夠同時取多個別名。
import
通常用於團隊開發,它能夠將多個配置文件,導入合併爲一個
<import resource="beans.xml"/>
6. DI依賴注入
構造器注入
set方式注入(重點)
- 依賴:bean對象的建立依賴於容器
- 注入:bean對象中的全部屬性,由容器來注入
【環境搭建】
- 複雜類型
- 真實測試對象
package com.pojo; import java.util.*; public class Student { private String name; private Address address; private String[] books; private List<String> hobbies; private Map<String, String> card; private Set<String> game; private Properties infor; private String wife; @Override public String toString() { return "Student{" + "name='" + name + '\'' + ", address=" + address + ", books=" + Arrays.toString(books) + ", hobbies=" + hobbies + ", card=" + card + ", game=" + game + ", infor=" + infor + ", wife='" + wife + '\'' + '}'; } }
public class Address { private String address; public String getAddress() { return address; } public void setAddress(String address) { this.address = address; } @Override public String toString() { return "Address{" + "address='" + address + '\'' + '}'; } }
<?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd"> <bean id="address" class="com.pojo.Address"> <property name="address" value="xian"></property> </bean> <bean id="student" class="com.pojo.Student"> <property name="name" value="hou"/> <property name="address" ref="address"/> <!--數組注入--> <property name="books"> <array> <value>三國</value> <value>西遊</value> <value>水滸</value> </array> </property> <!--list--> <property name="hobbies"> <list> <value>eat</value> <value>drink</value> <value>play</value> </list> </property> <property name="card"> <map> <entry key="1" value="12"/> <entry key="2" value="23"/> </map> </property> <property name="game"> <set> <value>wangzhe</value> <value>daota</value> <value>lol</value> </set> </property> <property name="wife"> <null></null> </property> <!--properties--> <property name="infor"> <props> <prop key="id">20200405</prop> <prop key="name">hdk</prop> </props> </property> </bean> </beans>
第三方
p標籤和c標籤
package com.pojo; public class User { private String name; private int age; public User() { } public User(String name, int age) { this.name = name; this.age = age; } @Override public String toString() { return "User{" + "name='" + name + '\'' + ", age=" + age + '}'; } public String getName() { return name; } public void setName(String name) { this.name = name; } public int getAge() { return age; } public void setAge(int age) { this.age = age; } }
<?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:p="http://www.springframework.org/schema/p" xmlns:c="http://www.springframework.org/schema/c" xsi:schemaLocation="http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd"> <!--p命名空間注入/set注入--> <bean id="use" class="com.pojo.User" p:name="dong" p:age="10"> </bean> <!--c命名空間/構造器--> <bean id="use2" class="com.pojo.User" c:name="kun" c:age="19"></bean> </beans>
bean的做用域
- 單例模式(默認)
<bean id="use2" class="com.pojo.User" c:name="kun" c:age="19" scope="singleton"></bean>
- 原型模式: 每次從容器中get的時候,都產生一個新對象!
<bean id="use2" class="com.pojo.User" c:name="kun" c:age="19" scope="prototype"></bean>
- 其他的request、session、application這些只能在web開放中使用!
7. Bean的自動裝配
- 自動裝配是Spring是知足bean依賴的一種方式
- Spring會在上下文自動尋找,並自動給bean裝配屬性
在Spring中有三種裝配的方式
-
在xml中顯示配置
-
在java中顯示配置
-
隱式的自動裝配bean 【重要】
-
環境搭建:一我的有兩個寵物
-
Byname自動裝配:byname會自動查找,和本身對象set對應的值對應的id
保證全部id惟一,而且和set注入的值一致
-
Bytype自動裝配:byType會自動查找,和本身對象屬性相同的bean
保證全部的class惟一
public class Cat { public void jiao(){ System.out.println("miao"); } }
public class Dog { public void jiao(){ System.out.println("wow"); } }
package com.pojo; public class People { private Cat cat; private Dog dog; private String name; @Override public String toString() { return "People{" + "cat=" + cat + ", dog=" + dog + ", name='" + name + '\'' + '}'; } public Cat getCat() { return cat; } public void setCat(Cat cat) { this.cat = cat; } public Dog getDog() { return dog; } public void setDog(Dog dog) { this.dog = dog; } public String getName() { return name; } public void setName(String name) { this.name = name; } }
<?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd"> <bean id="cat11" class="com.pojo.Cat"/> <bean id="dog" class="com.pojo.Dog"/> <!--byname會自動查找,和本身對象set對應的值對應的id--> <!--<bean id="people" class="com.pojo.People" autowire="byName">--> <!--<property name="name" value="hou"></property>--> <!--</bean>--> <!--byType會自動查找,和本身對象屬性相同的bean--> <bean id="people" class="com.pojo.People" autowire="byType"> <property name="name" value="hou"></property> </bean> </beans>
使用註解自動裝配
jdk1.5支持的註解,spring2.5支持的註解
The introduction of annotation-based configuration raised the question of whether this approach is 「better」 than XML.
導入context約束
<?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:context="http://www.springframework.org/schema/context" xsi:schemaLocation="http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context https://www.springframework.org/schema/context/spring-context.xsd"> <context:annotation-config/> </beans>
@Autowire
在屬性上個使用,也能夠在set上使用
咱們能夠不用編寫set方法了
public class People { @Autowired private Cat cat; @Autowired private Dog dog; private String name; }
@Nullable 字段標誌的註解,說明這個字段能夠爲null
若是@Autowired自動裝配環境比較複雜。自動裝配沒法經過一個註解完成的時候
咱們可使用@Qualifier(value = "dog")去配合使用,指定一個惟一的id對象
public class People { @Autowired private Cat cat; @Autowired @Qualifier(value = "dog") private Dog dog; private String name; }
@Resource(name="dog")也能夠
區別:
-
@autowire經過byType實現,並且必需要求這個對象存在
-
@resource默認經過byName實現,若是找不到,經過byType實現
8. 使用註解開發
在spring4以後,必需要保證aop的包導入
使用註解須要導入contex的約束
<?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:context="http://www.springframework.org/schema/context" xsi:schemaLocation="http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context https://www.springframework.org/schema/context/spring-context.xsd"> <context:annotation-config/> </beans>
- 屬性如何注入
@Component public class User { @Value("dong") private String name; public String getName() { return name; } public void setName(String name) { this.name = name; } }
- 衍生的註解
@Component有幾個衍生註解,會按照web開發中,mvc架構中分層。
- dao (@Repository)
- service(@Service)
- controller(@Controller)
這四個註解功能同樣的,都是表明將某個類註冊到容器中
- 做用域
@Scope("singleton")
@Component @Scope("prototype") public class User { @Value("dong") private String name; public String getName() { return name; } public void setName(String name) { this.name = name; } }
小結:
xml與註解
- xml更加萬能,維護簡單
- 註解,不是本身的類,使用不了,維護複雜
最佳實踐:
- xml用來管理bean
- 註解只用來完成屬性的注入
<?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:context="http://www.springframework.org/schema/context" xsi:schemaLocation="http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context https://www.springframework.org/schema/context/spring-context.xsd"> <context:annotation-config/> <!--指定要掃描的包--> <context:component-scan base-package="com.pojo"/> </beans>
9. 使用java方式配置spring
JavaConfig
Spring的一個子項目,在spring4以後,,他成爲了核心功能
@Configuration //這個也會被spring容器託管,註冊到容器中,由於他原本就是一個@Component @ComponentScan("com.pojo") @Import(Config2.class) public class MyConfig { @Bean public User getUser(){ return new User(); } }
@Component public class User { @Value("dong") private String name; public String getName() { return name; } public void setName(String name) { this.name = name; } @Override public String toString() { return "User{" + "name='" + name + '\'' + '}'; } }
這種純java配置方式
在springboot中,隨處可見
10. 動態代理
動態代理和靜態代理
角色同樣
動態代理類是動態生成的,不是咱們直接寫好的!
動態代理:基於接口,基於類
- 基於接口:JDK的動態代理【使用】
- 基於類:cglib
- java字節碼
InvocationHandler
Proxy
import java.lang.reflect.InvocationHandler; import java.lang.reflect.Method; import java.lang.reflect.Proxy; //會這個類,自動生成代理類 public class ProxyInvocation implements InvocationHandler { //被代理的接口 private Rent rent; public void setRent(Rent rent) { this.rent = rent; } //生成代理類 public Object getProxy(){ return Proxy.newProxyInstance(this.getClass().getClassLoader(),rent.getClass().getInterfaces(),this); } //處理代理實例,並返回結果 public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { seeHouse(); Object result = method.invoke(rent, args); fare(); return result; } public void seeHouse(){ System.out.println("see house"); } public void fare(){ System.out.println("fare"); } }
public interface Rent { void rent(); }
public class Host implements Rent { public void rent() { System.out.println("host rent"); } }
public class Client { public static void main(String[] args) { //真實角色 Host host = new Host(); //代理角色 ProxyInvocation proxyInvocation = new ProxyInvocation(); //經過調用程序處理角色來處理咱們要調用的接口對象 proxyInvocation.setRent(host); Rent proxy = (Rent) proxyInvocation.getProxy(); //這裏的proxy是動態生成的 proxy.rent(); } }
11.AOP
<dependencies> <dependency> <groupId>org.aspectj</groupId> <artifactId>aspectjweaver</artifactId> <version>1.9.4</version> </dependency> </dependencies>
方法一:使用spring接口【springAPI接口實現】
<?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:aop="http://www.springframework.org/schema/aop" xsi:schemaLocation="http://www.springframework.org/schema/beanss https://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/aop https://www.springframework.org/schema/aop/spring-aop.xsd"> <!--註冊bean--> <bean id="userservice" class="com.service.UserServiceImp"></bean> <bean id="log" class="com.log.Log"/> <bean id="afterlog" class="com.log.AfterLog"/> <!--配置aop--> <aop:config> <!--切入點:expression:表達式,execution(要執行的位置)--> <aop:pointcut id="point" expression="execution(* com.service.UserServiceImp.*(..))"/> <!--執行環繞--> <aop:advisor advice-ref="log" pointcut-ref="point"/> <aop:advisor advice-ref="afterlog" pointcut-ref="point"/> </aop:config> </beans>
public class UserServiceImp implements UserService { public void add() { System.out.println("add"); } public void delete() { System.out.println("delete"); } public void query() { System.out.println("query"); } public void update() { System.out.println("update"); } }
import org.springframework.aop.MethodBeforeAdvice; import java.lang.reflect.Method; public class Log implements MethodBeforeAdvice { //method:要執行的目標對象的方法 //args:參數 //target:目標對象 public void before(Method method, Object[] args, Object target) throws Throwable { System.out.println(target.getClass().getName()+method.getName()); } }
public class AfterLog implements AfterReturningAdvice { //returnVaule: 返回值 public void afterReturning(Object returnValue, Method method, Object[] args, Object target) throws Throwable { System.out.println(method.getName()+returnValue); } }
public class Mytest { public static void main(String[] args) { ApplicationContext context = new ClassPathXmlApplicationContext("ApplcationContext.xml"); //動態代理代理的是接口 UserService userService = (UserService) context.getBean("userservice"); userService.add(); } }
方法二:自定義來實現AOP【主要是切面定義】
<?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:aop="http://www.springframework.org/schema/aop" xsi:schemaLocation="http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/aop https://www.springframework.org/schema/aop/spring-aop.xsd"> <!--註冊bean--> <bean id="userservice" class="com.service.UserServiceImp"></bean> <bean id="log" class="com.log.Log"/> <bean id="afterlog" class="com.log.AfterLog"/> <bean id="diy" class="com.diy.DiyPointcut"> </bean> <aop:config> <!--自定義切面--> <aop:aspect ref="diy"> <!--切入點--> <aop:pointcut id="point" expression="execution(* com.service.UserServiceImp.*(..))"/> <aop:before method="before" pointcut-ref="point"/> <aop:after method="after" pointcut-ref="point"/> </aop:aspect> </aop:config> </beans>
public class DiyPointcut { public void before(){ System.out.println("before"); } public void after(){ System.out.println("after"); } }
方法三:註解方式
<?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:aop="http://www.springframework.org/schema/aop" xsi:schemaLocation="http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/aop https://www.springframework.org/schema/aop/spring-aop.xsd"> <bean id="ann" class="com.diy.Annotation"></bean> <aop:aspectj-autoproxy/> <!--註冊bean--> <bean id="userservice" class="com.service.UserServiceImp"></bean> </beans>
import org.aspectj.lang.ProceedingJoinPoint; import org.aspectj.lang.annotation.After; import org.aspectj.lang.annotation.Around; import org.aspectj.lang.annotation.Aspect; import org.aspectj.lang.annotation.Before; @Aspect //標註這個類是一個切面 public class Annotation { @Before("execution(* com.service.UserServiceImp.*(..))") public void before(){ System.out.println("before"); } @After("execution(* com.service.UserServiceImp.*(..))") public void after(){ System.out.println("after"); } //在環繞加強中,咱們能夠給地暖管一個參數,表明咱們要獲取切入的點 @Around("execution(* com.service.UserServiceImp.*(..))") public void around(ProceedingJoinPoint joinPoint) throws Throwable { System.out.println("around"); Object proceed = joinPoint.proceed(); System.out.println("after around"); } }
12. 整合mybatis
文檔: https://mybatis.org/spring/zh/
<?xml version="1.0" encoding="UTF-8"?> <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> <parent> <artifactId>spring-study</artifactId> <groupId>com.hou</groupId> <version>1.0-SNAPSHOT</version> </parent> <modelVersion>4.0.0</modelVersion> <artifactId>spring-10-mybatis</artifactId> <dependencies> <dependency> <groupId>mysql</groupId> <artifactId>mysql-connector-java</artifactId> <version>5.1.47</version> </dependency> <dependency> <groupId>org.mybatis</groupId> <artifactId>mybatis-spring</artifactId> <version>2.0.4</version> </dependency> <dependency> <groupId>org.springframework</groupId> <artifactId>spring-jdbc</artifactId> <version>5.2.3.RELEASE</version> </dependency> <dependency> <groupId>org.mybatis</groupId> <artifactId>mybatis</artifactId> <version>3.5.2</version> </dependency> <dependency> <groupId>org.aspectj</groupId> <artifactId>aspectjweaver</artifactId> <version>1.9.4</version> </dependency> <dependency> <groupId>org.projectlombok</groupId> <artifactId>lombok</artifactId> <version>1.18.12</version> </dependency> </dependencies> <build> <resources> <resource> <directory>src/main/resources</directory> <includes> <include>**/*.properties</include> <include>**/*.xml</include> </includes> </resource> <resource> <directory>src/main/java</directory> <includes> <include>**/*.properties</include> <include>**/*.xml</include> </includes> <filtering>true</filtering> </resource> </resources> </build> </project>
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE configuration PUBLIC "-//mybatis.org//DTD Config 3.0//EN" "http://mybatis.org/dtd/mybatis-3-config.dtd"> <configuration> <typeAliases> <package name="com.pojo"/> </typeAliases> <environments default="development"> <environment id="development"> <transactionManager type="JDBC"/> <dataSource type="POOLED"> <property name="driver" value="com.mysql.jdbc.Driver"/> <property name="url" value="jdbc:mysql://111.230.212.103:3306/mybatis?userSSL=true& userUnicode=true&characterEncoding=UTF-8"/> <property name="username" value="root"/> <property name="password" value="hdk123"/> </dataSource> </environment> </environments> <mappers> <mapper class="com.mapper.UserMapper"/> </mappers> </configuration>
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Config 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd"> <mapper namespace="com.mapper.UserMapper"> <select id="selectUser" resultType="user"> select * from mybatis.user; </select> </mapper>
public interface UserMapper { List<User> selectUser(); }
整合
方法一:
UserMapperImpl
package com.mapper; import com.pojo.User; import org.mybatis.spring.SqlSessionTemplate; import java.util.List; public class UserMapperImpl implements UserMapper { private SqlSessionTemplate sqlSessionTemplate; public void setSqlSessionTemplate(SqlSessionTemplate sqlSessionTemplate) { this.sqlSessionTemplate = sqlSessionTemplate; } public List<User> selectUser() { UserMapper mapper = sqlSessionTemplate.getMapper(UserMapper.class); return mapper.selectUser(); } }
mybatis.xml
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE configuration PUBLIC "-//mybatis.org//DTD Config 3.0//EN" "http://mybatis.org/dtd/mybatis-3-config.dtd"> <configuration> <typeAliases> <package name="com.pojo"/> </typeAliases> </configuration>
spring.xml
<?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:aop="http://www.springframework.org/schema/aop" xsi:schemaLocation="http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/aop https://www.springframework.org/schema/aop/spring-aop.xsd"> <!--data source--> <bean id="datasource" class="org.springframework.jdbc.datasource.DriverManagerDataSource"> <property name="driverClassName" value="com.mysql.jdbc.Driver"/> <property name="url" value="jdbc:mysql://111.230.212.103:3306/mybatis?userSSL=true& userUnicode=true&characterEncoding=UTF-8"/> <property name="username" value="root"/> <property name="password" value="hdk123"/> </bean> <!--sqlsession--> <bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean"> <property name="dataSource" ref="datasource" /> <!--bound mybatis--> <property name="configLocation" value="classpath:mybatis-config.xml"/> <property name="mapperLocations" value="classpath:com/mapper/UserMapper.xml"/> </bean> <bean id="sqlSession" class="org.mybatis.spring.SqlSessionTemplate"> <constructor-arg index="0" ref="sqlSessionFactory"/> </bean> <bean id="userMapper" class="com.mapper.UserMapperImpl"> <property name="sqlSessionTemplate" ref="sqlSession"></property> </bean> </beans>
test
import com.mapper.UserMapper; import com.pojo.User; import org.springframework.context.support.ClassPathXmlApplicationContext; import java.io.IOException; public class Mytest { public static void main(String[] args) throws IOException { ClassPathXmlApplicationContext context = new ClassPathXmlApplicationContext("spring-dao.xml"); UserMapper userMapper = context.getBean("userMapper", UserMapper.class); for (User user : userMapper.selectUser()) { System.out.println(user); } } }
方法二:
<?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd"> <!--data source--> <bean id="datasource" class="org.springframework.jdbc.datasource.DriverManagerDataSource"> <property name="driverClassName" value="com.mysql.jdbc.Driver"/> <property name="url" value="jdbc:mysql://111.230.212.103:3306/mybatis?userSSL=true& userUnicode=true&characterEncoding=UTF-8"/> <property name="username" value="root"/> <property name="password" value="hdk123"/> </bean> <!--sqlsession--> <bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean"> <property name="dataSource" ref="datasource" /> <!--bound mybatis--> <property name="configLocation" value="classpath:mybatis-config.xml"/> <property name="mapperLocations" value="classpath:com/mapper/UserMapper.xml"/> </bean> <!--<bean id="sqlSession" class="org.mybatis.spring.SqlSessionTemplate">--> <!--<constructor-arg index="0" ref="sqlSessionFactory"/>--> <!--</bean>--> <!--<bean id="userMapper" class="com.mapper.UserMapperImpl">--> <!--<property name="sqlSessionTemplate" ref="sqlSession"></property>--> <!--</bean>--> <bean id="userMapper2" class="com.mapper.UserMapperIml2"> <property name="sqlSessionFactory" ref="sqlSessionFactory"></property> </bean> </beans>
package com.mapper; import com.pojo.User; import org.apache.ibatis.session.SqlSession; import org.mybatis.spring.support.SqlSessionDaoSupport; import java.util.List; public class UserMapperIml2 extends SqlSessionDaoSupport implements UserMapper { public List<User> selectUser() { SqlSession sqlSession = getSqlSession(); UserMapper mapper = sqlSession.getMapper(UserMapper.class); return mapper.selectUser(); } }
13. 聲明式事務
- 要麼都成功,要麼都失敗
- 十分重要,涉及到數據一致性
- 確保完整性和一致性
事務的acid原則:
-
原子性
-
一致性
-
隔離性
- 多個業務可能操做一個資源,防止數據損壞
-
持久性
- 事務一旦提交,不管系統發生什麼問題,結果都不會被影響。
Spring中的事務管理
- 聲明式事務
- 編程式事務
聲明式事務
<?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:tx="http://www.springframework.org/schema/tx" xmlns:aop="http://www.springframework.org/schema/aop" xsi:schemaLocation="http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/tx https://www.springframework.org/schema/tx/spring-tx.xsd http://www.springframework.org/schema/aop https://www.springframework.org/schema/aop/spring-tx.aop"> <!--data source--> <bean id="datasource" class="org.springframework.jdbc.datasource.DriverManagerDataSource"> <property name="driverClassName" value="com.mysql.jdbc.Driver"/> <property name="url" value="jdbc:mysql://111.230.212.103:3306/mybatis?userSSL=true& userUnicode=true&characterEncoding=UTF-8"/> <property name="username" value="root"/> <property name="password" value="hdk123"/> </bean> <!--sqlsession--> <bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean"> <property name="dataSource" ref="datasource" /> <!--bound mybatis--> <property name="configLocation" value="classpath:mybatis-config.xml"/> <property name="mapperLocations" value="classpath:com/mapper/*.xml"/> </bean> <!--聲明式事務--> <bean id="transactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager"> <constructor-arg ref="datasource" /> </bean> <!--結合aop實現事務置入--> <!--配置事務的類--> <tx:advice id="tx1" transaction-manager="transactionManager"> <!--給哪些方法配置事務--> <!--配置事務的傳播特性--> <tx:attributes> <tx:method name="add" propagation="REQUIRED"/> <tx:method name="delete" propagation="REQUIRED"/> <tx:method name="update" propagation="REQUIRED"/> <tx:method name="*" propagation="REQUIRED"/> <tx:method name="query" read-only="true"/> </tx:attributes> </tx:advice> <!--配置事務切入--> <aop:config> <aop:pointcut id="txpointxut" expression="execution(* com.mapper.*.*(..))"/> <aop:advisor advice-ref="tx1" pointcut-ref="txpointxut"/> </aop:config> </beans>
<?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd"> <import resource="spring-dao.xml"/> <bean id="userMapper2" class="com.mapper.UserMapperIml2"> <property name="sqlSessionFactory" ref="sqlSessionFactory"></property> </bean> </beans>
Mapper
package com.mapper; import com.pojo.User; import java.util.List; public interface UserMapper { List<User> selectUser(); int addUser(User user); int delete(int id); }
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Config 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd"> <mapper namespace="com.mapper.UserMapper"> <select id="selectUser" resultType="user"> select * from mybatis.user; </select> <insert id="addUser" parameterType="user"> insert into mybatis.user (id, name, pwd) values (#{id}, #{name}, #{pwd}) </insert> <delete id="delete" parameterType="int"> delete from mybatis.user where id=#{id} </delete> </mapper>
package com.mapper; import com.pojo.User; import org.apache.ibatis.session.SqlSession; import org.mybatis.spring.support.SqlSessionDaoSupport; import java.util.List; public class UserMapperIml2 extends SqlSessionDaoSupport implements UserMapper { public List<User> selectUser() { User user = new User(6, "long", "zhi"); SqlSession sqlSession = getSqlSession(); UserMapper mapper = sqlSession.getMapper(UserMapper.class); mapper.addUser(user); mapper.delete(6); return mapper.selectUser(); } public int addUser(User user) { return getSqlSession().getMapper(UserMapper.class).addUser(user); } public int delete(int id) { return getSqlSession().getMapper(UserMapper.class).delete(id); } }