DB数据源之SpringBoot+MyBatis踏坑过程(二)手工配置数据源与加载Mapper.xml扫描

liuyuhang原创,未经允许进制转载 

吐槽之后应该有所改了,该方式可以作为一种过渡方式来使用。

 

系列目录连接

DB数据源之SpringBoot+Mybatis踏坑过程实录(一)

1.环境说明

  • 初次使用springboot,时间有限,需要迅速搭建好架构,没有时间研究
  • 使用springboot过程中数据源无法获取;
  • 使用springboot过程中注解莫名其妙失效;
  • 用springboot过程中因为版本不懂,不扫描application.properties;
  • 使用springboot过程中因为版本不懂,不扫描mybatis的mapper.xml包;
  • springboot或spring注解使用十分不习惯或者还没有来得及深入学习的情况;

  假设有以上问题,又时间紧迫,建议使用本文手工配置方式!!

  springboot,parent 2.0.2.和1.5.3.都已经测试过,

  在java8和java7环境下测试过。前者配java8,后者配java7,

  使用MyEclipse 2017 C1 64x,MyEclipse 2016之前的版本无法使用java8

  pom.xml核心如下:

    <parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.0.2.RELEASE</version>
<relativePath /> <!-- lookup parent from repository -->
</parent>
<dependencies>
<!-- 添加MySQL依赖 -->
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
</dependency>
<!-- 添加JDBC依赖 -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-jdbc</artifactId>
</dependency>
<!-- mybaits基础依赖 -->
<dependency>
<groupId>org.mybatis</groupId>
<artifactId>mybatis</artifactId>
<version>3.4.0</version>
</dependency>
<!-- mybatis插件依赖 -->
<dependency>
<groupId>org.mybatis.spring.boot</groupId>
<artifactId>mybatis-spring-boot-starter</artifactId>
<version>1.1.1</version>
</dependency>
<!-- mapper依赖 -->
<dependency>
<groupId>tk.mybatis</groupId>
<artifactId>mapper</artifactId>
<version>3.3.7</version>
</dependency> <dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-configuration-processor</artifactId>
<optional>true</optional>
</dependency>

2.配置思路

  2.1.手工获取application.properties文件中的属性;

  2.2.创建数据源DataSource;

  2.3.注入数据源属性;

  2.4.创建SqlSessionFactory;

  2.5.SqlSessionFactory配置DataSource;

  2.6.SqlSessionFactory配置扫描MyBatis-config.xml文件;

  2.7.SqlSessionFactory配置扫描Mapper.xml所在包;

  2.8.获取session查询数据库进行测试;

3.所需类与结构

  3.0.application.properties文件与相应内容作为数据源;

  3.1.SysConfig类,用于获取application.properties中的property;

  3.2.DataConfig类,用于获取SqlSessionFactory;

  3.3.ExampleController类,用于测试;

  3.4.AppRun类,springboot的启动入口,将DataConfig初始化;

  3.5.mapper.xml内容

4.代码 

  4.0.application.properties部分内容段落:

  

 master.url=jdbc:mysql://qqq.jjj.xxx.iii:3306/master?characterEncoding=utf8
master.username=root
master.password=root
master.driver=com.mysql.jdbc.Driver
#master.driver-class-name=com.mysql.jdbc.Driver  一般是使用这个命名模式

  

  4.1.SysConfig类,代码如下:

 package com.FM.config;

 import java.io.IOException;
import java.util.Properties; import org.springframework.context.annotation.Configuration;
import org.springframework.core.io.ClassPathResource;
import org.springframework.core.io.Resource;
import org.springframework.core.io.support.PropertiesLoaderUtils; /**
* 用于读取properties的类,基础配置文件名为application.properties,置于resources根目录下
* @author Liuyuhang
*/
public class SysConfig { private Properties properties; /**
* 修改无参构造,默认该类实例化的时候,加载配置文件中的内容,不做单例,因为配置文件可能更改
*/
public SysConfig() {
try {
Resource resource = new ClassPathResource("/application.properties");
properties = PropertiesLoaderUtils.loadProperties(resource);
} catch (IOException e) {
e.printStackTrace();
}
} /**
* 获取属性,传入参数key
*/
public String getProperty(String key) {
return properties.getProperty(key);
}
}

  4.2.DataSourceConfig类,代码如下:

 package com.FM.config;

 import java.util.HashMap;

 import javax.sql.DataSource;

 import org.apache.ibatis.session.SqlSessionFactory;
