springboot整合mybatis
直接截图:
1.新建springboot项目 | 2.选址jdk版本 |
3.测试项目命名com.zsw.two | 4.选择jar,这里我准备使用lomback记录日志,可不选 |
5.选择项目web | 6.选sql的jar包依赖:我用的是mysql |
7.新建项目完成,注意:project location要有\项目名 | 8.建立后的项目结构 |
9.项目依赖: pom.xml
<?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>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.1.4.RELEASE</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<groupId>com.zsw</groupId>
<artifactId>two</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>two</name>
<description>Demo project for Spring Boot</description>
<properties>
<java.version>1.8</java.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-jdbc</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.mybatis.spring.boot</groupId>
<artifactId>mybatis-spring-boot-starter</artifactId>
<version>2.0.1</version>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<scope>runtime</scope>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<optional>true</optional>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>druid</artifactId>
<version>1.1.10</version>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
</project>
10.个人感觉application配置文件yml格式更好用,就直接把application文件改为.yml了
server:
port: 6789
spring:
datasource:
url: jdbc:mysql://localhost:3306/zulin-dev?autoReconnect=true&useUnienabledcode=true&characterEncoding=utf8&zeroDateTimeBehavior=convertToNull
username: root
password: root
driver-class-name: com.mysql.cj.jdbc.Driver
# 使用druid数据源
type: com.alibaba.druid.pool.DruidDataSource
filters: stat
maxActive: 20
initialSize: 1
maxWait: 60000
minIdle: 1
timeBetweenEvictionRunsMillis: 60000
minEvictableIdleTimeMillis: 300000
validationQuery: select 'x'
testWhileIdle: true
testOnBorrow: false
testOnReturn: false
poolPreparedStatements: true
maxOpenPreparedStatements: 20
11.到这里就是springboot项目的建立,写个测试类,验证springboot项目:
|
|
12.开始集成mybatis: 首先application.yml新增mybatis相关配置:
mybatis:
#xml文件的映射地址 放在resources下
mapper-locations: classpath:mapper/*/*.xml
configuration:
#驼峰
map-underscore-to-camel-case: true
mapper-scanner:
#mapper.java文件的jar包地址
base-package: com.zsw.two.*.mapper
#实体类jar包地址
type-aliases-package: com.zsw.two.*.entity
13.新的项目层级结构:
14.VehicleMapper.java 注意:此处加注释@Repository,否则serviceImpl中注入时会报错,另外在
TwoApplication上加注释@MapperScan,如图19
package com.zsw.two.vehicle.mapper;
import org.springframework.stereotype.Repository;
import com.zsw.two.vehicle.entity.Vehicle;
/**
* 车辆信息 mapper
*
* @author zhangshiwei
* @since 2019年4月15日 下午11:41:57
*/
@Repository
public interface VehicleMapper {
/**
* 根据车辆主键id查询车辆信息
*
* @param condition 车辆id
* @return 查询结果
*/
Vehicle findVehicleById(Vehicle condition);
}
15.VehicleService
package com.zsw.two.vehicle.service;
import com.zsw.two.vehicle.entity.Vehicle;
/**
* 车辆信息 服务类接口
*
* @author zhangshiwei
* @since 2019年4月15日 下午11:42:27
*/
public interface VehicleService {
/**
* 根据车辆主键id查询车辆信息
*
* @param condition 车辆id
* @return 查询结果
*/
Vehicle findVehicleById(Vehicle condition);
}
16.VehicleServiceImpl
package com.zsw.two.vehicle.service.impl;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import com.zsw.two.vehicle.entity.Vehicle;
import com.zsw.two.vehicle.mapper.VehicleMapper;
import com.zsw.two.vehicle.service.VehicleService;
/**
* 车辆信息 服务实现类
*
* @author zhangshiwei
* @since 2019年4月15日 下午11:42:55
*/
@Service
public class VehicleServiceImpl implements VehicleService {
@Autowired
private VehicleMapper vehicleMapper;
@Override
public Vehicle findVehicleById(Vehicle condition) {
if (condition.getId() == null) {
return null;
}
return vehicleMapper.findVehicleById(condition);
}
}
17.VehicleController
package com.zsw.two.vehicle.web;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;
import com.zsw.two.vehicle.entity.Vehicle;
import com.zsw.two.vehicle.service.VehicleService;
/**
* 车辆信息 控制类
*
* @author zhangshiwei
* @since 2019年4月15日 下午11:43:35
*/
@RequestMapping("/vehicle")
@Controller
public class VehicleController {
@Autowired
private VehicleService vehicleService;
/**
* 根据车辆主键id查询车辆信息
*
* @param condition 车辆id
* @return 查询结果
*/
@RequestMapping("/findVehicleById")
@ResponseBody
public Vehicle findVehicleById(@RequestBody Vehicle condition) {
return vehicleService.findVehicleById(condition);
}
}
18.VehicleMapper.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.zsw.two.vehicle.mapper.VehicleMapper">
<!-- 通用查询映射结果 -->
<resultMap id="BaseResultMap" type="com.zsw.two.vehicle.entity.Vehicle">
<id column="id" property="id" />
<result column="vehicle_code" property="vehicleCode" />
<result column="vehicle_brand_id" property="vehicleBrandId" />
<result column="vehicle_brand_name" property="vehicleBrandName" />
<result column="vehicle_vendor_id" property="vehicleVendorId" />
<result column="vehicle_vendor_name" property="vehicleVendorName" />
<result column="vehicle_series_id" property="vehicleSeriesId" />
<result column="vehicle_series_name" property="vehicleSeriesName" />
<result column="vehicle_type_id" property="vehicleTypeId" />
<result column="vehicle_type_name" property="vehicleTypeName" />
<result column="vehicle_color" property="vehicleColor" />
</resultMap>
<sql id="Base_Column">
id as id,
vehicle_code as vehicleCode,
vehicle_brand_id as vehicleBrandId,
vehicle_brand_name as vehicleBrandName,
vehicle_vendor_id as vehicleVendorId,
vehicle_vendor_name as vehicleVendorName,
vehicle_series_id as vehicleSeriesId,
vehicle_series_name as vehicleSeriesName,
vehicle_type_id as vehicleTypeId,
vehicle_type_name as vehicleTypeName,
vehicle_color as vehicleColor
</sql>
<select id="findVehicleById" resultType="com.zsw.two.vehicle.entity.Vehicle"
parameterType="com.zsw.two.vehicle.entity.Vehicle">
SELECT
<include refid="Base_Column"/>
from t_vehicle t
where
t.is_deleted = 'N'
<if test="id != null and id != ''">
and t.id = #{id}
</if>
</select>
</mapper>
19.TwoApplication加注解@MapperScan:
package com.zsw.two;
import org.mybatis.spring.annotation.MapperScan;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
@MapperScan("com.zsw.two.*.mapper")
@SpringBootApplication
public class TwoApplication {
public static void main(String[] args) {
SpringApplication.run(TwoApplication.class, args);
}
}
20.测试:
21.虽然结果对了,但是,控制台没有输出日志,application.yml增加日志输出配置,并输出日志文件:
# 记录日志文件
logging:
config: classpath:logback.xml
22.logback.xml 注意:此配置文件的地址是resources下的log内的! 要和application.yml设置的一致!
<?xml version="1.0" encoding="UTF-8"?>
<configuration>
<!-- %m输出的信息, %p日志级别, %t线程名, %d日期, %c类的全名, %i索引 -->
<!-- appender是configuration的子节点,是负责写日志的组件 -->
<!-- ConsoleAppender把日志输出到控制台 -->
<!-- <property name="CONSOLE_LOG_PATTERN" -->
<!-- value="%date{yyyy-MM-dd HH:mm:ss} | %highlight(%-5level) | %boldYellow(%thread) | %boldGreen(%logger) | %msg%n"/> -->
<appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">
<encoder>
<!--<pattern>${CONSOLE_LOG_PATTERN}</pattern> -->
<!--<pattern>%date{yyyy-MM-dd HH:mm:ss} %highlight(%-5level) (%file:%line\)- %m%n</pattern>-->
<!--<pattern>%d{HH:mm:ss.SSS} %contextName [%thread] %-5level %logger{360} - %msg%n</pattern>-->
<pattern>%d [%thread] %highlight(%-5level) [%c] [%F:%L] [trace=%X{traceId}] - %msg%n</pattern>
<!-- 控制台也要使用utf-8,不要使用gbk -->
<charset>UTF-8</charset>
</encoder>
</appender>
<!-- RollingFileAppender:滚动记录文件,先将日志记录到指定文件,当符合某个条件时,将日志记录到其他文件 -->
<!-- 1.先按日期存日志,日期变了,将前一天的日志文件名重命名为xxx%日期%索引,新的日志仍然是sys.log -->
<!-- 2.如果日期没有变化,但是当前日志文件的大小超过1kb时,对当前日志进行分割 重名名 -->
<appender name="syslog" class="ch.qos.logback.core.rolling.RollingFileAppender">
<File>mylog/sys.log</File>
<!-- rollingPolicy:当发生滚动时,决定 RollingFileAppender 的行为,涉及文件移动和重命名。 -->
<!-- TimeBasedRollingPolicy: 最常用的滚动策略,它根据时间来制定滚动策略,既负责滚动也负责出发滚动 -->
<rollingPolicy class="ch.qos.logback.core.rolling.TimeBasedRollingPolicy">
<!-- 活动文件的名字会根据fileNamePattern的值,每隔一段时间改变一次 -->
<!-- 文件名:log/sys.2017-12-05.0.log -->
<fileNamePattern>mylog/sys.%d.%i.log</fileNamePattern>
<!-- 每产生一个日志文件,该日志文件的保存期限为30天 -->
<maxHistory>30</maxHistory>
<timeBasedFileNamingAndTriggeringPolicy class="ch.qos.logback.core.rolling.SizeAndTimeBasedFNATP">
<!-- maxFileSize:这是活动文件的大小,默认值是10MB,本篇设置为1KB,只是为了演示 -->
<maxFileSize>10240KB</maxFileSize>
</timeBasedFileNamingAndTriggeringPolicy>
</rollingPolicy>
<encoder>
<!-- pattern节点,用来设置日志的输入格式 -->
<pattern>
%d %p (%file:%line\)- %m%n
</pattern>
<!-- 记录日志的编码 -->
<charset>UTF-8</charset> <!-- 此处设置字符集 -->
</encoder>
</appender>
<!-- 控制台日志输出级别 -->
<root level="INFO">
<appender-ref ref="STDOUT" />
</root>
<!-- 指定项目中某个包,当有日志操作行为时的日志记录级别 -->
<!-- com.appley为根包,也就是只要是发生在这个根包下面的所有日志操作行为的权限都是DEBUG -->
<!-- 级别依次为【从高到低】:FATAL > ERROR > WARN > INFO > DEBUG > TRACE -->
<logger name="com.zsw.two" level="DEBUG">
<appender-ref ref="syslog" />
</logger>
</configuration>
23.为了追踪同一个线程的日志,在日志中加了tranceId,子线程会从父线程中拿取,方便查找统一线程的日志,定位问题所在!
加pom.xml依赖:
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-aop</artifactId>
<version>4.3.10.RELEASE</version>
</dependency>
<dependency>
<groupId>org.aspectj</groupId>
<artifactId>aspectjweaver</artifactId>
<version>1.8.13</version>
</dependency>
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>fastjson</artifactId>
<version>1.2.37</version>
</dependency>
24.处理日志的aop
package com.zsw.two.log;
import javax.servlet.http.HttpServletRequest;
import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.annotation.AfterReturning;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Before;
import org.aspectj.lang.annotation.Pointcut;
import org.slf4j.MDC;
import org.springframework.stereotype.Component;
import org.springframework.web.context.request.RequestContextHolder;
import org.springframework.web.context.request.ServletRequestAttributes;
import com.alibaba.fastjson.JSON;
import com.fasterxml.jackson.annotation.JsonInclude;
import com.fasterxml.jackson.databind.ObjectMapper;
import lombok.extern.slf4j.Slf4j;
/**
* 统一日志追踪处理器
*/
@Slf4j
@Component
@Aspect
public class ControllerLogAop {
@Pointcut(value = "execution(* com.zsw.two.*.web..*.*(..))")
public void controllerMethodPointcut() {
}
@Before("controllerMethodPointcut()")
public void controllerMethodPointcutBefore(JoinPoint joinPoint) throws Exception {
String traceId = String.valueOf(System.currentTimeMillis());
MDC.put("traceId", traceId);
ServletRequestAttributes attributes = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();
HttpServletRequest request = attributes.getRequest();
StringBuffer requestLog = new StringBuffer();
requestLog.append("controller请求结果请求信息:")
.append("URL = {" + request.getRequestURI() + "},\t")
.append("HTTP_METHOD = {" + request.getMethod() + "},\t")
.append("IP = {" + request.getRemoteAddr() + "},\t")
.append("CLASS_METHOD = {" + joinPoint.getSignature().getDeclaringTypeName() + "."
+ joinPoint.getSignature().getName() + "},\t");
if (joinPoint.getArgs().length == 0) {
requestLog.append("ARGS = {} ");
} else {
requestLog.append("ARGS = " + new ObjectMapper().setSerializationInclusion(JsonInclude.Include.NON_NULL)
.writeValueAsString(joinPoint.getArgs()[0]) + "");
}
log.info(requestLog.toString());
}
@AfterReturning(returning = "returnValue", pointcut = "controllerMethodPointcut()")
public void logPageInfoAfterReturning(JoinPoint joinPoint, Object returnValue) {
log.info("controller请求结果:{}", JSON.toJSON(returnValue));
}
}
25.最终的日志打印结果:
2019-04-16 00:51:03,074 [http-nio-6789-exec-2] INFO [org.apache.catalina.core.ContainerBase.[Tomcat].[localhost].[/]] [DirectJDKLog.java:173] [trace=] - Initializing Spring DispatcherServlet 'dispatcherServlet' 2019-04-16 00:51:03,074 [http-nio-6789-exec-2] INFO [org.springframework.web.servlet.DispatcherServlet] [FrameworkServlet.java:524] [trace=] - Initializing Servlet 'dispatcherServlet' 2019-04-16 00:51:03,109 [http-nio-6789-exec-2] INFO [org.springframework.web.servlet.DispatcherServlet] [FrameworkServlet.java:546] [trace=] - Completed initialization in 35 ms 2019-04-16 00:51:03,216 [http-nio-6789-exec-2] INFO [com.zsw.two.log.ControllerLogAop] [ControllerLogAop.java:56] [trace=1555347063197] - controller请求结果请求信息:URL = {/vehicle/findVehicleById}, HTTP_METHOD = {POST}, IP = {0:0:0:0:0:0:0:1}, CLASS_METHOD = {com.zsw.two.vehicle.web.VehicleController.findVehicleById}, ARGS = {"id":3450} 2019-04-16 00:51:03,312 [http-nio-6789-exec-2] INFO [com.alibaba.druid.pool.DruidDataSource] [DruidDataSource.java:930] [trace=1555347063197] - {dataSource-1} inited 2019-04-16 00:51:03,865 [http-nio-6789-exec-2] DEBUG [com.zsw.two.vehicle.mapper.VehicleMapper.findVehicleById] [BaseJdbcLogger.java:143] [trace=1555347063197] - ==> Preparing: SELECT id as id, vehicle_code as vehicleCode, vehicle_brand_id as vehicleBrandId, vehicle_brand_name as vehicleBrandName, vehicle_vendor_id as vehicleVendorId, vehicle_vendor_name as vehicleVendorName, vehicle_series_id as vehicleSeriesId, vehicle_series_name as vehicleSeriesName, vehicle_type_id as vehicleTypeId, vehicle_type_name as vehicleTypeName, vehicle_color as vehicleColor from t_vehicle t where t.is_deleted = 'N' and t.id = ? 2019-04-16 00:51:03,885 [http-nio-6789-exec-2] DEBUG [com.zsw.two.vehicle.mapper.VehicleMapper.findVehicleById] [BaseJdbcLogger.java:143] [trace=1555347063197] - ==> Parameters: 3450(Long) 2019-04-16 00:51:03,958 [http-nio-6789-exec-2] DEBUG [com.zsw.two.vehicle.mapper.VehicleMapper.findVehicleById] [BaseJdbcLogger.java:143] [trace=1555347063197] - <== Total: 1 2019-04-16 00:51:04,031 [http-nio-6789-exec-2] INFO [com.zsw.two.log.ControllerLogAop] [ControllerLogAop.java:61] [trace=1555347063197] - controller请求结果:{"vehicleColor":"宝石青金属漆","vehicleSeriesId":162,"vehicleTypeId":3529,"vehicleVendorName":"华晨宝马","vehicleVendorId":20,"vehicleBrandId":7,"vehicleBrandName":"宝马","vehicleCode":"V15517665610000002064","id":3450,"vehicleSeriesName":"5系","vehicleTypeName":"2018款 528Li 上市特别版"} |
26.再次强调我踩的坑! @MapperScan的jar包必须正确!yml中配置的地址必须正确!
27.集成thymeleaf模板展示数据到前台,首先添加pom依赖:
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-thymeleaf</artifactId>
<version>2.2.0.M1</version>
</dependency>
28.添加yml配置:
spring:
#Thymeleaf配置
thymeleaf:
prefix: classpath:/templates/
suffix: .html
mode: HTML
encoding: UTF-8
cache: false
#取消缓存,修改即可见
resources:
chain:
strategy:
content:
enabled: true
paths: /**
29.新建html和css,测试:
vehicleList.html |
|
test.css |
|
测试方法: |
|
测试结果: |
30.td出现双边框,修改css
body {
color: black;
}
table {
border-right: 1px solid #F00;
border-bottom: 1px solid #F00
}
table td {
border-left: 1px solid #F00;
border-top: 1px solid #F00
}
31.再次测试,结果:
32.springboot会自己去templates下查询匹配html静态文件,去static下查询匹配css文件和js文件,在html中引入js和css文件:
<link rel="stylesheet" href="../test/test.css" type="text/css" />注意文件层级结构即可;
推荐阅读
-
Vue整合AdminLTE模板的方法
-
Mybatis中SqlSessionFactory和SqlSession学习和原理
-
yii2整合百度编辑器umeditor,yii2整合umeditor
-
yii2整合百度编辑器umeditor apk编辑器 apk editor pro editor文本编辑器 百度编辑器uedito
-
springboot系列之03-使用IDEA完成第一个示例程序
-
网站用php实现paypal整合方法_php技巧
-
原创001 | 搭上SpringBoot自动注入源码分析专车
-
小白的springboot之路(七)、事务支持
-
SpringBoot 2.0 开发案例之百倍级减肥瘦身之旅
-
SparkStreaming整合Flume的pull方式之启动报错解决方案