2 示例1
2.1 创建
2.1.1 创建项目
新建Maven项目,然后直接下一步。
展开三角填写信息,最后一行版本不填,直接用默认的。然后完成。
进度条走完后,点文件,设置,展开编辑器,在点文件和代码模板。
然后先点加号,在输入名称和扩展名,再在下面黑框里输入以下代码。下面框全部勾选。
<?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=""> </mapper>步骤同上,但是只勾选第一个框。
上面的操作只是保存到模版里,还需要在项目中创建。
这个是主配置文件,在resources目录下创建SqlMapConfig.xml的配置文件(其实名称可以任意,具体解释见11),导入对应的约束,编写主配置文件。
<?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> <environments default="mysql"> <environment id="mysql"> <!--配置事务的类型,使用本地事务策略--> <transactionManager type="JDBC"></transactionManager> <!--是否使用连接池 POOLED表示使用链接池,UNPOOLED表示不使用连接池--> <dataSource type="POOLED"> <property name="driver" value="com.mysql.jdbc.Driver"/> <property name="url" value="jdbc:mysql://localhost:3306/mybatis_demo"/> <property name="username" value="root"/> <property name="password" value="036520"/> </dataSource> </environment> </environments> <!-- 加载映射的配置文件 --> <mappers> <mapper resource="mapper/UserDao.xml"></mapper> </mappers> </configuration>2.1.2 创建数据库和表
新建表
CREATE TABLE `user` ( `id` int(11) NOT NULL auto_increment, `username` varchar(32) NOT NULL COMMENT '用户名称', `birthday` datetime default NULL COMMENT '生日', `sex` char(1) default NULL COMMENT '性别', `address` varchar(256) default NULL COMMENT '地址', PRIMARY KEY (`id`) ) ENGINE=InnoDB DEFAULT CHARSET=utf8; insert into `user`(`id`,`username`,`birthday`,`sex`,`address`) values (1,'老王','2018-02-27 17:47:08','男','北京'),(2,'熊大','2018-03-02 15:09:37','女','上海'),(3,'熊二','2018-03-04 11:34:34','女','深圳'),(4,'光头强','2018-03-04 12:04:06','男','广州');2.1.3 修改包的显示方式。
2.1.4 创建包等
2.1.4.1 entity包
- 对应关系:实体类与数据库中的表存在一一对应关系,实体类的属性对应表中的字段 。例如数据库中有一张 user 表,包含 id、username、password 等字段,那么在 entity 包下的 User 实体类就会有与之对应的属性,如 private int id;、private String username;、private String password; 。通过 MyBatis 的映射配置,可实现实体类与表之间的数据交互,方便进行增删改查操作。
- 数据持久化:当执行数据库插入操作时,将实体类对象的属性值对应插入到表的相应字段中;查询操作则是将表中的记录数据映射填充到实体类对象的属性上 。比如执行 SELECT * FROM user WHERE id = 1 语句后,查询结果会被封装成 User 实体类对象返回。
package com.lsl.entity; import java.util.Date; /** * 对应数据库中的User表 */ public class User { private Integer id; private String username; private Date birthday; private String sex; private String address; private String password; private Integer pageSize; private Integer pageStart; public Integer getPageSize() { return pageSize; } public void setPageSize(Integer pageSize) { this.pageSize = pageSize; } public Integer getPageStart() { return pageStart; } public void setPageStart(Integer pageStart) { this.pageStart = pageStart; } public User() { } public User(String username, Date birthday, String sex, String address) { this.username = username; this.birthday = birthday; this.sex = sex; this.address = address; } public String getSex() { return sex; } public void setSex(String sex) { this.sex = sex; } public String getPassword() { return password; } public void setPassword(String password) { this.password = password; } public String getAddress() { return address; } public void setAddress(String address) { this.address = address; } public String getUsername() { return username; } public void setUsername(String username) { this.username = username; } public Date getBirthday() { return birthday; } public void setBirthday(Date birthday) { this.birthday = birthday; } public Integer getId() { return id; } public void setId(Integer id) { this.id = id; } @Override public String toString() { return "User{" + "id=" + id + ", username='" + username + '\'' + ", birthday=" + birthday + ", sex='" + sex + '\'' + ", address='" + address + '\'' + ", password='" + password + '\'' + '}'; } }2.1.4.2 dao包和mapper目录
- dao 层(数据访问对象层,Data Access Object):在软件架构中,dao 层主要负责与数据库进行交互,执行数据的增删改查操作 。它屏蔽了具体的数据库操作细节,为上层业务逻辑提供统一的数据访问接口。通过 dao 层,业务层可以不用关心底层是 MySQL、Oracle 等哪种数据库,以及具体的 SQL 语句如何编写和执行等细节。
- mapper:在基于 MyBatis 框架的项目中,mapper 通常是指存放 SQL 映射文件的目录。MyBatis 是一种将 SQL 语句从 Java 代码中分离出来的持久层框架,mapper 目录下的 XML 文件(或使用注解方式)定义了具体的 SQL 语句,比如 SELECT、INSERT、UPDATE、DELETE 等操作,并且将这些 SQL 语句与 dao 层的接口方法进行映射关联。
- 创建目录和文件
- 在项目中创建 mapper 目录:在资源目录(resources)下新建一个名为 mapper 的目录,后续所有与 SQL 相关的 XML 文件都将存放在这个目录下 。比如要对用户表进行操作,就可以在这个目录下创建一个 UserMapper.xml 文件(具体操作见下面),在其中编写针对用户表的 SQL 语句,像查询用户列表的 SELECT * FROM user 语句等。
- 在 dao 层创建接口:在 dao 包(这里是 com.qcby.dao)下新建一个 UserDao 接口 。这个接口定义了一系列对用户数据操作的抽象方法,比如 List selectAllUsers()(查询所有用户) 、User selectUserById(int id)(根据用户 ID 查询用户)等。它并不包含具体的实现逻辑,具体的实现逻辑是通过与 mapper 目录下的 XML 文件进行映射,由 MyBatis 框架来动态生成实现类并执行 SQL 语句。
- 创建 sqlMapConfig.xml 文件:在 resources 目录下创建一个SqlMapConfig,名为 SqlMapConfig.xml 的文件,它是 MyBatis 的全局配置文件 。在这个文件中,可以配置 MyBatis 的一些全局属性,如数据库连接信息(数据源配置)、事务管理方式、类型别名、mapper 映射文件的位置等。例如,通过配置 来告诉 MyBatis 到 mapper 目录下加载 UserMapper.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> <settings> <!--设置mybatis输出日志--> <!--logImpl:表示对日志的控制--> <!--STDOUT_LOGGING:将日志输出到控制台上--> <setting name="logImpl" value="STDOUT_LOGGING"/> </settings> <environments default="mysql"> <environment id="mysql"> <!--配置事务的类型,使用本地事务策略--> <transactionManager type="JDBC"></transactionManager> <!--是否使用连接池 POOLED表示使用链接池,UNPOOLED表示不使用连接池--> <dataSource type="POOLED"> <property name="driver" value="com.mysql.jdbc.Driver"/> <property name="url" value="jdbc:mysql://localhost:3306/mybatis_demo"/> <property name="username" value="root"/> <property name="password" value="036520"/> </dataSource> </environment> </environments> <mappers> <mapper resource="mapper/UserMapper.xml"></mapper> </mappers> </configuration>2.1.5 在pom.xml中导入相关依赖
- 引入MyBatis的3.4.5的版本的坐标
- 引入MySQL驱动的jar包,5.1.6版本
- 引入Junit单元测试的jar
- 引入log4j的jar包,1.2.12版本(需要引入log4j.properties的配置文件,该配置文件的具体解释见框架集成 ssm 4.2)
<?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>com.lsl</groupId> <artifactId>MyBatisDemoTest</artifactId> <version>1.0-SNAPSHOT</version> <properties> <maven.compiler.source>8</maven.compiler.source> <maven.compiler.target>8</maven.compiler.target> </properties> <dependencies> <!--mybatis核心包--> <dependency> <groupId>org.mybatis</groupId> <artifactId>mybatis</artifactId> <version>3.4.5</version> </dependency> <!--mysql驱动包--> <dependency> <groupId>mysql</groupId> <artifactId>mysql-connector-java</artifactId> <version>8.0.33</version> </dependency> <!-- 单元测试 --> <dependency> <groupId>junit</groupId> <artifactId>junit</artifactId> <version>4.10</version> </dependency> <!-- 日志 --> <dependency> <groupId>log4j</groupId> <artifactId>log4j</artifactId> <version>1.2.17</version> </dependency> </dependencies> </project>随后点右上角的m标志。
如果没有就点最右边的Maven,然后再点红框。
进度条走完就可以继续写代码了。
如果此时SqlMapConfig.xml第四行代码报错。如下图。只用把这个文件删了,重新再建一个即可。
2.2 代码
2.2.1 UserMapper.xml
2.2.1.1 初始配置
在UserMapper.xml中的第四行代码的namespace加上com.lsl.dao.UserDao。目的是把UserMapper.xml映射到UserDao中,具体解释如下。
文件命名及对应关系:UserMapper.xml 这个文件命名中的 User 与 UserDao 接口以及业务中的 User 实体类相对应 。在 UserMapper.xml 文件中,通过 (这个叫做名称空间)来指定该映射文件与 UserDao 接口关联,然后在文件中定义的 SQL 语句就会与 UserDao 接口中的方法进行对应,当在业务层调用 UserDao 接口的方法时,MyBatis 框架会根据这种映射关系找到对应的 SQL 语句并执行。
<?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.lsl.dao.UserDao"> </mapper>2.2.1.2 第一个查询语句
- 使用标签定义查询语句,id属性需与接口方法名完全一致(如findAll)。resultType指定返回值类型(com.lsl.entity.User),MyBatis 自动将查询结果映射为实体对象或集合。示例 SQL:select * from user,查询所有用户数据,返回List集合。
<?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.lsl.dao.UserDao"> <!-- id:方法名称 --> <!-- resultType:数据返回的类型 --> <select id="findAll" resultType="com.lsl.entity.User"> select * from user; </select> </mapper>2.2.2 UserDao.java
接口方法与映射文件的对应关系
接口方法名需与映射文件中 SQL 标签的id一致(如findAll()对应)。
返回值类型需与resultType匹配:List对应查询多条数据,User对应单条数据。
接口方法默认使用public abstract修饰(可省略),符合 Java 接口规范。
package com.lsl.dao; import com.lsl.entity.User; import org.apache.ibatis.annotations.Param; import java.util.List; public interface UserDao { public abstract List<User> findAll(); }2.2.3 UserTest.java
在test下的java包中新建一个UserTest的类。
测试方法(@Test)执行流程
调用接口方法(如userDao.findAll()),MyBatis 自动匹配映射文件中的 SQL 并执行。
处理返回结果:通过for-each循环遍历List,打印实体对象信息。
import com.lsl.dao.UserDao; import com.lsl.entity.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.IOException; import java.io.InputStream; import java.util.Arrays; import java.util.Date; import java.util.List; public class UserTest { private InputStream in = null; private SqlSession session = null; private UserDao userDao = null; @Before //前置通知, 在方法执行之前执行 public void init() throws IOException { //加载主配置文件,目的是为了构建SqlSessionFactory对象 in = Resources.getResourceAsStream("SqlMapConfig.xml"); //创建SqlSessionFactory对象 SqlSessionFactory factory = new SqlSessionFactoryBuilder().build(in); //通过SqlSessionFactory工厂对象创建SqlSesssion对象 session = factory.openSession(); //通过Session创建UserDao接口代理对象 userDao = session.getMapper(UserDao.class); } @After //@After: 后置通知, 在方法执行之后执行 。 public void destory() throws IOException { //释放资源 if (session != null) { // 增加null检查 session.close(); } in.close(); } @Test public void aaa(){ List<User> users = userDao.findAll(); for (User user: users ) { System.out.println(user.toString()); } }2.2.4 test方法的写法
- 基于 Spring 注解的 AOP 方式
- 接口代理方式
/** * 测试查询所有的方法 * @throws Exception */ @Test public void testFindAll() throws Exception { // 加载主配置文件,目的是构建SqlSessionFactory的对象 InputStream in = Resources.getResourceAsStream("SqlMapConfig.xml"); // 创建SqlSessionFactory对象 SqlSessionFactory factory = new SqlSessionFactoryBuilder().build(in); // 使用SqlSessionFactory工厂对象创建SqlSession对象 SqlSession session = factory.openSession(); // 通过session创建UserMapper接口的代理对象 UserDao mapper = session.getMapper(UserDao.class); // 调用查询所有的方法 List<User> list = mapper.findAll(); // 遍历集合 for (User user : list) { System.out.println(user); } // 释放资源 session.close(); in.close(); }- 字符串标识方式(命名空间 + 方法名)
@Test public void run2() throws Exception { // 加载配置文件 InputStream inputStream = Resources.getResourceAsStream("SqlMapConfig.xml"); // 构建SqlSessionFactory对象 SqlSessionFactory factory = new SqlSessionFactoryBuilder().build(inputStream); // 获取到session对象 SqlSession session = factory.openSession(); // 查询所有的数据 List<User> list = session.selectList("com.qcby.dao.UserDao.findAll"); // 变量集合 for (User user : list) { System.out.println(user); } // 关闭资源 session.close(); inputStream.close(); }