import org.mybatis.spring.SqlSessionFactoryBean;
import org.springframework.boot.jdbc.DataSourceBuilder;
import org.springframework.core.io.DefaultResourceLoader;
import org.springframework.core.io.Resource;
import org.springframework.core.io.support.PathMatchingResourcePatternResolver;
/**
* DataConfig,获取数据源,配置给SqlSessionFactory,并以此获取session
*
* @author liuyuhang
*/
public class DataConfig {
/**
* 缓存factory的map,作为单例SessionFactory存储
*/
public static HashMap<String, SqlSessionFactory> factoryMap = new HashMap<String, SqlSessionFactory>(); /**
* 构造器对缓存中的factory只实例化一次
* 不保证该单例能顺利执行,若看出问题,自行更改
* @throws Exception
*/
public DataConfig() {
System.out.println("out init sessionFactory:" + factoryMap);
if (factoryMap.isEmpty()) {
synchronized (factoryMap) {
if (factoryMap.isEmpty()) {
try {
SqlSessionFactory sessionFactory = getSessionFactory();
factoryMap.put("master", sessionFactory);
System.out.println("in init sessionFactory:" + factoryMap);
} catch (Exception e) {
System.out.println("该错误比较严重,出现在数据源无参构造函数中!!");
e.printStackTrace();
} }
} } } /**
* 手动获取sessionFactory用例
* @param dataSourcePerfix
* @return
* @throws Exception
*/
public SqlSessionFactory getSessionFactory() throws Exception {
SysConfig sc = new SysConfig();
String masterUrl = sc.getProperty("master.url");
String masterDriver = sc.getProperty("master.driver");
String masterUsername = sc.getProperty("master.username");
String masterPassword = sc.getProperty("master.password");
// 创建数据源
DataSourceBuilder create = DataSourceBuilder.create();
create.url(masterUrl);
create.driverClassName(masterDriver);
create.username(masterUsername);
create.password(masterPassword);
DataSource source = create.build();
// 创建sessionFactory
SqlSessionFactoryBean factoryBean = new SqlSessionFactoryBean();
factoryBean.setDataSource(source);// 加载数据源
// 扫描mapper.xml
Resource[] resources = new PathMatchingResourcePatternResolver().getResources("classpath:com/FM/mapper/*.xml");
factoryBean.setMapperLocations(resources);
// 读取config
factoryBean.setConfigLocation(new DefaultResourceLoader().getResource("classpath:mybatis-config.xml"));
SqlSessionFactory sessionFactory = factoryBean.getObject();
return sessionFactory;
} }

  4.3.ExampleController类,代码如下:

  package com.FM.controller;

  import java.util.HashMap;
import java.util.List;
import java.util.Map; import javax.servlet.http.HttpServletRequest; import org.apache.ibatis.session.SqlSession;
import org.apache.ibatis.session.SqlSessionFactory;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController; import com.FM.config.DataConfig; /**
* Controler用于测试
* @author liuyuhang
*/
@RestController //等同于responseBody + controller双重注解
public class ExampleController { /**
* 手动创建session查询数据库用例,该方法可以创建多个sessionFactory,用多线程
* @param request
* @return
* @throws Exception
*/
@RequestMapping("/helloMybatis")
public List helloMybatis(HttpServletRequest request) throws Exception {
//数据源配置无参构造器
DataConfig dc = new DataConfig();
SqlSessionFactory sessionFactory = dc.getSessionFactory();//获取sessionfactory
SqlSession session = sessionFactory.openSession();//获取session
List<Object> selectList = session.selectList("com.FM.mapper.MySqlMapper.getUser");
return selectList;//自动转换为json
}
}

  4.4.AppRun类,代码如下:

 package com.FM;

 import org.springframework.boot.SpringApplication;
