当前位置: 首页 > news >正文

网站开发需求分析报告怎样做分类网站

网站开发需求分析报告,怎样做分类网站,燕郊房价2023年最新房价走势,网站制作公司有哪些声明#xff1a;该内容来源于动力节点#xff0c;本人在学习mybatis过程中参考该内容#xff0c;并自己做了部分笔记#xff0c;但个人觉得本人做的笔记不如动力节点做的好#xff0c;故使用动力节点的笔记作为后续mybatis的复习。 一、MyBatis概述 1.1 框架 在文献中看…声明该内容来源于动力节点本人在学习mybatis过程中参考该内容并自己做了部分笔记但个人觉得本人做的笔记不如动力节点做的好故使用动力节点的笔记作为后续mybatis的复习。 一、MyBatis概述 1.1 框架 在文献中看到的framework被翻译为框架Java常用框架 SSM三大框架Spring SpringMVC MyBatisSpringBootSpringCloud等。。 框架其实就是对通用代码的封装提前写好了一堆接口和类我们可以在做项目的时候直接引入这些接口和类引入框架基于这些现有的接口和类进行开发可以大大提高开发效率。框架一般都以jar包的形式存在。(jar包中有class文件以及各种配置文件等。)SSM三大框架的学习顺序MyBatis、Spring、SpringMVC仅仅是建议 1.2 三层架构 表现层UI直接跟前端打交互一是接收前端ajax请求二是返回json数据给前端业务逻辑层BLL一是处理表现层转发过来的前端请求也就是具体业务二是将从持久层获取的数据返回到表现层。数据访问层DAL直接操作数据库完成CRUD并将获得的数据返回到上一层也就是业务逻辑层。Java持久层框架 MyBatisHibernate实现了JPA规范jOOQGuzzSpring Data实现了JPA规范ActiveJDBC… 1.3 JDBC不足 示例代码1 // ...... // sql语句写死在java程序中 String sql insert into t_user(id,idCard,username,password,birth,gender,email,city,street,zipcode,phone,grade) values(?,?,?,?,?,?,?,?,?,?,?,?); PreparedStatement ps conn.prepareStatement(sql); // 繁琐的赋值思考一下这种有规律的代码能不能通过反射机制来做自动化。 ps.setString(1, 1); ps.setString(2, 123456789); ps.setString(3, zhangsan); ps.setString(4, 123456); ps.setString(5, 1980-10-11); ps.setString(6, 男); ps.setString(7, zhangsan126.com); ps.setString(8, 北京); ps.setString(9, 大兴区凉水河二街); ps.setString(10, 1000000); ps.setString(11, 16398574152); ps.setString(12, A); // 执行SQL int count ps.executeUpdate(); // ......示例代码2 // ...... // sql语句写死在java程序中 String sql select id,idCard,username,password,birth,gender,email,city,street,zipcode,phone,grade from t_user; PreparedStatement ps conn.prepareStatement(sql); ResultSet rs ps.executeQuery(); ListUser userList new ArrayList(); // 思考以下循环中的所有代码是否可以使用反射进行自动化封装。 while(rs.next()){// 获取数据String id rs.getString(id);String idCard rs.getString(idCard);String username rs.getString(username);String password rs.getString(password);String birth rs.getString(birth);String gender rs.getString(gender);String email rs.getString(email);String city rs.getString(city);String street rs.getString(street);String zipcode rs.getString(zipcode);String phone rs.getString(phone);String grade rs.getString(grade);// 创建对象User user new User();// 给对象属性赋值user.setId(id);user.setIdCard(idCard);user.setUsername(username);user.setPassword(password);user.setBirth(birth);user.setGender(gender);user.setEmail(email);user.setCity(city);user.setStreet(street);user.setZipcode(zipcode);user.setPhone(phone);user.setGrade(grade);// 添加到集合userList.add(user); } // ......JDBC不足 SQL语句写死在Java程序中不灵活。改SQL的话就要改Java代码。违背开闭原则OCP。给?传值是繁琐的。能不能自动化将结果集封装成Java对象是繁琐的。能不能自动化 1.4 了解MyBatis MyBatis本质上就是对JDBC的封装通过MyBatis完成CRUD。MyBatis在三层架构中负责持久层的属于持久层框架。MyBatis的发展历程【引用百度百科】 MyBatis本是apache的一个开源项目iBatis2010年这个项目由apache software foundation迁移到了google code并且改名为MyBatis。2013年11月迁移到Github。iBATIS一词来源于“internet”和“abatis”的组合是一个基于Java的持久层框架。iBATIS提供的持久层框架包括SQL Maps和Data Access ObjectsDAOs。 打开mybatis代码可以看到它的包结构中包含ibatis ORM对象关系映射 OObjectJava虚拟机中的Java对象RRelational关系型数据库MMapping将Java虚拟机中的Java对象映射到数据库表中一行记录或是将数据库表中一行记录映射成Java虚拟机中的一个Java对象。ORM图示 - MyBatis属于半自动化ORM框架。Hibernate属于全自动化的ORM框架。 MyBatis框架特点 支持定制化 SQL、存储过程、基本映射以及高级映射避免了几乎所有的 JDBC 代码中手动设置参数以及获取结果集支持XML开发也支持注解式开发。【为了保证sql语句的灵活所以mybatis大部分是采用XML方式开发。】将接口和 Java 的 POJOs(Plain Ordinary Java Object简单普通的Java对象)映射成数据库中的记录体积小好学两个jar包两个XML配置文件。完全做到sql解耦合。提供了基本映射标签。提供了高级映射标签。提供了XML标签支持动态SQL的编写。… 二、MyBatis入门程序 只要你会JDBCMyBatis就可以学。 2.1 版本 软件版本 IntelliJ IDEA2022.1.4Navicat for MySQL16.0.14MySQL数据库8.0.30 组件版本 MySQL驱动8.0.30MyBatis3.5.10JDKJava17JUnit4.13.2Logback1.2.11 2.2 MyBatis下载 从github上下载地址https://github.com/mybatis/mybatis-3 将框架以及框架的源码都下载下来下载框架后解压打开mybatis目录 通过以上解压可以看到框架一般都是以jar包的形式存在。我们的mybatis课程使用maven所以这个jar我们不需要。官方手册需要。 2.3 MyBatis入门程序开发步骤 写代码前准备 准备数据库表汽车表t_car字段包括 id主键自增【bigint】car_num汽车编号【varchar】brand品牌【varchar】guide_price厂家指导价【decimal类型专门为财务数据准备的类型】produce_time生产时间【char年月日即可10个长度‘2022-10-11’】car_type汽车类型燃油车、电车、氢能源【varchar】 使用navicat for mysql工具建表 使用navicat for mysql工具向t_car表中插入两条数据如下 - - 创建Project建议创建Empty Project设置Java版本以及编译版本等。 设置IDEA的maven 创建Module普通的Maven Java模块 步骤1打包方式jar不需要war因为mybatis封装的是jdbc。 groupIdcom.powernode/groupId artifactIdmybatis-001-introduction/artifactId version1.0-SNAPSHOT/version packagingjar/packaging步骤2引入依赖mybatis依赖 mysql驱动依赖 !--mybatis核心依赖-- dependencygroupIdorg.mybatis/groupIdartifactIdmybatis/artifactIdversion3.5.10/version /dependency !--mysql驱动依赖-- dependencygroupIdmysql/groupIdartifactIdmysql-connector-java/artifactIdversion8.0.30/version /dependency步骤3在resources根目录下新建mybatis-config.xml配置文件可以参考mybatis手册拷贝 ?xml version1.0 encodingUTF-8 ? !DOCTYPE configurationPUBLIC -//mybatis.org//DTD Config 3.0//ENhttp://mybatis.org/dtd/mybatis-3-config.dtd configurationenvironments defaultdevelopmentenvironment iddevelopmenttransactionManager typeJDBC/dataSource typePOOLEDproperty namedriver valuecom.mysql.cj.jdbc.Driver/property nameurl valuejdbc:mysql://localhost:3306/powernode/property nameusername valueroot/property namepassword valueroot//dataSource/environment/environmentsmappers!--sql映射文件创建好之后需要将该文件路径配置到这里--mapper resource//mappers /configuration注意1mybatis核心配置文件的文件名不一定是mybatis-config.xml可以是其它名字。 注意2mybatis核心配置文件存放的位置也可以随意。这里选择放在resources根下相当于放到了类的根路径下。 步骤4在resources根目录下新建CarMapper.xml配置文件可以参考mybatis手册拷贝 ?xml version1.0 encodingUTF-8 ? !DOCTYPE mapperPUBLIC -//mybatis.org//DTD Mapper 3.0//ENhttp://mybatis.org/dtd/mybatis-3-mapper.dtd !--namespace先随意写一个-- mapper namespacecar!--insert sql保存一个汽车信息--insert idinsertCarinsert into t_car(id,car_num,brand,guide_price,produce_time,car_type) values(null,102,丰田mirai,40.30,2014-10-05,氢能源)/insert /mapper注意1sql语句最后结尾可以不写“;” 注意2CarMapper.xml文件的名字不是固定的。可以使用其它名字。 注意3CarMapper.xml文件的位置也是随意的。这里选择放在resources根下相当于放到了类的根路径下。 注意4将CarMapper.xml文件路径配置到mybatis-config.xml mapper resourceCarMapper.xml/步骤5编写MyBatisIntroductionTest代码 package com.powernode.mybatis;import org.apache.ibatis.session.SqlSession; import org.apache.ibatis.session.SqlSessionFactory; import org.apache.ibatis.session.SqlSessionFactoryBuilder;import java.io.InputStream;/*** MyBatis入门程序* author 老杜* since 1.0* version 1.0*/ public class MyBatisIntroductionTest {public static void main(String[] args) {// 1. 创建SqlSessionFactoryBuilder对象SqlSessionFactoryBuilder sqlSessionFactoryBuilder new SqlSessionFactoryBuilder();// 2. 创建SqlSessionFactory对象InputStream is Thread.currentThread().getContextClassLoader().getResourceAsStream(mybatis-config.xml);SqlSessionFactory sqlSessionFactory sqlSessionFactoryBuilder.build(is);// 3. 创建SqlSession对象SqlSession sqlSession sqlSessionFactory.openSession();// 4. 执行sqlint count sqlSession.insert(insertCar); // 这个insertCar必须是sql的idSystem.out.println(插入几条数据 count);// 5. 提交mybatis默认采用的事务管理器是JDBC默认是不提交的需要手动提交。sqlSession.commit();// 6. 关闭资源只关闭是不会提交的sqlSession.close();} }注意1默认采用的事务管理器是JDBC。JDBC事务默认是不提交的需要手动提交。 步骤6运行程序查看运行结果以及数据库表中的数据 2.4 关于MyBatis核心配置文件的名字和路径详解 核心配置文件的名字是随意的因为以下的代码 // 文件名是出现在程序中的文件名如果修改了对应这里的java程序也改一下就行了。 InputStream is Thread.currentThread().getContextClassLoader().getResourceAsStream(mybatis-config.xml);核心配置文件必须放到resources下吗放到D盘根目录下可以吗测试一下 将mybatis-config.xml文件拷贝一份放到D盘根下然后编写以下程序 package com.powernode.mybatis;import org.apache.ibatis.session.SqlSession; import org.apache.ibatis.session.SqlSessionFactory; import org.apache.ibatis.session.SqlSessionFactoryBuilder;import java.io.FileInputStream; import java.io.InputStream;/*** 测试mybatis核心配置文件路径问题* author 老杜* since 1.0* version 1.0*/ public class MyBatisConfigFilePath {public static void main(String[] args) throws Exception{// 1. 创建SqlSessionFactoryBuilder对象SqlSessionFactoryBuilder sqlSessionFactoryBuilder new SqlSessionFactoryBuilder();// 2. 创建SqlSessionFactory对象// 这只是一个输入流可以自己new。InputStream is new FileInputStream(D:/mybatis-config.xml); SqlSessionFactory sqlSessionFactory sqlSessionFactoryBuilder.build(is);// 3. 创建SqlSession对象SqlSession sqlSession sqlSessionFactory.openSession();// 4. 执行sqlint count sqlSession.insert(insertCar);System.out.println(插入几条数据 count);// 5. 提交mybatis默认采用的事务管理器是JDBC默认是不提交的需要手动提交。sqlSession.commit();// 6. 关闭资源只关闭是不会提交的sqlSession.close();} }以上程序运行后看到数据库表t_car中又新增一条数据如下成功了 经过测试说明mybatis核心配置文件的名字是随意的存放路径也是随意的。 虽然mybatis核心配置文件的名字不是固定的但通常该文件的名字叫做mybatis-config.xml 虽然mybatis核心配置文件的路径不是固定的但通常该文件会存放到类路径当中这样让项目的移植更加健壮。 在mybatis中提供了一个类Resources【org.apache.ibatis.io.Resources】该类可以从类路径当中获取资源我们通常使用它来获取输入流InputStream代码如下 // 这种方式只能从类路径当中获取资源也就是说mybatis-config.xml文件需要在类路径下。 InputStream is Resources.getResourceAsStream(mybatis-config.xml);2.5 MyBatis第一个比较完整的代码写法 package com.powernode.mybatis;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 java.io.IOException;/*** 比较完整的第一个mybatis程序写法* author 老杜* since 1.0* version 1.0*/ public class MyBatisCompleteCodeTest {public static void main(String[] args) {SqlSession sqlSession null;try {// 1.创建SqlSessionFactoryBuilder对象SqlSessionFactoryBuilder sqlSessionFactoryBuilder new SqlSessionFactoryBuilder();// 2.创建SqlSessionFactory对象SqlSessionFactory sqlSessionFactory sqlSessionFactoryBuilder.build(Resources.getResourceAsStream(mybatis-config.xml));// 3.创建SqlSession对象sqlSession sqlSessionFactory.openSession();// 4.执行SQLint count sqlSession.insert(insertCar);System.out.println(更新了几条记录 count);// 5.提交sqlSession.commit();} catch (Exception e) {// 回滚if (sqlSession ! null) {sqlSession.rollback();}e.printStackTrace();} finally {// 6.关闭if (sqlSession ! null) {sqlSession.close();}}} }运行后数据库表的变化 2.6 引入JUnit JUnit是专门做单元测试的组件。 在实际开发中单元测试一般是由我们Java程序员来完成的。我们要对我们自己写的每一个业务方法负责任要保证每个业务方法在进行测试的时候都能通过。测试的过程中涉及到两个概念 期望值实际值 期望值和实际值相同表示测试通过期望值和实际值不同则单元测试执行时会报错。 这里引入JUnit是为了代替main方法。使用JUnit步骤 第一步引入依赖 !-- junit依赖 -- dependencygroupIdjunit/groupIdartifactIdjunit/artifactIdversion4.13.2/versionscopetest/scope /dependency第二步编写单元测试类【测试用例】测试用例中每一个测试方法上使用Test注解进行标注。 测试用例的名字以及每个测试方法的定义都是有规范的 测试用例的名字XxxTest测试方法声明格式public void test业务方法名(){} // 测试用例 public class CarMapperTest{// 测试方法Testpublic void testInsert(){}Testpublic void testUpdate(){}}第三步可以在类上执行也可以在方法上执行 在类上执行时该类中所有的测试方法都会执行。在方法上执行时只执行当前的测试方法。 编写一个测试用例来测试insertCar业务 package com.powernode.mybatis;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.Test;public class CarMapperTest {Testpublic void testInsertCar(){SqlSession sqlSession null;try {// 1.创建SqlSessionFactoryBuilder对象SqlSessionFactoryBuilder sqlSessionFactoryBuilder new SqlSessionFactoryBuilder();// 2.创建SqlSessionFactory对象SqlSessionFactory sqlSessionFactory sqlSessionFactoryBuilder.build(Resources.getResourceAsStream(mybatis-config.xml));// 3.创建SqlSession对象sqlSession sqlSessionFactory.openSession();// 4.执行SQLint count sqlSession.insert(insertCar);System.out.println(更新了几条记录 count);// 5.提交sqlSession.commit();} catch (Exception e) {// 回滚if (sqlSession ! null) {sqlSession.rollback();}e.printStackTrace();} finally {// 6.关闭if (sqlSession ! null) {sqlSession.close();}}} }执行单元测试查看数据库表的变化 2.7 引入日志框架logback 引入日志框架的目的是为了看清楚mybatis执行的具体sql。启用标准日志组件只需要在mybatis-config.xml文件中添加以下配置【可参考mybatis手册】 settingssetting namelogImpl valueSTDOUT_LOGGING / /settings标准日志也可以用但是配置不够灵活可以集成其他的日志组件例如log4jlogback等。 logback是目前日志框架中性能较好的较流行的所以我们选它。引入logback的步骤 第一步引入logback相关依赖 dependencygroupIdch.qos.logback/groupIdartifactIdlogback-classic/artifactIdversion1.2.11/versionscopetest/scope /dependency第二步引入logback相关配置文件文件名叫做logback.xml或logback-test.xml放到类路径当中 ?xml version1.0 encodingUTF-8?configuration debugfalse!-- 控制台输出 --appender nameSTDOUT classch.qos.logback.core.ConsoleAppenderencoder classch.qos.logback.classic.encoder.PatternLayoutEncoder!--格式化输出%d表示日期%thread表示线程名%-5level级别从左显示5个字符宽度%msg日志消息%n是换行符--pattern%d{yyyy-MM-dd HH:mm:ss.SSS} [%thread] %-5level %logger{50} - %msg%n/pattern/encoder/appender!-- 按照每天生成日志文件 --appender nameFILE classch.qos.logback.core.rolling.RollingFileAppenderrollingPolicy classch.qos.logback.core.rolling.TimeBasedRollingPolicy!--日志文件输出的文件名--FileNamePattern${LOG_HOME}/TestWeb.log.%d{yyyy-MM-dd}.log/FileNamePattern!--日志文件保留天数--MaxHistory30/MaxHistory/rollingPolicyencoder classch.qos.logback.classic.encoder.PatternLayoutEncoder!--格式化输出%d表示日期%thread表示线程名%-5level级别从左显示5个字符宽度%msg日志消息%n是换行符--pattern%d{yyyy-MM-dd HH:mm:ss.SSS} [%thread] %-5level %logger{50} - %msg%n/pattern/encoder!--日志文件最大的大小--triggeringPolicy classch.qos.logback.core.rolling.SizeBasedTriggeringPolicyMaxFileSize100MB/MaxFileSize/triggeringPolicy/appender!--mybatis log configure--logger namecom.apache.ibatis levelTRACE/logger namejava.sql.Connection levelDEBUG/logger namejava.sql.Statement levelDEBUG/logger namejava.sql.PreparedStatement levelDEBUG/!-- 日志输出级别,logback日志级别包括五个TRACE DEBUG INFO WARN ERROR --root levelDEBUGappender-ref refSTDOUT/appender-ref refFILE//root/configuration再次执行单元测试方法testInsertCar查看控制台是否有sql语句输出 2.8 MyBatis工具类SqlSessionUtil的封装 每一次获取SqlSession对象代码太繁琐封装一个工具类 package com.powernode.mybatis.utils;import org.apache.ibatis.io.Resources; import org.apache.ibatis.session.SqlSession; import org.apache.ibatis.session.SqlSessionFactory; import org.apache.ibatis.session.SqlSessionFactoryBuilder;/*** MyBatis工具类** author 老杜* version 1.0* since 1.0*/ public class SqlSessionUtil {private static SqlSessionFactory sqlSessionFactory;/*** 类加载时初始化sqlSessionFactory对象*/static {try {SqlSessionFactoryBuilder sqlSessionFactoryBuilder new SqlSessionFactoryBuilder();sqlSessionFactory sqlSessionFactoryBuilder.build(Resources.getResourceAsStream(mybatis-config.xml));} catch (Exception e) {e.printStackTrace();}}/*** 每调用一次openSession()可获取一个新的会话该会话支持自动提交。** return 新的会话对象*/public static SqlSession openSession() {return sqlSessionFactory.openSession(true);} }测试工具类将testInsertCar()改造 Test public void testInsertCar(){SqlSession sqlSession SqlSessionUtil.openSession();// 执行SQLint count sqlSession.insert(insertCar);System.out.println(插入了几条记录: count);sqlSession.close(); }三、使用MyBatis完成CRUD 准备工作 创建moduleMaven的普通Java模块mybatis-002-crudpom.xml 打包方式jar依赖 mybatis依赖mysql驱动依赖junit依赖logback依赖 mybatis-config.xml放在类的根路径下CarMapper.xml放在类的根路径下logback.xml放在类的根路径下提供com.powernode.mybatis.utils.SqlSessionUtil工具类创建测试用例com.powernode.mybatis.CarMapperTest 3.1 insertCreate 分析以下SQL映射文件中SQL语句存在的问题 ?xml version1.0 encodingUTF-8 ? !DOCTYPE mapperPUBLIC -//mybatis.org//DTD Mapper 3.0//ENhttp://mybatis.org/dtd/mybatis-3-mapper.dtd!--namespace先随便写-- mapper namespacecarinsert idinsertCarinsert into t_car(car_num,brand,guide_price,produce_time,car_type) values(103, 奔驰E300L, 50.3, 2022-01-01, 燃油车)/insert /mapper存在的问题是SQL语句中的值不应该写死值应该是用户提供的。之前的JDBC代码是这样写的 // JDBC中使用 ? 作为占位符。那么MyBatis中会使用什么作为占位符呢 String sql insert into t_car(car_num,brand,guide_price,produce_time,car_type) values(?,?,?,?,?); // ...... // 给 ? 传值。那么MyBatis中应该怎么传值呢 ps.setString(1,103); ps.setString(2,奔驰E300L); ps.setDouble(3,50.3); ps.setString(4,2022-01-01); ps.setString(5,燃油车);在MyBatis中可以这样做 在Java程序中将数据放到Map集合中 在sql语句中使用 #{map集合的key} 来完成传值#{} 等同于JDBC中的 ? #{}就是占位符 Java程序这样写 package com.powernode.mybatis;import com.powernode.mybatis.utils.SqlSessionUtil; import org.apache.ibatis.session.SqlSession; import org.junit.Test;import java.util.HashMap; import java.util.Map;/*** 测试MyBatis的CRUD* author 老杜* version 1.0* since 1.0*/ public class CarMapperTest {Testpublic void testInsertCar(){// 准备数据MapString, Object map new HashMap();map.put(k1, 103);map.put(k2, 奔驰E300L);map.put(k3, 50.3);map.put(k4, 2020-10-01);map.put(k5, 燃油车);// 获取SqlSession对象SqlSession sqlSession SqlSessionUtil.openSession();// 执行SQL语句使用map集合给sql语句传递数据int count sqlSession.insert(insertCar, map);System.out.println(插入了几条记录 count);} }SQL语句这样写 ?xml version1.0 encodingUTF-8 ? !DOCTYPE mapperPUBLIC -//mybatis.org//DTD Mapper 3.0//ENhttp://mybatis.org/dtd/mybatis-3-mapper.dtd!--namespace先随便写-- mapper namespacecarinsert idinsertCarinsert into t_car(car_num,brand,guide_price,produce_time,car_type) values(#{k1},#{k2},#{k3},#{k4},#{k5})/insert /mapper#{} 的里面必须填写map集合的key不能随便写运行测试程序查看数据库 如果#{}里写的是map集合中不存在的key会有什么问题 ?xml version1.0 encodingUTF-8 ? !DOCTYPE mapperPUBLIC -//mybatis.org//DTD Mapper 3.0//ENhttp://mybatis.org/dtd/mybatis-3-mapper.dtdmapper namespacecarinsert idinsertCarinsert into t_car(car_num,brand,guide_price,produce_time,car_type) values(#{kk},#{k2},#{k3},#{k4},#{k5})/insert /mapper运行程序 通过测试看到程序并没有报错。正常执行。不过 #{kk} 的写法导致无法获取到map集合中的数据最终导致数据库表car_num插入了NULL。 在以上sql语句中可以看到#{k1} #{k2} #{k3} #{k4} #{k5}的可读性太差为了增强可读性我们可以将Java程序做如下修改 MapString, Object map new HashMap(); // 让key的可读性增强 map.put(carNum, 103); map.put(brand, 奔驰E300L); map.put(guidePrice, 50.3); map.put(produceTime, 2020-10-01); map.put(carType, 燃油车);SQL语句做如下修改这样可以增强程序的可读性 ?xml version1.0 encodingUTF-8 ? !DOCTYPE mapperPUBLIC -//mybatis.org//DTD Mapper 3.0//ENhttp://mybatis.org/dtd/mybatis-3-mapper.dtd mapper namespacecarinsert idinsertCarinsert into t_car(car_num,brand,guide_price,produce_time,car_type) values(#{carNum},#{brand},#{guidePrice},#{produceTime},#{carType})/insert /mapper运行程序查看数据库表 使用Map集合可以传参那使用pojo简单普通的java对象可以完成传参吗测试一下 第一步定义一个pojo类Car提供相关属性。 package com.powernode.mybatis.pojo;/*** POJOs简单普通的Java对象。封装数据用的。* author 老杜* version 1.0* since 1.0*/ public class Car {private Long id;private String carNum;private String brand;private Double guidePrice;private String produceTime;private String carType;Overridepublic String toString() {return Car{ id id , carNum carNum \ , brand brand \ , guidePrice guidePrice , produceTime produceTime \ , carType carType \ };}public Car() {}public Car(Long id, String carNum, String brand, Double guidePrice, String produceTime, String carType) {this.id id;this.carNum carNum;this.brand brand;this.guidePrice guidePrice;this.produceTime produceTime;this.carType carType;}public Long getId() {return id;}public void setId(Long id) {this.id id;}public String getCarNum() {return carNum;}public void setCarNum(String carNum) {this.carNum carNum;}public String getBrand() {return brand;}public void setBrand(String brand) {this.brand brand;}public Double getGuidePrice() {return guidePrice;}public void setGuidePrice(Double guidePrice) {this.guidePrice guidePrice;}public String getProduceTime() {return produceTime;}public void setProduceTime(String produceTime) {this.produceTime produceTime;}public String getCarType() {return carType;}public void setCarType(String carType) {this.carType carType;} }第二步Java程序 Test public void testInsertCarByPOJO(){// 创建POJO封装数据Car car new Car();car.setCarNum(103);car.setBrand(奔驰C200);car.setGuidePrice(33.23);car.setProduceTime(2020-10-11);car.setCarType(燃油车);// 获取SqlSession对象SqlSession sqlSession SqlSessionUtil.openSession();// 执行SQL传数据int count sqlSession.insert(insertCarByPOJO, car);System.out.println(插入了几条记录 count); }第三步SQL语句 insert idinsertCarByPOJO!--#{} 里写的是POJO的属性名--insert into t_car(car_num,brand,guide_price,produce_time,car_type) values(#{carNum},#{brand},#{guidePrice},#{produceTime},#{carType}) /insert运行程序查看数据库表 #{} 里写的是POJO的属性名如果写成其他的会有问题吗 insert idinsertCarByPOJOinsert into t_car(car_num,brand,guide_price,produce_time,car_type) values(#{a},#{brand},#{guidePrice},#{produceTime},#{carType}) /insert运行程序出现了以下异常 错误信息中描述在Car类中没有找到a属性的getter方法。 修改POJO类Car的代码只将getCarNum()方法名修改为getA()其他代码不变如下 再运行程序查看数据库表中数据 经过测试得出结论 如果采用map集合传参#{} 里写的是map集合的key如果key不存在不会报错数据库表中会插入NULL。 如果采用POJO传参#{} 里写的是get方法的方法名去掉get之后将剩下的单词首字母变小写例如getAge对应的是#{age}getUserName对应的是#{userName}如果这样的get方法不存在会报错。 注意其实传参数的时候有一个属性parameterType这个属性用来指定传参的数据类型不过这个属性是可以省略的 insert idinsertCar parameterTypejava.util.Mapinsert into t_car(car_num,brand,guide_price,produce_time,car_type) values(#{carNum},#{brand},#{guidePrice},#{produceTime},#{carType}) /insertinsert idinsertCarByPOJO parameterTypecom.powernode.mybatis.pojo.Carinsert into t_car(car_num,brand,guide_price,produce_time,car_type) values(#{carNum},#{brand},#{guidePrice},#{produceTime},#{carType}) /insert3.2 deleteDelete 需求根据car_num进行删除。 SQL语句这样写 delete iddeleteByCarNumdelete from t_car where car_num #{SuiBianXie} /deleteJava程序这样写 Test public void testDeleteByCarNum(){// 获取SqlSession对象SqlSession sqlSession SqlSessionUtil.openSession();// 执行SQL语句int count sqlSession.delete(deleteByCarNum, 102);System.out.println(删除了几条记录 count); }运行结果 注意当占位符只有一个的时候${} 里面的内容可以随便写。 3.3 updateUpdate 需求修改id34的Car信息car_num为102brand为比亚迪汉guide_price为30.23produce_time为2018-09-10car_type为电车 修改前 SQL语句如下 update idupdateCarByPOJOupdate t_car set car_num #{carNum}, brand #{brand}, guide_price #{guidePrice}, produce_time #{produceTime}, car_type #{carType} where id #{id} /updateJava代码如下 Testpublic void testUpdateCarByPOJO(){// 准备数据Car car new Car();car.setId(34L);car.setCarNum(102);car.setBrand(比亚迪汉);car.setGuidePrice(30.23);car.setProduceTime(2018-09-10);car.setCarType(电车);// 获取SqlSession对象SqlSession sqlSession SqlSessionUtil.openSession();// 执行SQL语句int count sqlSession.update(updateCarByPOJO, car);System.out.println(更新了几条记录 count);}运行结果 当然了如果使用map传数据也是可以的。 3.4 selectRetrieve select语句和其它语句不同的是查询会有一个结果集。来看mybatis是怎么处理结果集的 查询一条数据 需求查询id为1的Car信息 SQL语句如下 select idselectCarByIdselect * from t_car where id #{id} /selectJava程序如下 Test public void testSelectCarById(){// 获取SqlSession对象SqlSession sqlSession SqlSessionUtil.openSession();// 执行SQL语句Object car sqlSession.selectOne(selectCarById, 1);System.out.println(car); }运行结果如下 ### Error querying database. Cause: org.apache.ibatis.executor.ExecutorException: A query was run and no Result Maps were found for the Mapped Statement car.selectCarById. 【翻译】对于一个查询语句来说没有找到查询的结果映射。Its likely that neither a Result Type nor a Result Map was specified. 【翻译】很可能既没有指定结果类型也没有指定结果映射。以上的异常大致的意思是对于一个查询语句来说你需要指定它的“结果类型”或者“结果映射”。 所以说你想让mybatis查询之后返回一个Java对象的话至少你要告诉mybatis返回一个什么类型的Java对象可以在标签中添加resultType属性用来指定查询要转换的类型 select idselectCarById resultTypecom.powernode.mybatis.pojo.Carselect * from t_car where id #{id} /select运行结果 运行后之前的异常不再出现了这说明添加了resultType属性之后解决了之前的异常可以看出resultType是不能省略的。 仔细观察控制台的日志信息不难看出结果查询出了一条。并且每个字段都查询到值了Row: 1, 100, 宝马520Li, 41.00, 2022-09-01, 燃油车 但是奇怪的是返回的Car对象只有id和brand两个属性有值其它属性的值都是null这是为什么呢我们来观察一下查询结果列名和Car类的属性名是否能一一对应 查询结果集的列名id, car_num, brand, guide_price, produce_time, car_type Car类的属性名id, carNum, brand, guidePrice, produceTime, carType 通过观察发现只有id和brand是一致的其他字段名和属性名对应不上这是不是导致null的原因呢我们尝试在sql语句中使用as关键字来给查询结果列名起别名试试 select idselectCarById resultTypecom.powernode.mybatis.pojo.Carselect id, car_num as carNum, brand, guide_price as guidePrice, produce_time as produceTime, car_type as carType from t_car where id #{id} /select运行结果如下 通过测试得知如果当查询结果的字段名和java类的属性名对应不上的话可以采用as关键字起别名当然还有其它解决方案我们后面再看。 查询多条数据 需求查询所有的Car信息。 SQL语句如下 !--虽然结果是List集合但是resultType属性需要指定的是List集合中元素的类型。-- select idselectCarAll resultTypecom.powernode.mybatis.pojo.Car!--记得使用as起别名让查询结果的字段名和java类的属性名对应上。--selectid, car_num as carNum, brand, guide_price as guidePrice, produce_time as produceTime, car_type as carTypefromt_car /selectJava代码如下 Test public void testSelectCarAll(){// 获取SqlSession对象SqlSession sqlSession SqlSessionUtil.openSession();// 执行SQL语句ListObject cars sqlSession.selectList(selectCarAll);// 输出结果cars.forEach(car - System.out.println(car)); }运行结果如下 3.5 关于SQL Mapper的namespace 在SQL Mapper配置文件中标签的namespace属性可以翻译为命名空间这个命名空间主要是为了防止sqlId冲突的。 创建CarMapper2.xml文件代码如下 ?xml version1.0 encodingUTF-8 ? !DOCTYPE mapperPUBLIC -//mybatis.org//DTD Mapper 3.0//ENhttp://mybatis.org/dtd/mybatis-3-mapper.dtdmapper namespacecar2select idselectCarAll resultTypecom.powernode.mybatis.pojo.Carselectid, car_num as carNum, brand, guide_price as guidePrice, produce_time as produceTime, car_type as carTypefromt_car/select /mapper不难看出CarMapper.xml和CarMapper2.xml文件中都有 id“selectCarAll” 将CarMapper2.xml配置到mybatis-config.xml文件中。 mappersmapper resourceCarMapper.xml/mapper resourceCarMapper2.xml/ /mappers编写Java代码如下 Test public void testNamespace(){// 获取SqlSession对象SqlSession sqlSession SqlSessionUtil.openSession();// 执行SQL语句ListObject cars sqlSession.selectList(selectCarAll);// 输出结果cars.forEach(car - System.out.println(car)); }运行结果如下 org.apache.ibatis.exceptions.PersistenceException: ### Error querying database. Cause: java.lang.IllegalArgumentException: selectCarAll is ambiguous in Mapped Statements collection (try using the full name including the namespace, or rename one of the entries) 【翻译】selectCarAll在Mapped Statements集合中不明确请尝试使用包含名称空间的全名或重命名其中一个条目【大致意思是】selectCarAll重名了你要么在selectCarAll前添加一个名称空间要有你改个其它名字。Java代码修改如下 Test public void testNamespace(){// 获取SqlSession对象SqlSession sqlSession SqlSessionUtil.openSession();// 执行SQL语句//ListObject cars sqlSession.selectList(car.selectCarAll);ListObject cars sqlSession.selectList(car2.selectCarAll);// 输出结果cars.forEach(car - System.out.println(car)); }运行结果如下 四、MyBatis核心配置文件详解 ?xml version1.0 encodingUTF-8 ? !DOCTYPE configurationPUBLIC -//mybatis.org//DTD Config 3.0//ENhttp://mybatis.org/dtd/mybatis-3-config.dtd configurationenvironments defaultdevelopmentenvironment iddevelopmenttransactionManager typeJDBC/dataSource typePOOLEDproperty namedriver valuecom.mysql.cj.jdbc.Driver/property nameurl valuejdbc:mysql://localhost:3306/powernode/property nameusername valueroot/property namepassword valueroot//dataSource/environment/environmentsmappersmapper resourceCarMapper.xml/mapper resourceCarMapper2.xml//mappers /configurationconfiguration根标签表示配置信息。environments环境多个以“s”结尾表示复数也就是说mybatis的环境可以配置多个数据源。 default属性表示默认使用的是哪个环境default后面填写的是environment的id。default的值只需要和environment的id值一致即可。 environment具体的环境配置主要包括事务管理器的配置 数据源的配置 id给当前环境一个唯一标识该标识用在environments的default后面用来指定默认环境的选择。 transactionManager配置事务管理器 type属性指定事务管理器具体使用什么方式可选值包括两个 JDBC使用JDBC原生的事务管理机制。底层原理事务开启conn.setAutoCommit(false); …处理业务…事务提交conn.commit();MANAGED交给其它容器来管理事务比如WebLogic、JBOSS等。如果没有管理事务的容器则没有事务。没有事务的含义只要执行一条DML语句则提交一次。 dataSource指定数据源 type属性用来指定具体使用的数据库连接池的策略可选值包括三个 UNPOOLED采用传统的获取连接的方式虽然也实现Javax.sql.DataSource接口但是并没有使用池的思想。 property可以是 driver 这是 JDBC 驱动的 Java 类全限定名。url 这是数据库的 JDBC URL 地址。username 登录数据库的用户名。password 登录数据库的密码。defaultTransactionIsolationLevel 默认的连接事务隔离级别。defaultNetworkTimeout 等待数据库操作完成的默认网络超时时间单位毫秒 POOLED采用传统的javax.sql.DataSource规范中的连接池mybatis中有针对规范的实现。 property可以是除了包含UNPOOLED中之外 poolMaximumActiveConnections 在任意时间可存在的活动正在使用连接数量默认值10poolMaximumIdleConnections 任意时间可能存在的空闲连接数。其它… JNDI采用服务器提供的JNDI技术实现来获取DataSource对象不同的服务器所能拿到DataSource是不一样。如果不是web或者maven的war工程JNDI是不能使用的。 property可以是最多只包含以下两个属性 initial_context 这个属性用来在 InitialContext 中寻找上下文即initialContext.lookup(initial_context)这是个可选属性如果忽略那么将会直接从 InitialContext 中寻找 data_source 属性。data_source 这是引用数据源实例位置的上下文路径。提供了 initial_context 配置时会在其返回的上下文中进行查找没有提供时则直接在 InitialContext 中查找。 mappers在mappers标签中可以配置多个sql映射文件的路径。mapper配置某个sql映射文件的路径 resource属性使用相对于类路径的资源引用方式url属性使用完全限定资源定位符URL方式 4.1 environment mybatis-003-configuration ?xml version1.0 encodingUTF-8 ? !DOCTYPE configurationPUBLIC -//mybatis.org//DTD Config 3.0//ENhttp://mybatis.org/dtd/mybatis-3-config.dtd configuration!--默认使用开发环境--!--environments defaultdev--!--默认使用生产环境--environments defaultproduction!--开发环境--environment iddevtransactionManager typeJDBC/dataSource typePOOLEDproperty namedriver valuecom.mysql.cj.jdbc.Driver/property nameurl valuejdbc:mysql://localhost:3306/powernode/property nameusername valueroot/property namepassword valueroot//dataSource/environment!--生产环境--environment idproductiontransactionManager typeJDBC /dataSource typePOOLEDproperty namedriver valuecom.mysql.cj.jdbc.Driver/property nameurl valuejdbc:mysql://localhost:3306/mybatis/property nameusername valueroot/property namepassword valueroot//dataSource/environment/environmentsmappersmapper resourceCarMapper.xml//mappers /configuration?xml version1.0 encodingUTF-8 ? !DOCTYPE mapperPUBLIC -//mybatis.org//DTD Mapper 3.0//ENhttp://mybatis.org/dtd/mybatis-3-mapper.dtdmapper namespacecarinsert idinsertCarinsert into t_car(id,car_num,brand,guide_price,produce_time,car_type) values(null,#{carNum},#{brand},#{guidePrice},#{produceTime},#{carType})/insert /mapperpackage com.powernode.mybatis;import com.powernode.mybatis.pojo.Car; 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.Test;public class ConfigurationTest {Testpublic void testEnvironment() throws Exception{// 准备数据Car car new Car();car.setCarNum(133);car.setBrand(丰田霸道);car.setGuidePrice(50.3);car.setProduceTime(2020-01-10);car.setCarType(燃油车);// 一个数据库对应一个SqlSessionFactory对象// 两个数据库对应两个SqlSessionFactory对象以此类推SqlSessionFactoryBuilder sqlSessionFactoryBuilder new SqlSessionFactoryBuilder();// 使用默认数据库SqlSessionFactory sqlSessionFactory sqlSessionFactoryBuilder.build(Resources.getResourceAsStream(mybatis-config.xml));SqlSession sqlSession sqlSessionFactory.openSession(true);int count sqlSession.insert(insertCar, car);System.out.println(插入了几条记录 count);// 使用指定数据库SqlSessionFactory sqlSessionFactory1 sqlSessionFactoryBuilder.build(Resources.getResourceAsStream(mybatis-config.xml), dev);SqlSession sqlSession1 sqlSessionFactory1.openSession(true);int count1 sqlSession1.insert(insertCar, car);System.out.println(插入了几条记录 count1);} }执行结果 4.2 transactionManager ?xml version1.0 encodingUTF-8 ? !DOCTYPE configurationPUBLIC -//mybatis.org//DTD Config 3.0//ENhttp://mybatis.org/dtd/mybatis-3-config.dtd configurationenvironments defaultdevenvironment iddevtransactionManager typeMANAGED/dataSource typePOOLEDproperty namedriver valuecom.mysql.cj.jdbc.Driver/property nameurl valuejdbc:mysql://localhost:3306/powernode/property nameusername valueroot/property namepassword valueroot//dataSource/environment/environmentsmappersmapper resourceCarMapper.xml//mappers /configurationTest public void testTransactionManager() throws Exception{// 准备数据Car car new Car();car.setCarNum(133);car.setBrand(丰田霸道);car.setGuidePrice(50.3);car.setProduceTime(2020-01-10);car.setCarType(燃油车);// 获取SqlSessionFactory对象SqlSessionFactoryBuilder sqlSessionFactoryBuilder new SqlSessionFactoryBuilder();SqlSessionFactory sqlSessionFactory sqlSessionFactoryBuilder.build(Resources.getResourceAsStream(mybatis-config2.xml));// 获取SqlSession对象SqlSession sqlSession sqlSessionFactory.openSession();// 执行SQLint count sqlSession.insert(insertCar, car);System.out.println(插入了几条记录 count); }当事务管理器是JDBC 采用JDBC的原生事务机制 开启事务conn.setAutoCommit(false);处理业务…提交事务conn.commit(); 当事务管理器是MANAGED 交给容器去管理事务但目前使用的是本地程序没有容器的支持当mybatis找不到容器的支持时没有事务。也就是说只要执行一条DML语句则提交一次。 4.3 dataSource ?xml version1.0 encodingUTF-8 ? !DOCTYPE configurationPUBLIC -//mybatis.org//DTD Config 3.0//ENhttp://mybatis.org/dtd/mybatis-3-config.dtd configurationenvironments defaultdevenvironment iddevtransactionManager typeJDBC/dataSource typeUNPOOLEDproperty namedriver valuecom.mysql.cj.jdbc.Driver/property nameurl valuejdbc:mysql://localhost:3306/powernode/property nameusername valueroot/property namepassword valueroot//dataSource/environment/environmentsmappersmapper resourceCarMapper.xml//mappers /configurationTest public void testDataSource() throws Exception{// 准备数据Car car new Car();car.setCarNum(133);car.setBrand(丰田霸道);car.setGuidePrice(50.3);car.setProduceTime(2020-01-10);car.setCarType(燃油车);// 获取SqlSessionFactory对象SqlSessionFactoryBuilder sqlSessionFactoryBuilder new SqlSessionFactoryBuilder();SqlSessionFactory sqlSessionFactory sqlSessionFactoryBuilder.build(Resources.getResourceAsStream(mybatis-config3.xml));// 获取SqlSession对象SqlSession sqlSession sqlSessionFactory.openSession(true);// 执行SQLint count sqlSession.insert(insertCar, car);System.out.println(插入了几条记录 count);// 关闭会话sqlSession.close(); }当type是UNPOOLED控制台输出 修改配置文件mybatis-config3.xml中的配置 dataSource typePOOLEDJava测试程序不需要修改直接执行看控制台输出 通过测试得出UNPOOLED不会使用连接池每一次都会新建JDBC连接对象。POOLED会使用数据库连接池。【这个连接池是mybatis自己实现的。】 dataSource typeJNDIJNDI的方式表示对接JNDI服务器中的连接池。这种方式给了我们可以使用第三方连接池的接口。如果想使用dbcp、c3p0、druid德鲁伊等需要使用这种方式。 这种再重点说一下typePOOLED的时候它的属性有哪些 ?xml version1.0 encodingUTF-8 ? !DOCTYPE configurationPUBLIC -//mybatis.org//DTD Config 3.0//ENhttp://mybatis.org/dtd/mybatis-3-config.dtd configurationenvironments defaultdevenvironment iddevtransactionManager typeJDBC/dataSource typePOOLEDproperty namedriver valuecom.mysql.cj.jdbc.Driver/property nameurl valuejdbc:mysql://localhost:3306/powernode/property nameusername valueroot/property namepassword valueroot/!--最大连接数--property namepoolMaximumActiveConnections value3/!--这是一个底层设置如果获取连接花费了相当长的时间连接池会打印状态日志并重新尝试获取一个连接避免在误配置的情况下一直失败且不打印日志默认值20000 毫秒即 20 秒。--property namepoolTimeToWait value20000/!--强行回归池的时间--property namepoolMaximumCheckoutTime value20000/!--最多空闲数量--property namepoolMaximumIdleConnections value1//dataSource/environment/environmentsmappersmapper resourceCarMapper.xml//mappers /configurationpoolMaximumActiveConnections最大的活动的连接数量。默认值10 poolMaximumIdleConnections最大的空闲连接数量。默认值5 poolMaximumCheckoutTime强行回归池的时间。默认值20秒。 poolTimeToWait当无法获取到空闲连接时每隔20秒打印一次日志避免因代码配置有误导致傻等。时长是可以配置的 当然还有其他属性。对于连接池来说以上几个属性比较重要。 最大的活动的连接数量就是连接池连接数量的上限。默认值10如果有10个请求正在使用这10个连接第11个请求只能等待空闲连接。 最大的空闲连接数量。默认值5如何已经有了5个空闲连接当第6个连接要空闲下来的时候连接池会选择关闭该连接对象。来减少数据库的开销。 需要根据系统的并发情况来合理调整连接池最大连接数以及最多空闲数量。充分发挥数据库连接池的性能。【可以根据实际情况进行测试然后调整一个合理的数量。】 下图是默认配置 在以上配置的基础之上可以编写java程序测试 Test public void testPool() throws Exception{SqlSessionFactoryBuilder sqlSessionFactoryBuilder new SqlSessionFactoryBuilder();SqlSessionFactory sqlSessionFactory sqlSessionFactoryBuilder.build(Resources.getResourceAsStream(mybatis-config3.xml));for (int i 0; i 4; i) {SqlSession sqlSession sqlSessionFactory.openSession();Object selectCarByCarNum sqlSession.selectOne(selectCarByCarNum);} }select idselectCarByCarNum resultTypecom.powernode.mybatis.pojo.Carselect id,car_num carNum,brand,guide_price guidePrice,produce_time produceTime,car_type carType from t_car where car_num 100 /select4.4 properties mybatis提供了更加灵活的配置连接数据库的信息可以单独写到一个属性资源文件中假设在类的根路径下创建jdbc.properties文件配置如下 jdbc.drivercom.mysql.cj.jdbc.Driver jdbc.urljdbc:mysql://localhost:3306/powernode在mybatis核心配置文件中引入并使用 ?xml version1.0 encodingUTF-8 ? !DOCTYPE configurationPUBLIC -//mybatis.org//DTD Config 3.0//ENhttp://mybatis.org/dtd/mybatis-3-config.dtd configuration!--引入外部属性资源文件--properties resourcejdbc.propertiesproperty namejdbc.username valueroot/property namejdbc.password valueroot//propertiesenvironments defaultdevenvironment iddevtransactionManager typeJDBC/dataSource typePOOLED!--${key}使用--property namedriver value${jdbc.driver}/property nameurl value${jdbc.url}/property nameusername value${jdbc.username}/property namepassword value${jdbc.password}//dataSource/environment/environmentsmappersmapper resourceCarMapper.xml//mappers /configuration编写Java程序进行测试 Test public void testProperties() throws Exception{SqlSessionFactoryBuilder sqlSessionFactoryBuilder new SqlSessionFactoryBuilder();SqlSessionFactory sqlSessionFactory sqlSessionFactoryBuilder.build(Resources.getResourceAsStream(mybatis-config4.xml));SqlSession sqlSession sqlSessionFactory.openSession();Object car sqlSession.selectOne(selectCarByCarNum);System.out.println(car); }properties两个属性 resource这个属性从类的根路径下开始加载。【常用的。】 url从指定的url加载假设文件放在d:/jdbc.properties这个url可以写成file:///d:/jdbc.properties。注意是三个斜杠哦。 注意如果不知道mybatis-config.xml文件中标签的编写顺序的话可以有两种方式知道它的顺序 第一种方式查看dtd约束文件。第二种方式通过idea的报错提示信息。【一般采用这种方式】 4.5 mapper mapper标签用来指定SQL映射文件的路径包含多种指定方式这里先主要看其中两种 第一种resource从类的根路径下开始加载【比url常用】 mappersmapper resourceCarMapper.xml/ /mappers如果是这样写的话必须保证类的根下有CarMapper.xml文件。 如果类的根路径下有一个包叫做testCarMapper.xml如果放在test包下的话这个配置应该是这样写 mappersmapper resourcetest/CarMapper.xml/ /mappers第二种url从指定的url位置加载 假设CarMapper.xml文件放在d盘的根下这个配置就需要这样写 mappersmapper urlfile:///d:/CarMapper.xml/ /mappersmapper还有其他的指定方式后面再看
http://www.zqtcl.cn/news/741679/

