Spring框架
一:框架
理念:
使现有的技术更加容易使用,本身是一个大杂烩,整合现有的技术框架
:SSM :
SpringMVC +Spring +MyBatis
1.spring配置文件
1.1:jar包依赖
<?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">
<modelVersion>4.0.0</modelVersion>
<groupId>org.example</groupId>
<artifactId>spring06</artifactId>
<version>1.0-SNAPSHOT</version>
<packaging>war</packaging>
<name>spring06 Maven Webapp</name>
<!-- FIXME change it to the project's website -->
<url>http://www.example.com</url>
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<maven.compiler.source>1.8</maven.compiler.source>
<maven.compiler.target>1.8</maven.compiler.target>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-jdbc</artifactId>
<version>5.3.5</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
<version>5.3.5</version>
</dependency>
<!--JUnit是一个开放源代码的Java测试框架,用于编写和运行可重复的测试-->
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.12</version>
<scope>test</scope>
</dependency>
</dependencies>
</project>
1.2:spring.xml 配置文件头标签
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans" xmlns:context="http://www.springframework.org/schema/context"
xmlns:util="http://www.springframework.org/schema/util"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-3.2.xsd
http://www.springframework.org/schema/context
http://www.springframework.org/schema/context/spring-context-3.2.xsd
http://www.springframework.org/schema/util
http://www.springframework.org/schema/util/spring-util-3.2.xsd">
<!-- 开启属性注解 -->
<context:annotation-config />
<!--开启注解支持 在使用AOP 中-->
<aop:aspecttj-autoproxy/>
1.3:注解大全
-@Autowired :自动装配通过类型,名字 如果Autowired 不能唯一自动装配上属性,则需要通过-@Qualifier(value="xxx")
-@Nullable字段标记了这个注解,说明这个字段可以为null
-@Resource:自动装配通过名字,类型
-@Component :组件放在类上,说明这个类被Spring 管理了
1.4:拓展
【lombok 】去除麻烦的实体类get和set,toString书写
1.4.1:在pom.xml中添加
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<version>1.16.18</version><!-- -->
</dependency>
1.4.2.在实体类中添加
具体用法时在实体类上加注解
@Data//自动生成get和set,tostring
@NoArgsConstructor//自动生成无参构造函数
@AllArgsConstructor//自动生成全参数构造函数
@Setter:注解在属性上;为属性提供 setting 方法
@Getter:注解在属性上;为属性提供 getting 方法
@Log4j :注解在类上;为类提供一个 属性名为log 的 log4j 日志对象
1.4.3:例:
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
@Data //自动生成get 和set ,tostring
@NoArgsConstructor //自动生成无参构造
@AllArgsConstructor //自动生成全参数构造函数
public class Person {
public String name;
public Dog dog;
public Cat cat;
}
1.4.4:Spring Book
一个快速开发的脚手架
基于SpringBoot 可以快速的开发单个微服务
约定大于配置
Spring Cloud 是基于Spring Boot实现的
1.5:优点
1.:Spring 是一个开源的免费的框架(容器)
2.Spring 是一个轻量级,非侵入式的框架
3.控制反转(IOC),面向切面编程(AOP)
4.支持事务的处理,对框架整合的支持
1.6:总结
Spring就是一个轻量级的控制反转(IOC)和面向切面编程(AOP)的框架!
1.7:组成
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-KGmVi9cn-1619590998926)(捕获 (3)]-1619324153526.PNG)
二:IOC理论推导
1.dao 接口
2.daoimpl 实现类
3.service 业务接口
4 serviceimpl 业务实现类
2.1:set 进行动态实现值的注入
//userDao 接口
public void setUserDao(UserDao userDao){
this.userDao=userDao;
}
//实现类
((UserServiceImpl) userServise).setUserDao(new UserDaoSqlServerImpl);
userService.getUser();
再我们之前的业务中,用户的需求可能会影响我们原来的代码,我们需要根据用户的需求修改源代码
我们使用一个 Set 接口实现的好处
1.之前,程序是主动创建对象,控制权在程序猿手上
2.使用set 注入控制权在用户手上
这种思想,从本质上解决了问题,我们不用在去管理对象的创建。系统耦合性大大降低,可以更加专注于业务上的实现。这就是IOC 的原!(捕获 (2).PNG)
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-9BZVegqe-1619590998928)(捕获1-1619312357645.PNG)]
IOC本质
控制反转,是一种设计思想,DI(依赖注入)是实现IOC的一种方法,没有IOC的程序中我们使用面向对象编程,对象的创建与对象间的依赖关系完全硬编码在程序中,对象的创建由程序自己控制,控制反转就是对象的创建给别人
个人认为反转就是:获取依赖对象的方式反转了
IOC 是Spring 的核心内容,使用多种方法完美的实现IOC,
控制反转是一种通过描述(xml或注解)并通过第三方去生产或获取特定对象的方式。在Spring中实现控制反转的是IOC 容器,其实现的方法就是依赖注入(Dependency injection。DI)
1.导入jar包
两个jar包
spring-webmvc
spring-jdbc
2.创建一个实体类
public class hello
3.写 spring.xml 文件
<!--使用Spring来创建对象,在spring 这些都称为BEan
类型 变量名=new 类型();
bean =对象 new hello();
id=变量名
class = new 的对象
property 相当于给队象中的属性设置一个值
-->
<bean id="hello " class="com.zhke.pojo.hello">
<property name="str" value="Spring"/>
<!--
ref:引用Spring容器中创建好的对象
value:具体的值,基本数据类型
-->
</bean>
测试类
//获取spring上下文对象
//获取ApplicationContext spring 容器
ApplicationContext context=new ClassPathxmlApplictionContext("beans.xml")
//我们的对象现在都在Spring 中管理,我们要是使用,直接去取
hello hello= context.getBean("hello")
这个过程就是控制反转
控制:
谁来控制对象的创建,使用spring 后对象就是由spring 创建
反转:
程序本身不创建对象,而变成了被动的接受对象
依赖注入:
就是利用set 方法进行注入
IOC 是一种编程思想,由主动的编程变成被动的接受
要实现不同的操作,只需要在xml 文件中进行修改。
IOC 就是:对象由Spring 来创建 ,管理,装配
IOC创建对象的方式
1.通过无参构造创建对象,默认
2.假设我们要是用有参构造创建对象
1.下标赋值
<constructor -arg index="0" value ="节点覅"/>
2.类型创建
<!-- 通过类型创建-->
<constructor-arg type="java.lang.String" value="傻逼"/>
3.通过参数类型
<!--通过参数类型-->
<constructor-arg name="name" value="hg " />
总结:
在配置文件加载的时候,容器中管理的对象就已经初始化了
Spring 配置
别名:
<!--别名,直接通过参数名来设置-->
<alias name="user" alias="userNew"
Bean 的配置
<!--
id:bean 的唯一标识符,也就是我们学的对象名
class :bean 对象对应的全限定名:包
名 + 类型
name : 也是别名,而且同时取多个别名
-->
<bean id="user" class="com.zhke.pojo.user" name="user1">
<property name="name" value="西部"/>
</bean>
import
这个import ,一般用于团队开发,他可以将多个配置文件,导入合并为一个
依赖注入(DI)
1.构造器注入
2.通过set注入【重点】
依赖注入:set注入
依赖:bean对象的创建依赖于容器
注入:bean 对象中的所有属性,
环境搭建:
1.复杂类型
package com.zhke.pojo;
public class address {
private address address;
public com.zhke.pojo.address getAddress() {
return address;
}
public void setAddress(com.zhke.pojo.address address) {
this.address = address;
}
}
2.真实测试对象
public class Student {
private String name;
private address address;
private String[] books;
private List<String> hobbys;
private Map<String,String> card;
private Set<String > games;
private String wife;
private Properties info;
3.spring.xml
<!--普通注入 基本数据类型 value-->
<bean id="student" class="com.zhke.pojo.Student">
<property name="name" value="张珊"/>
</bean>
4.测试类
ApplicationContext context = new ClassPathXmlApplicationContext("spring.xml");
Student student = (Student) context.getBean("student");
System.out.println(student.getName());
}
5.各种注入
##### <?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
http://www.springframework.org/schema/beans/spring-beans-3.0.xsd">
<bean id="add" class="com.zhke.pojo.address">
<property name="address" value="更好"/>
<!-- <property name="address" value="河岸"/>-->
</bean>
<!--普通注入 基本类型 value-->
<bean id="student" class="com.zhke.pojo.Student">
<property name="name" value="张珊"/>
<!--引用注入 引用类型 ref-->
<property name="address" ref="add"/>
<!--数组 类型 set 注入-->
<!-- <bean id="books" class="com.zhke.pojo.Student">-->
<property name="books">
<array >
<value> 红楼梦</value>
<value> 西游记</value>
<value> 水浒传</value>
<value> 三国演义</value>
</array>
</property>
<!-- </bean>-->
<!-- list-->
<!-- <bean id="hobbys" class="com.zhke.pojo.Student">-->
<property name="hobbys" >
<list>
<value>打游戏</value>
<value>看小说</value>
<value>打豆豆</value>
</list>
</property>
<!--map 注入-->
<property name="card" >
<map>
<entry key="身份证" value="411326"/>
<entry key="学号" value="20183230"/>
<entry key="手机号" value="123105"/>
</map>
</property>
<!-- set 注入-->
<property name="games">
<set>
<value>辣条</value>
<value>卫龙辣条</value>
<value>莫干辣椒</value>
</set>
</property>
<!-- null注入 -->
<property name="wife">
<null/>
</property>
<!-- Properties 注入-->
<property name="info">
<props>
<prop key="QQ号">123</prop>
<prop key="猪肉">40</prop>
</props>
</property>
</bean>
</beans>
拓展方式注入
<!--重要 :头文件两个 链接-->
<beans
xmles:p="http://www.springframework.org/schema/p"
xmles:c="http://www.springframework.org/schema/c"
<!--p命名空间注入,可以直接注入属性的值: property-->
<bean id="user" class="com.kuang.pojo.User" p:name="冻干粉" page="18"/>
<!--c命名空间注入,通过构造器注入: construct-args-->
<bean id="user2" class="com.kuang.pojo.User" c:age="18" c:name="胡椒粉"/>
</beans>
注意点:不能直接使用,需要导入xml约束
bean Scopes( bean 的作用域)
单例模式(spring默认机制)
<bean name="user1" class="com.zhke.pojo.User " c:age="415" c:name="环境" scope="singleton"/>
原型模式:每次从容器中get的时候,等会产生一个心得对象
<bean name="user1" class="com.zhke.pojo.User " c:age="415" c:name="环境" scope="prototype"/>
7:Bean 自动装配
自动装配是Spring满足bean依赖的一种方式
Spring 会在上下文中自动寻找,并自动给bean装配属性
在spring中有三种方式
1.在xml中显示的配置
2.在java中配置
3.隐式自动装配(重点)
autowire (自动装配)
byname :会自动在容器上下文中查找,和自己对象set 方法后面 的值对应的 beanid
<bean id="person" class="com.zhke.pojo.Person" autowire="byName">
<property name="name" value="站"/>
bytype :会自动在容器上下文中查找,和自己对象属性类型相同的bean
<bean class="com.zhke.pojo.Dog"/>
<bean class="com.zhke.pojo.Cat"/>
<bean id="person" class="com.zhke.pojo.Person" autowire="byType">
<property name="name" value="站"/>
</bean>
小结:
byname:的时候,需要保证bean的ID唯一,并且这个bean需要和自动注入的属性的set方法一致
bytype 的时候需要保证所有bean的class 唯一,并且这个bean需要和自动注入的类型一致
使用注解开发实现自动装配
jdk 1.5 支持的注解
Spring2.5 支持注解
要使用注解须知 头文件
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans" xmlns:context="http://www.springframework.org/schema/context"
xmlns:util="http://www.springframework.org/schema/util"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-3.2.xsd
http://www.springframework.org/schema/context
http://www.springframework.org/schema/context/spring-context-3.2.xsd
http://www.springframework.org/schema/util
http://www.springframework.org/schema/util/spring-util-3.2.xsd">
<!-- 开启属性注解 -->
<context:annotation-config />
</beans>
1.导入约束 context 约束
2.配置注解的支持context:annotation-config
@Autwired
自动注入 ,直接在属性上使用,也可以在set 方法使用
使用Autwired 我们不用编写set 方法,前提
自动装配的属性在IOC (spring容器中存在),且符合名字 byname
科普:
@Nullable 字段标记了这个注解,说明这个字段可以为 null
如果@AUtwired 自动装配环境比较复杂,自动装配无法通过注解完成时可以是配合使用
@Qualifier (value=“xxxx”) 可以和@Autwired 一起使用
@Resource
@Resource 和 @Autowired 的区别
都是用来自动装配的,都可以放在属性字段上
区别
@ Autowired 通过bytype 的方式实现而且必须要求这个对象存在
@ Resource 通过byname 的方式实现如果找不到名字,则通过bytype 实现,如果都找不到就报错
执行顺序不同
使用注解开发
使用注解需要导包 前面有
扫描器
<context :compoent-scan base-pacjage : "com.zhke"/>
属性如何注入
@Component
等价于 <bean id ="user" class="com.zhke.pojo.User"/>
@Component 组件
@Value("环境")
相当于
<property name="name" value="环境"/>
衍生注解
@Conponent 有几个衍生注解我们在web开发中,会按照MVC 三层架构分层
dao 【@Repositoty】
sevice 【@Service】
controller 【Controller】
这四个注解功能都是一样的,都是代表将某个类注册到Spring 中 装配Bean
作用域
Scope (“prototype”) 单例
小结
xml 与注解
xml 更加万能,适用于任何场合,维护简单方便
注解不是自己的类使用不了,维护相对复杂
xml与注解最佳实践:
xml 用来管理bean ;
注解只负责完成属性的注入;
我们使用过程中只需要注意一个问题,必须让注解生效
<!--指定要扫描的包,这个包下的注解就会生效-->
<context:component-scan base-psckage="com.zhke"/>
<!--开启属性注解-->
<context:annotation-config/>
三:代理模式
为什么要学习代理模式
因为这就是SpringAOP 的底层【SpringAOP 和SpringMVC】必考
3.1:代理模式
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-63NroHLj-1619590998930)(G:\学习至上\spring\图片\4.PNG)]
3.1.1:静态代理:
角色分析
抽象角色:一般会使用接口或者抽象类来解决
真实角色:被代理的角色
代理的角色:代理这是角色,代理真实角色后,我们一般会做一些附属操作
客户:访问对象的人
代码步骤
1.接口
public interface Rent {
public void rent();
}
2.真实角色
public class House implements Rent, jia{
@Override
public void rent() {
System.out.println("房东出租房屋");
}
@Override
public void furniture() {
System.out.println("房东卖家具");
}
}
3.代理角色
public class Agent {
private House house;
public Agent() {
}
public Agent(House house) {
this.house = house;
}
public void rent(){
house.rent();
money();
seeHouse();
house.furniture();
}
public void money(){
System.out.println("中介说钱");
}
public void seeHouse(){
System.out.println("中介看房");
}
}
4客户端角色
public class Person {
private static House rent;
public static void main(String[] args) {
//房东要出租房子
House house = new House();
// house.rent();
//代理租房
Agent agent = new Agent(house);
//你不用向房东租直接找中介
agent.rent();
}
}
3.1.2:代理模式的好处:
可以使真实角色的操作更家纯粹,不用去关注一些公共的业务
公共也就就交给代理角色,实现了业务的分工
公共业务发生拓展的时候,方便集中管理
缺点:
一个真实角色就会产生一个代理角色:代码量会翻倍,开发效率就会变低
AOP 深入理解
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-ZwflBike-1619590998933)(aop.PNG)]
3.2:动态代理 (运用反射)
动态代理和静态代理角色一样
动态代理的代理类是动态生成的,不是我们直接写好的
动态代理分两大类
:基于接口的动态代理,基于类的动态代理
基于接口—jdk动态代理【我们使用这个】
基于类:cglib
java 字节码:javaAssist
英文单词:reflect (反射)
需要了解两个类:proxy(代理)
提供了创建动态代理和市里的静态方法,他也是由这些方法创建的
inocattionHandler ()
万能代理类代码(只需要修改 house)
public class ProxyInvocationHAndler implements InvocationHandler {
//被代理的接口
private Object house;
public void setHouse(Object house) {
this.house = house;
}
//生成代理类
public Object getProxy() {
return Proxy.newProxyInstance(this.getClass().getClassLoader(), house.getClass().getInterfaces(),this);
}
//处理 dailishil,并返回结果
@Override
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
Object result = method.invoke(house, args);
return null;
}
}
r
测试类
House house = new House();
//代理角色
ProxyInvocationHAndler pih = new ProxyInvocationHAndler();
//通过调用程序处理角色来处理我们要调用的接口对象
//设置要代理的对象
pih.setHouse(house);
//proxy 是动态代理生成的
Rent proxy = (Rent) pih.getProxy();
proxy.rent();
}
}
动态代理的好处
1.可以使真实角色的操作更加纯粹,不用去关注一些公共的业务
2.公共也就是交给代理角色,实现了业务的份分工
3.公共业务发生拓展的时候,方便集中管理
4.一个动态代理类代理的是一个接口,一般就是对应的一类业务
5.一个动态代理类可以代理多个类,只要是实现了同一个接口即可
四:AOP
4.1:什么是AOP :
AOP 意为:面向切面编程,通过预编译方式和运行期动态代理实现程序功能的同一维护的一种技术。AOP 是OOP 的延续,是软件开发中的一个热点,也是Spring 框架中一个重要内容。是函数式编程的一种衍生泛型,利用AOP 可以对业务逻辑的各个部分进行分割,从而使得业务逻辑各个部分的耦合度降低,提高程序的可重要性,同时提高开发的效率。
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-uXTEINnI-1619590998935)(aop1.PNG)]
4.2:AOP在spring中的作用
提供事务,允许用户自定义切面
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-oQ1MZeIs-1619590998936)(aop03.PNG)]
4.3:springAOP中,通过Advice定义横向切逻辑,Spring中支撑5中类型的Advice
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-Ld7dXgOx-1619590998937)(aop04.PNG)]
即在不改变原有代码的情况下,去增加心的功能
4.4:使用Spring实现AOP
【重点】使用AOP织入,需要导入一个依赖包
aspectjweaver
4.4.1:方式一:使用Spring Api接口 MethodBeforAdvice APi接口【主要SpringAPI接口实现】
public class log implements MethodBeforeAdvice {
//method:要执行对象的方法
//args:参数
//target:目标对象
@Override
public void before(Method method, Object[] args, Object target) throws Throwable {
System.out.println(target.getClass().getName()+"的"+method.getName()+"被执行了");
}
}
2.spring.xml 中配置
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans" xmlns:context="http://www.springframework.org/schema/context"
xmlns:util="http://www.springframework.org/schema/util"
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
http://www.springframework.org/schema/beans/spring-beans-3.2.xsd
http://www.springframework.org/schema/context
http://www.springframework.org/schema/context/spring-context-3.2.xsd
http://www.springframework.org/schema/util
http://www.springframework.org/schema/util/spring-util-3.2.xsd
http://www.springframework.org/schema/aop
https://www.springframework.org/schema/aop/spring-aop.xsd">
<!-- <!– 开启属性注解 –>-->
<!-- <context:annotation-config />-->
<bean id="userService" class="com.zhke.service.UserServiceImpl"/>
<bean id="log" class="com.zhke.log4j.log"/>
<!--方式一:使用原生Spring Api接口-->
<!-- 配置aop-->
<aop:config>
<!-- 切入点 expression 表达式:execution(要执行的位置 *****)-->
<aop:pointcut id="pointcut" expression="execution(* com.zhke.service.UserServiceImpl.*(..))"/>
<!--执行环绕增加-->
<aop:advisor advice-ref="log" pointcut-ref="pointcut"/>
</aop:config>
</beans>
在spring .xml 中配置aop :需要导入aop 的约束
<dependency>
<groupId>org.aspectj</groupId>
<artifactId>aspectjweaver</artifactId>
<version>1.9.6</version>
</dependency>
4.4.2:方式二:自定义来实现AOP【主要是切面定义】
public void before(){
System.out.println("方法执行前")
}
<!--自定义类-->
<bean id=diy class="com.zhke.diy"/>
<aop:config>
<!--自定义切面,-->
<aop:aspect ref="diy">
<!--切入点-->
<aop:pointcut id="point" expression="execution" ( * com.zhke.service.UserServiceImpl.*(..))/>
<!--通知-->
<aop:before method="before" pointcut-ref="point"/>
</aop:aspect>
</aop:config>
</aop:config>
4.4.3 :使用注解实现
//使用注解方式实现AOP
@Aspect //标注这个类是一个切面
public class An(){
@Before("execution (* com.zhke.service.UserServiceIpml.*(..))")
System.out.print("方法执行前")
public void befre(){
System.out.print("方法执行前")
}
// @After("")在方法执行后
@After("execution(* com.zhke.service.UserServiceImpl.*(..))")
public void after(){
System.out.println("方法执行后");
}
//@Around("")在环绕增强中我们可以给定一个参数,代表我们要获取处理的切入点
@Around("execution(* com.zhke.service.UserServiceImpl .*(..))")
public void around(ProceedingJoinPOint jp) throws Throwable{
Object proceed=jp.proceed();//执行方法
}
//joinPoint 获取切入的点
}
<!--开启注解支持-->
<aop:aspecttj-autoproxy/>
五:整合myBatis
去maven上找jar
步骤:
1.导入jar包
junit
mybatis
mysql 数据库
spring 相关
aop 织入[aspectjweaver]
mybatis-spring 【new 】
longbook
2.编写配置文件
3.测试
回忆mybatis
1.编写实体类
2.编写核心文件
3.编写接口
4.编写MAppering.xml
5.测试
1.MyBatis基本步骤
1.导入jar包
<dependencies>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.11</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.mybatis</groupId>
<artifactId>mybatis</artifactId>
<version>3.5.6</version>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>5.1.46</version>
</dependenc>
<dependency>
<groupId>log4j</groupId>
<artifactId>log4j</artifactId>
<version>1.2.17</version>
</dependency>
</dependencies>
<build>
<resources>
<resource>
<directory>src/main/java</directory>
<includes>
<include>**/*.xml</include>
</includes>
</resource>
</resources>
</build>
1.编写实体类
public class User {
private int uid;
private String uusername;
private String upassword;
2.编写接口
public interface UserMapper {
public List<User> SelectAll();
}
3.编写Mapper.xml
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper
PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.zhke.mapper.UserMapper">
<select id="SelectAll" resultType="com.zhke.pojo.User">
select * from user
</select>
</mapper>
3.写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>
<!-- 和spring整合后 environments配置将废除 -->
<environments default="development">
<environment id="development">
<!-- 使用jdbc事务管理 -->
<transactionManager type="JDBC" />
<!-- 数据库连接池 -->
<dataSource type="POOLED">
<property name="driver" value="com.mysql.jdbc.Driver" />
<property name="url" value="jdbc:mysql://localhost:3306/mydb?characterEncoding=utf-8" />
<property name="username" value="root" />
<property name="password" value="root" />
</dataSource>
</environment>
</environments>
<mappers>
<package name="com.zhke.mapper"/>
</mappers>
</configuration>
4.log4j .xml
log4j.rootLogger=DEBUG,Console
log4j.appender.Console=org.apache.log4j.ConsoleAppender
log4j.appender.Console.layout=org.apache.log4j.PatternLayout
log4j.appender.Console.layout.ConversionPattern=%d [%t] %-5p [%c] - %m%n
log4j.logger.org.apache=INFO
5.编写MyBatisUitl 使其变成单例模式
private void MyBatisUitl(){}
private static SqlSessionFactory sqlSessionFactory;
static{
try {
sqlSessionFactory = new SqlSessionFactoryBuilder()
.build(Resources.getResourceAsStream("mybatis-config.xml"));
} catch (IOException e) {
e.printStackTrace();
}
}
public static SqlSessionFactory getSqlSessionFactory(){
return sqlSessionFactory;
}
}
6.测试
public class mytest {
public static void main(String[] args) {
SqlSessionFactory factory = MyBatisUtil.getSqlSessionFactory();
SqlSession session = factory.openSession(true);
// List<User> users = session.selectList();
UserMapper mapper = session.getMapper(UserMapper.class);
List<User> users = mapper.SelectAll();
for (User user : users) {
System.out.println(user);
}
}
}
2.mybatis—spring 整合
什么是Mybatis-spring
他会帮助你讲mybatis 无缝整合到 spring
xxxTemplate :模板
一:.步骤
1.编写数据源
<?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
http://www.springframework.org/schema/beans/spring-beans.xsd">
2.sqlSessionFactory
<!-- 配置SQL sessionFactory 关联MyBatis-->
<bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">
<property name="dataSource" ref="dataSource"/>
<!-- 关联mybatis -->
<property name="configLocation" value="classpath:mybatis-config.xml"/>
<property name="mapperLocations" value="classpath:com/zhke/mapper/*.xml"/>
</bean>
3.sqlSessionTemplate
<!-- 注册sqlSessionTemplate 关联 sqlSessionFactory-->
<bean id="sqlSession" class="org.mybatis.spring.SqlSessionTemplate">
<!--利用构造器注入-->
<constructor-arg index="0" ref="sqlSessionFactory"/>
</bean>
4.需要给接口加实现类【】
public class UserMapperImpl implements UserMapper{
//sqlSession 不用我们自己创建,spring 来管理
private SqlSessionTemplate sqlSession;
public void setSqlSession(SqlSessionTemplate sqlSession) {
this.sqlSession = sqlSession;
}
@Override
public List<User> SelectAll() {
UserMapper mapper = sqlSession.getMapper(UserMapper.class);
return mapper.SelectAll();
}
}
5.将自己写的实体类注入到 speing.xml中
ApplicationContext context = new ClassPathXmlApplicationContext("spring-dao.xml");
UserMapper userDao = (UserMapper) context.getBean("userDao");
List<User> users = userDao.SelectAll();
for (User user : users) {
System.out.println(user);
六:声明式事务
1.回顾事务
1.把一组业务当成一个业务:要么成功,要么失败
2.事务在项目开发中十分重要,涉及到数据的一致性,不能马虎
3.确保完整性和一致性
事务ACID 原则
原子性
一致性
隔离性
多个业务可能操作同一个资源,防止数据损坏
持久化
事务一旦提交,无论系统发生了什么问题,结果都不会在被影响,被持久化的写到存储器中’
2.spring 中的事务管理
声明式事务:AOP
编程式事务:【基本不用】
<!--配置声明式事务-->
<bean id="teansactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
<property name="dataSource " ref="dataSource"/>
<!--结合AOP 实现事务的注入-->
<!--配置事务通知-->
<tx:advice id="txAdvice" transaction-manager="transactionMAnager">
<!--给哪些方法配置事务-->
<!--配置事务的传播特性:new propagation-->
<tx:attributes>
<tx:method name="*"/>
</tx:attributes>
</tx:advice>
</bean>
<!--配置事务的切入-->
<aop:config>
<aop:pointcut id="txPointCut" expression="exection(* com.zhke.mapper.*.*(..))"/>
<aop:advisor advice-ref="txAdvice" pointcut-ref="txPointCut"/>
</aop:config>
3.为什么需要事务
如果不配置事务,可能存在数据提交不一致的情况
如果我们不在 SPRING 中去配置声明式事务,我们需要在代码中手动配置事务
= sqlSession;
}
@Override
public List<User> SelectAll() {
UserMapper mapper = sqlSession.getMapper(UserMapper.class);
return mapper.SelectAll();
}
}
5.将自己写的实体类注入到 speing.xml中
```java
ApplicationContext context = new ClassPathXmlApplicationContext("spring-dao.xml");
UserMapper userDao = (UserMapper) context.getBean("userDao");
List<User> users = userDao.SelectAll();
for (User user : users) {
System.out.println(user);
六:声明式事务
1.回顾事务
1.把一组业务当成一个业务:要么成功,要么失败
2.事务在项目开发中十分重要,涉及到数据的一致性,不能马虎
3.确保完整性和一致性
事务ACID 原则
原子性
一致性
隔离性
多个业务可能操作同一个资源,防止数据损坏
持久化
事务一旦提交,无论系统发生了什么问题,结果都不会在被影响,被持久化的写到存储器中’
2.spring 中的事务管理
声明式事务:AOP
编程式事务:【基本不用】
<!--配置声明式事务-->
<bean id="teansactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
<property name="dataSource " ref="dataSource"/>
<!--结合AOP 实现事务的注入-->
<!--配置事务通知-->
<tx:advice id="txAdvice" transaction-manager="transactionMAnager">
<!--给哪些方法配置事务-->
<!--配置事务的传播特性:new propagation-->
<tx:attributes>
<tx:method name="*"/>
</tx:attributes>
</tx:advice>
</bean>
<!--配置事务的切入-->
<aop:config>
<aop:pointcut id="txPointCut" expression="exection(* com.zhke.mapper.*.*(..))"/>
<aop:advisor advice-ref="txAdvice" pointcut-ref="txPointCut"/>
</aop:config>
3.为什么需要事务
如果不配置事务,可能存在数据提交不一致的情况
如果我们不在 SPRING 中去配置声明式事务,我们需要在代码中手动配置事务
事务在项目的开发中十分重要,设计到数据的一致性和完整性问题。