import org.springframework.boot.SpringBootConfiguration;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.autoconfigure.jdbc.DataSourceAutoConfiguration;
import org.springframework.boot.web.servlet.ServletComponentScan; import com.FM.config.DataConfig; @SpringBootApplication(exclude = { DataSourceAutoConfiguration.class }) // 禁用默认的单数据源配置
@SpringBootConfiguration // springboot基础配置注解
@ServletComponentScan // springboot servlet filter
// @EnableConfigurationProperties//该注解于springboot1.5以上废弃
public class AppRun { public static void main(String[] args) throws Exception {
SpringApplication.run(AppRun.class, args);
DataConfig dc = new DataConfig();//初始化配置 }
}

  4.5.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.FM.mapper.MySqlMapper">
<!-- 随便写作为测试而已 -->
<resultMap id="getUserMap" type="java.util.Map">
<result column="id" property="id" jdbcType="INTEGER" javaType="int" />
<result column="username" property="username" jdbcType="VARCHAR" javaType="String" /><
<result column="password" property="password" jdbcType="VARCHAR" javaType="String" />
</resultMap>
<select id="getUser" parameterType="java.util.Map" resultMap="getUserMap">
select * from user
</select>
</mapper>

5.测试

  启动后控制台显示如下:

  浏览器输入    http://localhost:8080/helloMybatis

  控制台结果如下图:

  页面结果如下图:

6.总结

  spring注解一直是我饿心结,当我想将我的代码改成以注解方式来进行装配注入的时候,总是不行的,

  于是乎我学会了很多奇葩的手段,可能不主流。

  吐槽归吐槽,学习归学习,工作归工作,一码是一码!!!

  注:本文配置方式会产生几个问题

    要确保手动加载mapper.xml的扫描只扫描一次,否则是否会加载产生多个mapper加入VM管理并不确定,很可能数量很多。

    springboot以这种方式配置的数据源,本质上是交给内置的tomcat来管理的,内置的tomcat来管理会涉及到连接池的问题。

      如果数据库对于连接数量没有扩容,而内置tomcat的连接池没有配置,短时间内会产生大量连接而不销毁,会导致连接      

      拒绝,而报错。

  可能报出的两个常见的错误,主要内容如下:

      a:Error querying database.  Cause: com.mysql.jdbc.exceptions.jdbc4.CommunicationsException: Communications link failure

        Cause: com.mysql.jdbc.exceptions.jdbc4.CommunicationsException: Communications link failure

        The last packet successfully received from the server was 14,595,596 milliseconds ago.  The last packet sent successfully to the server was 14,595,612 milliseconds ago.

 

        该错误的原因通常是因为session没有保证关闭引起的

 

      b: o.a.tomcat.jdbc.pool.ConnectionPool      : Unable to create initial connections of pool.

        Data source rejected establishment of connection,  message from server: "Too many connections"

        

        本示例中使用的是MySql数据库,Threads_connected设置的数值是512,因此报上述错误。

        该错误的原因不仅有Mysql数据库优化的问题,同时也有连接池管理配置的问题

    以上列举问题将在后文中处理,更新后将在文尾插入连接!

  对于以上配置过程的springBoot的注解版,明日再更

 

休息!

以上!

DB数据源之SpringBoot+MyBatis踏坑过程(二)手工配置数据源与加载Mapper.xml扫描的更多相关文章

  1. DB数据源之SpringBoot+Mybatis踏坑过程实录系列(一)

    DB数据源之SpringBoot+MyBatis踏坑过程(一) liuyuhang原创,未经允许进制转载 系列目录 DB数据源之SpringBoot+Mybatis踏坑过程实录(一) DB数据源之Sp ...

  2. DB数据源之SpringBoot+MyBatis踏坑过程(三)手工+半自动注解配置数据源与加载Mapper.xml扫描

    DB数据源之SpringBoot+MyBatis踏坑过程(三)手工+半自动注解配置数据源与加载Mapper.xml扫描 liuyuhang原创,未经允许禁止转载    系列目录连接 DB数据源之Spr ...

  3. DB数据源之SpringBoot+MyBatis踏坑过程(四)没有使用连接池的后果