相关文章:

  • 保定建站价格dw软件免费安装
  • 在建设部网站上的举报凡科网怎么建网站
  • wordpress做小说网站工作期间员工花钱做的网站
  • 婚介网站方案小说网站架构
  • 英文在线购物网站建设湖北建设厅举报网站
  • 漯河网络推广哪家好宁波网站seo公司
  • 网站设计ppt案例做物流用哪个网站好
  • 做网站官网需多少钱天元建设集团有限公司财务分析
  • 一般网站建设用什么语言网络规划设计师历年考点
  • 做网站卖菜刀需要什么手续江苏网站优化
  • 花生壳内网穿透网站如何做seo优化鞍山58同城网
  • 怎么为一个网站做外链跨境电商app
  • 医疗网站不备案seo技巧课程
  • 网页和网站有什么区别湖南省郴州市邮编
  • 公考在哪个网站上做试题武威做网站的公司
  • 河南如何做网站常州网站建设价位
  • 昆山网站建设培训班成都百度
  • 兰山网站建设郑州最好的网站建设
  • 手机网站后台源码枣庄市建设局网站
  • 网站建设傲鸿wordpress 获取分类下的文章
  • 网站运行速度优化wordpress国内优化
  • wordpress全站网易云音乐播放网站建设案例公司
  • 湘潭网站建设多少钱 报价表湘潭磐石网络北京百度seo点击器
  • 什么做的网站电子商务网站的建设的原理
  • 河北建站科技网络公司媒体平台
  • 做同城信息类网站如何赚钱石景山网站建设多少钱
  • 用ip的网站要备案吗网站的建设维护及管理制度
  • dedecms 百度网站地图南宁比优建站
  • 沈阳大熊网站建设制作怎么增加网站的权重
  • 网站建设 价格低建设网站大约多少钱