ssm——mybatis整理
目录
5、一个简单的mybatis框架demo(annotation配置)
文章中所涉及的代码源码下载地址:https://gitee.com/wulinchun/ssm-learning.git
1、mybatis框架概述
mybatis 是一个优秀的基于 java 的持久层框架,它内部封装了 jdbc,使开发者只需要关注sql 语句本身, 而不需要花费精力去处理加载驱动、创建连接、创建 statement 等繁杂的过程。 mybatis 通过 xml 或注解的方式将要执行的各种 statement 配置起来,并通过 java 对象和 statement 中 sql 的动态参数进行映射生成最终执行的 sql 语句,最后由 mybatis 框架执行sql 并将结果映射为 java 对象并返回。 采用ORM思想解决了实体和数据库映射的问题,对 jdbc 进行了封装,屏蔽了jdbc api底层访问细节,使我们不用与 jdbc api 打交道,就可以完成对数据库的持久化操作。 为了我们能够更好掌握框架运行的内部过程,并且有更好的体验,下面我们将从自定义 Mybatis 框架开始来 学习框架。此时我们将会体验框架从无到有的过程体验,也能够很好的综合前面阶段所学的基础。
2、直接使用jdbc连接数据库带来的问题
- 数据库链接创建、释放频繁造成系统资源浪费从而影响系统性能,如果使用数据库链接池可解决此问题。
- Sql 语句在代码中硬编码,造成代码不易维护,实际应用 sql 变化的可能较大,sql 变动需要改变 java 代码。
- 使用 preparedStatement 向占有位符号传参数存在硬编码,因为 sql 语句的 where 条件不一定,可能多也可能少,修改 sql 还要修改代码,系统不易维护。
- 对结果集解析存在硬编码(查询列名),sql 变化导致解析代码变化,系统不易维护,如果能将数据库记 录封装成 pojo 对象解析比较方便。
(projo对象就是简单的java对象,可以理解为实体类与数据库中表一一映射的对象,可以参考https://blog.csdn.net/kobexiaol/article/details/78195856)
3、mybatis连接池
连接池就是用于存储连接对象的一个容器。而容器就是一个集合,且必须是线程安全的,即两个线程不能拿到同一个连接对象。同时还要具备队列的特性:先进先出原则。
使用连接池的好处:避免频繁创建和关闭数据库连接造成的开销,节省系统资源。
3.1、mybatis连接池yml配置
server:
port: 8080
spring:
datasource:
name: erp
url: jdbc:mysql://localhost:3306/ssm?useUnicode=true&characterEncoding=utf-8&useSSL=true&serverTimezone=Hongkong
username: root
password: 123456
driver-class-name: com.mysql.cj.jdbc.Driver
mybatis:
mapper-locations: classpath:mapper/*.xml #注意:一定要对应mapper映射xml文件的所在路径
type-aliases-package: com.mybatis_demo.domain # 注意:对应实体类的路径jetbrains://idea/navigate/reference?project=DataBase_conn&fqn=com.example.demo.Entity
3.2、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">
<!-- mybatis的主配置文件 -->
<configuration>
<properties url="file:///C:/Users/Administrator/Desktop/ssm框架/mybatis_demo/src/main/resources/jdbcConfig.properties">
</properties>
<!--使用typeAliases配置别名,它只能配置domain中类的别名 -->
<typeAliases>
<!-- 用于指定要配置别名的包,当指定之后,该包下的实体类都会注册别名,并且类名就是别名,不再区分大小写-->
<package name="com.mybatis_demo.domain"></package>
</typeAliases>
<!-- 配置环境 -->
<environments default="mysql">
<!-- 配置mysql的环境-->
<environment id="mysql">
<!-- 配置事务的类型-->
<transactionManager type="JDBC"></transactionManager>
<!-- 配置数据源(连接池) -->
<dataSource type="POOLED">
<!-- 配置连接数据库的4个基本信息 -->
<property name="driver" value="${jdbc.driver}"/>
<property name="url" value="${jdbc.url}"/>
<property name="username" value="${jdbc.username}"/>
<property name="password" value="${jdbc.password}"/>
</dataSource>
</environment>
</environments>
<!-- 配置映射文件位置 -->
<mappers>
<package name="com.mybatis_demo.dao"></package>
</mappers>
</configuration>
4、一个简单的mybatis框架demo(XML配置)
建立一个maven工程
eclipse配置maven可参考 https://blog.csdn.net/wcc27857285/article/details/81812304
eclipse建立maven工程可参考 https://jingyan.baidu.com/article/2fb0ba40a2b22b00f2ec5faf.html
4.1、maven项目目录结构如下:
4.2、代码
IUserDao.java
package com.mybatis_demo.dao;
import com.mybatis_demo.domain.User;
import java.util.List;
/**
* @description:
* @author: wu linchun
* @time: 2020/12/29 23:13
*/
public interface IUserDao {
/**
*查询所有
* @return
*/
List<User> findAll();
/**
* 根据id查询
* @param id
* @return
*/
List<User> findByUid(Integer uid);
/**
* 根据name模糊查询
* @param userName
* @return
*/
List<User> findByName(String userName);
/**
* 根据id删除
* @param id
* @return
*/
int deleteUser(Integer uid);
/**
* 添加
* @param user
* @return
*/
int saveUser(User user);
/**
* 修改
* @param user
* @return
*/
int updateUser(User user);
}
User.java
package com.mybatis_demo.domain;
import java.io.Serializable;
import java.sql.Date;
/**
* @description:
* @author: wu linchun
* @time: 2020/12/29 23:08
*/
public class User implements Serializable {
private Integer uid;
private String userName;
private Date userBirthday;
private String userSex;
private String userAddress;
public User() {
}
public User(Integer uid, String userName, Date userBirthday, String userSex, String userAddress) {
this.uid = uid;
this.userName = userName;
this.userBirthday = userBirthday;
this.userSex = userSex;
this.userAddress = userAddress;
}
public Integer getUid() {
return uid;
}
public void setUid(Integer uid) {
this.uid = uid;
}
public String getUserName() {
return userName;
}
public void setUserName(String userName) {
this.userName = userName;
}
public Date getUserBirthday() {
return userBirthday;
}
public void setUserBirthday(Date userBirthday) {
this.userBirthday = userBirthday;
}
public String getUserSex() {
return userSex;
}
public void setUserSex(String userSex) {
this.userSex = userSex;
}
public String getUserAddress() {
return userAddress;
}
public void setUserAddress(String userAddress) {
this.userAddress = userAddress;
}
@Override
public String toString() {
return "User{" +
"uid=" + uid +
", userName='" + userName + '\'' +
", userBirthday=" + userBirthday +
", userSex='" + userSex + '\'' +
", userAddress='" + userAddress + '\'' +
'}';
}
}
IUserDao.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.mybatis_demo.dao.IUserDao">
<!-- 配置 查询结果的列名和实体类的属性名的对应关系 -->
<resultMap id="userMap" type="com.mybatis_demo.domain.User">
<!--property是实体类中的字段,column是数据库表中相应列名 -->
<!-- 主键字段的对应 -->
<id property="uid" column="id"></id>
<!--非主键字段的对应 -->
<result property="userName" column="username"></result>
<result property="userAddress" column="address"></result>
<result property="userSex" column="sex"></result>
<result property="userBirthday" column="birthday"></result>
</resultMap>
<!--配置查询所有 -->
<!-- <select id="findAll" resultType="com.mybatis_demo.domain.User"> select
* from user </select> -->
<select id="findAll" resultMap="userMap">
select id ,username ,address ,sex ,birthday from user;
/*select * from user*/
</select>
<!-- 保存用户 -->
<insert id="saveUser" parameterType="user">
insert into
user(id,username,address,sex,birthday)values(#{uid},#{userName},#{userAddress},#{userSex},#{userBirthday})
</insert>
<!--删除用户 -->
<delete id="deleteUser" parameterType="java.lang.Integer">
delete from user where id=#{uid}
</delete>
<!--根据uid查询用户 -->
<select id="findByUid" parameterType="java.lang.Integer"
resultMap="userMap">
select * from user where id=#{uid}
</select>
<!--根据userName模糊查询 -->
<select id="findByName" parameterType="String"
resultMap="userMap">
select * from user where username like #{userName}
</select>
<update id="updateUser"
parameterType="user">
update user set username=#{userName},address=#{userAddress},sex=#{userSex},birthday=#{userBirthday} where id=#{uid}
</update>
</mapper>
IUserDao.xml中的映射配置需要注意!!!
jdbcConfig.properties
jdbc.driver=com.mysql.jdbc.Driver
#mysql5.7以下版本,则可以直接这样写
#jdbc.url=jdbc:mysql://localhost:3306/ssm
#注意url这里,如果是mysql5.7及以上的要在后面设置useUnicode=true&characterEncoding=UTF-8
#否则会出现中文显示?
jdbc.url=jdbc:mysql://localhost:3306/ssm?useUnicode=true&characterEncoding=UTF-8
jdbc.username=root
jdbc.password=123456
SqlMapConfig.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">
<!-- mybatis的主配置文件 -->
<configuration>
<!-- 配置properties
可以在标签内部配置连接数据库的信息。也可以通过属性引用外部配置文件信息
resource属性: 常用的
用于指定配置文件的位置,是按照类路径的写法来写,并且必须存在于类路径下。
url属性:
是要求按照Url的写法来写地址
URL:Uniform Resource Locator 统一资源定位符。它是可以唯一标识一个资源的位置。
它的写法:
http://localhost:8080/mybatisserver/demo1Servlet
协议 主机 端口 URI
URI:Uniform Resource Identifier 统一资源标识符。它是在应用中可以唯一定位一个资源的。
-->
<properties url="file:///C:/Users/Administrator/Desktop/ssm框架/mybatis_demo/src/main/resources/jdbcConfig.properties">
</properties>
<!--使用typeAliases配置别名,它只能配置domain中类的别名 -->
<typeAliases>
<!-- 用于指定要配置别名的包,当指定之后,该包下的实体类都会注册别名,并且类名就是别名,不再区分大小写-->
<package name="com.mybatis_demo.domain"></package>
</typeAliases>
<!-- 配置环境 -->
<environments default="mysql">
<!-- 配置mysql的环境-->
<environment id="mysql">
<!-- 配置事务的类型-->
<transactionManager type="JDBC"></transactionManager>
<!-- 配置数据源(连接池) -->
<dataSource type="POOLED">
<!-- 配置连接数据库的4个基本信息 -->
<property name="driver" value="${jdbc.driver}"/>
<property name="url" value="${jdbc.url}"/>
<property name="username" value="${jdbc.username}"/>
<property name="password" value="${jdbc.password}"/>
</dataSource>
</environment>
</environments>
<!-- 配置映射文件位置 -->
<mappers>
<package name="com.mybatis_demo.dao"></package>
</mappers>
</configuration>
MybatisTest.java
package com.mybatis_demo.test;
import com.mybatis_demo.dao.IUserDao;
import com.mybatis_demo.domain.User;
import org.apache.ibatis.io.Resources;
import org.apache.ibatis.session.SqlSession;
import org.apache.ibatis.session.SqlSessionFactory;
import org.apache.ibatis.session.SqlSessionFactoryBuilder;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;
import java.io.InputStream;
import java.sql.Date;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.List;
/**
* @description:
* @author: wu linchun
* @time: 2020/12/30 22:25
*/
public class MybatisTest {
private InputStream in;
private SqlSession sqlSession;
private IUserDao userDao;
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
@Before//用于在测试方法执行之前执行
public void init() throws Exception {
//1.读取配置文件,生成字节输入流
in = Resources.getResourceAsStream("SqlMapConfig.xml");
//2.获取SqlSessionFactory
SqlSessionFactory factory = new SqlSessionFactoryBuilder().build(in);
//3.获取SqlSession对象
sqlSession = factory.openSession();
//4.获取dao的代理对象
userDao = sqlSession.getMapper(IUserDao.class);
}
@After//用于在测试方法执行之后执行
public void destroy() throws Exception {
//提交事务
sqlSession.commit();
//6.释放资源
sqlSession.close();
in.close();
}
/**
* 测试查询所有
*/
@Test
public void testFindAll(){
List<User> userList = userDao.findAll();
for(User user : userList){
System.out.println(user);
}
}
/**
* 测试添加用户
* @throws ParseException
*/
@Test
public void testSaveUser() throws ParseException {
java.util.Date bir=sdf.parse("2020-01-04");
java.sql.Date bir_sql=new java.sql.Date(bir.getTime());
User user=new User(11,"test11", bir_sql,"男","testAddress");
userDao.saveUser(user);
}
/**
* 测试删除用户
*/
@Test
public void testDeleteUser(){
userDao.deleteUser(7);
}
/**
* 测试根据uid查找
*/
@Test
public void testFindByUid(){
List<User> userList = userDao.findByUid(6);
for(User user : userList){
System.out.println(user);
}
}
/**
* 测试根据userName模糊查询
*/
@Test
public void testFindByName(){
List<User> userList=userDao.findByName("%t%");
for(User user : userList){
System.out.println(user);
}
}
/**
* 测试修改
* @throws ParseException
*/
@Test
public void testUpdateUser() throws ParseException {
java.util.Date bir=sdf.parse("2020-01-04");
java.sql.Date bir_sql=new java.sql.Date(bir.getTime());
User user=new User(5,"test5",bir_sql,"男","testAddress");
userDao.updateUser(user);
}
/**
* 入门案例
* @param args
*/
/*public static void main(String[] args) throws Exception {
//1.读取配置文件D:\学习资料\后端\ssm代码\mybatis_demo\src\main\resources\SqlMapConfig.xml
InputStream in = Resources.getResourceAsStream("SqlMapConfig.xml");
//2.创建SqlSessionFactory工厂
SqlSessionFactoryBuilder builder = new SqlSessionFactoryBuilder();
SqlSessionFactory factory = builder.build(in);
//3.使用工厂生产SqlSession对象
SqlSession session = factory.openSession();
//4.使用SqlSession创建Dao接口的代理对象
IUserDao userDao = session.getMapper(IUserDao.class);
//5.使用代理对象执行方法
List<User> users = userDao.findAll();
for(User user : users){
System.out.println(user);
}
//6.释放资源
session.close();
in.close();
}*/
}
4.3、mybatis代码架构分析
5、一个简单的mybatis框架demo(annotation配置)
5.1、maven项目目录结构如下
5.2、mybatis注解使用
IUserDao.java
package com.mybatis_demo_ann.dao;
import com.mybatis_demo_ann.domain.User;
import org.apache.ibatis.annotations.Select;
import org.apache.ibatis.annotations.Update;
import org.apache.ibatis.annotations.Delete;
import org.apache.ibatis.annotations.Insert;
import org.apache.ibatis.annotations.Result;
import org.apache.ibatis.annotations.Results;
import java.util.List;
/**
* @description:
* @author: wu linchun
* @time: 2020/12/29 23:08
*/
public interface IUserDao {
/**
* 查询所有操作
*
* @return
*/
@Select("select * from user")
//映射转换,将实体类中的字段与数据库表的列名一一对应起来
@Results(id = "userMap", value = {
// id字段默认为false,表示不是主键
// column表示数据库表字段,property表示实体类属性名。
@Result(id = true, column = "id", property = "uid"), @Result(column = "username", property = "userName"),
@Result(column = "birthday", property = "userBirthday"), @Result(column = "sex", property = "userSex"),
@Result(column = "address", property = "userAddress"), })
List<User> findAll();
/**
* 插入操作
* @param user
* @return
*/
@Insert("insert into user (id,username,birthday,sex,address) values (#{uid},#{userName},#{userBirthday},#{userSex},#{userAddress})")
@Results(id = "userMap", value = {
// id字段默认为false,表示不是主键
// column表示数据库表字段,property表示实体类属性名。
@Result(id = true, column = "id", property = "uid"), @Result(column = "username", property = "userName"),
@Result(column = "birthday", property = "userBirthday"), @Result(column = "sex", property = "userSex"),
@Result(column = "address", property = "userAddress"), })
int saveUser(User user);
/**
* 更新操作
* @param user
* @return
*/
@Update("update user set username=#{userName},birthday=#{userBirthday},sex=#{userSex},address=#{userAddress} where id=#{uid}")
@Results(id = "userMap", value = {
// id字段默认为false,表示不是主键
// column表示数据库表字段,property表示实体类属性名。
@Result(id = true, column = "id", property = "uid"), @Result(column = "username", property = "userName"),
@Result(column = "birthday", property = "userBirthday"), @Result(column = "sex", property = "userSex"),
@Result(column = "address", property = "userAddress"), })
int updateUser(User user);
/**
* 模糊查询
* @param username
* @return
*/
@Select("select * from user where username like #{username}")
List<User> findByName(String username);
/**
* 删除用户
* @param id
* @return
*/
@Delete("delete from user where id=#{id}")
int deleteUser(int id);
}
注意!!!使用注解开发时,要求实体类数据中属性必须和 mysql 中的属性名一致(除非你进行映射转换的配置),可以忽略大小写。
可参考文章:https://blog.csdn.net/guan_sir/article/details/104561362 https://blog.csdn.net/weixin_44149454/article/details/90373036
6、mybatis总结
7、参考资料
- https://www.bilibili.com/video/BV1mE411X7yp?from=search
- https://blog.csdn.net/IT_CREATE/article/details/86564305
- https://www.cnblogs.com/arrows/p/10531808.html
- https://blog.csdn.net/dwenxue/article/details/82351120
- https://blog.csdn.net/writedew/article/details/94459863
- https://blog.csdn.net/although1/article/details/103719383
- https://www.cnblogs.com/king0207/p/13578912.html
- https://blog.csdn.net/weixin_44149454/article/details/90373036
- https://blog.csdn.net/guan_sir/article/details/104561362
- https://blog.csdn.net/chpllp/article/details/81945600
- https://www.cnblogs.com/jpfss/p/7681420.html
- https://blog.csdn.net/sinat_24230393/article/details/97006106
- https://www.cnblogs.com/jtlgb/p/8780594.html
- https://bbs.csdn.net/topics/380189849
- https://blog.csdn.net/qq_34902437/article/details/105041210
- https://jingyan.baidu.com/article/2fb0ba40a2b22b00f2ec5faf.html
- https://blog.csdn.net/zj420964597/article/details/84564440
- https://bbs.csdn.net/topics/391027203?list=lz
- https://blog.csdn.net/cc41798520101/article/details/52411401
- https://blog.csdn.net/qq_40645822/article/details/101844675
- https://developer.aliyun.com/article/619693
- https://blog.csdn.net/weixin_33716557/article/details/92423934
- https://www.cnblogs.com/softidea/p/5773191.html
- https://blog.csdn.net/csdn1428208016/article/details/85243863
- https://blog.csdn.net/u013412772/article/details/73648537
- https://www.itdaan.com/blog/2008/08/20/8aa0deb865221baa90f4259603ad2f64.html
- https://www.cnblogs.com/chongaizhen/p/11170595.html
ssm——mybatis整理的更多相关文章
- ssm知识点整理
第1章 resultType和resultMap的区别是什么? MyBatis中在查询进行select映射的时候,返回类型可以用resultType,也可以用resultMap,resultType ...
- SSM Mybatis将新增数据写入数据库时出现的500状态码:Error updating database.的可能
关于maven下ssm整合的项目推荐这篇博客:https://www.cnblogs.com/yiye/p/5969157.html 今日在ssm下的将新增数据写回数据库时遇到不少的问题,现作记录 如 ...
- Mybatis整理_01
Mybatis专题 Mybaits介绍 Mybatis是一个持久化框架,它有不同语言的版本,比如.NET和Java都有Mybatis对应的类库:它有大多数ORM框架都具有的功能,比如自定义的SQL语句 ...
- [原] MyBatis 整理
花了一上午的时间,先整理一个脑图.
- Mybatis整理系列(01)————传入参数方式以及#{}与${}的区别
一.在MyBatis的select.insert.update.delete这些元素中都提到了parameterType这个属性.MyBatis现在可以使用的parameterType有基本数据类型和 ...
- SSM - Mybatis SQL映射文件
MyBatis 真正的力量是在映射语句中.和对等功能的jdbc来比价,映射文件节省很多的代码量.MyBatis的构建就是聚焦于sql的. sql映射文件有如下几个顶级元素:(按顺序) cache配置给 ...
- mybatis整理笔记
以下是idea2018辑编器 新建 Maven工程 1 file ->new ->project 新建后编程器在右下角加载插件.,这个时候需要会儿, 加载好后,软件目录会多一个ja包 ...
- SSM+MyBatis框架详解
- 【Mybatis架构】 延迟加载
在上一篇博客中,我们提到过有关于Mybatis输出映射中resultMap能够实现延迟加载的事,然而真的是所有的resultMap都能实现延迟加载还是咋地啊?现在我们就来对那一句话做一下阐述和实例说明 ...
- 【Mybatis框架】查询缓存(二级缓存)
继上一篇博客,我们讲述了mybatis的一级缓存,接下来,我们来学习一下mybatis的二级缓存 博客链接地址: http://blog.csdn.NET/liweizhong193516/artic ...
随机推荐
- web share api 分享
概述 Navigator.share() 方法通过调用本机的共享机制作为 Web Share API 的一部分.如果不支持 Web Share API,则此方法为 undefined. 此项功能仅在 ...
- golang中的socket编程
0.1.索引 https://waterflow.link/articles/1664591292871 1.tcp的3次握手(建立连接) 客户端的协议栈向服务器端发送了 SYN 包,并告诉服务器端当 ...
- JavaScript函数式编程之函子
函子(Functor) 函子是一个特殊的容器,通过一个普通对象来实现,该对象具有map方法,map方法可以运行一个函数对值进行处理(变形关系),容器包含值和值变形关系(这个变形关系就是函数).函数式编 ...
- 【原创】i.MXRT J-Flash烧写算法使能eFuse熔丝位写入
临近年底,终于又憋了一篇文章出来,本来年初的时候是有计划把去年总结的一些东西整理下发布出来的,结果还是被工作和生活上各种琐事给耽搁了.哎,今年刚过了自己35岁的生日,眼瞅着这个人生节点 ...
- MySQL的下载、安装、配置
下载 官方下载地址:下载地址: 找到免费社区版本 进入到下面页面的时候,下载对应的MySQL,我这里选择Windows. 点击Download ,如下图: 后面他会提示你登录注册啥的,我们选择不需要, ...
- Python基础部分:9、数据的类型和内置方法
目录 一.数据类型内置方法理论 1.什么是数据内置方法 2.如何调用数据内置方法 二.整型(int)内置方法与操作 1.类型转换 2.进制数转换 三.浮点型(float)内置方法与操作 1.类型转换 ...
- Day16自定义异常
package com.exception.demo02;//自定义的异常类public class MyException extends Exception{ //传递数字>10抛出异常 p ...
- .net 温故知新:【9】.NET日志记录 ILogger使用和原理
日志 日志作为我们程序记录的"黑匣子"是不论什么系统都会使用到的,比如我们经常使用的log4net就是第三方日志记录提供程序.NET 支持使用各种内置和第三方日志记录提供程序的日志 ...
- <四>构造函数初始化列表
示例代码1 点击查看代码 class CDate{ public: CDate(int _year,int _month, int _day){ this->year=_year; this-& ...
- perl中 use strict会出现“requires explicit package name”错误
转载 perl中use strict的用法 如果你使用 use strict 的话,它会强迫你用 my 声明变量,否则将会报上述错误.