    DB数据源之SpringBoot+MyBatis踏坑过程(四)没有使用连接池的后果 liuyuhang原创,未经允许禁止转载  系列目录连接 DB数据源之SpringBoot+Mybatis踏坑过程实 ...

  4. DB数据源之SpringBoot+MyBatis踏坑过程(五)手动使用Hikari连接池

    DB数据源之SpringBoot+MyBatis踏坑过程(五)手动使用Hikari连接池 liuyuhang原创,未经允许禁止转载  系列目录连接 DB数据源之SpringBoot+Mybatis踏坑 ...

  5. DB数据源之SpringBoot+MyBatis踏坑过程(七)手动使用Tomcat连接池

    DB数据源之SpringBoot+MyBatis踏坑过程(七)手动使用Tomcat连接池 liuyuhang原创,未经允许禁止转载  系列目录连接 DB数据源之SpringBoot+Mybatis踏坑 ...

  6. DB数据源之SpringBoot+MyBatis踏坑过程(六)mysql中查看连接,配置连接数量

    DB数据源之SpringBoot+MyBatis踏坑过程(六)mysql中查看连接,配置连接数量 liuyuhang原创,未经允许禁止转载 系列目录连接 DB数据源之SpringBoot+Mybati ...

  7. 在mybatis 中批量加载mapper.xml

    可以直接加载一个包文件名,将这个包里的所有*mapper.xml文件加载进来. 指定mapper接口的包名,mybatis自动扫描包下边所有mapper接口进行加载: 必须按一定的标准:即xml文件和 ...

  8. Mybatis热加载Mapper.xml

    开发的时候,写Mybatis Mapper.xml文件的时候,每次修改SQL都需要重启服务,感觉十分麻烦,于是尝试写了一个Mybatis的Mapper.xml热加载. 能在修改Mapper.xml之后 ...

  9. Springboot & Mybatis 构建restful 服务二

    Springboot & Mybatis 构建restful 服务二 1 前置条件 成功执行完Springboot & Mybatis 构建restful 服务一 2 restful ...

随机推荐

  1. How to Build MySQL from Source Code on Windows & compile MySQL on win7+vs2010

    Not counting obtaining the source code, and once you have the prerequisites satisfied, [Windows] use ...

  2. 【Python】回文palindrome——利用字符串反转

    回文 palindrome Python 字符串反转string[::-1] Slice notation "[a : b : c]" means "count in i ...

  3. matlab练习程序(三角形外接圆)

    三角形两边的垂直平分线就能确定外接圆. 结果如下: matlab代码如下: clear all;close all;clc; p=rand(,); %(x,y) cen1=(p(,:)+p(,:))/ ...

  4. IIS6.0配置正常,但是显示“网页无法访问”,Httperr.log中显示全是“Connections_refused”,问题总结

    转自:http://blog.csdn.net/foxeatapple/article/details/21983869 最近部门的Web服务器突然无法访问! 加班解决! 问题症状: 1.“Inter ...

  5. QT5.3.1 Quick 开发(二) 项目类型的选择

    作为一个转行QT开发的新手,面对基于QML的开发时候 看到很多的项目类型感到很困惑,不知道应该怎么选择.如图: 经过研究发现QT widgets Application.QtQuick Applica ...

  6. Windows ->> Windows下一代文件系统 -- Resilient file system(ReFS)

    Comming soon!!! 参考文献: Building the next generation file system for Windows: ReFS ReFS: What you need ...

  7. Web API 2 入门——使用ASP.NET Web API和Angular.js构建单页应用程序(SPA)(谷歌翻译)

    在这篇文章中 概观 演习 概要 由网络营 下载网络营训练包 在传统的Web应用程序中,客户机(浏览器)通过请求页面启动与服务器的通信.然后,服务器处理请求,并将页面的HTML发送给客户端.在与页面的后 ...

  8. 【Leetcode】【Medium】Binary Tree Right Side View

    Given a binary tree, imagine yourself standing on the right side of it, return the values of the nod ...

  9. 【Leetcode】【Medium】Unique Binary Search Trees II

    Given n, generate all structurally unique BST's (binary search trees) that store values 1...n. For e ...

  10. QT的动图加载

    http://blog.csdn.net/u011619422/article/details/47342403