专栏首页架构探险之道[Spring Boot] Spring boot 整合mybatis、postgresql [Gradle构建项目]

[Spring Boot] Spring boot 整合mybatis、postgresql [Gradle构建项目]

[Spring Boot] Spring boot 整合mybatis、postgresql [Gradle构建项目]

[Spring Boot] Spring boot 整合mybatis、postgresql [Gradle构建项目]

依赖关系

下文中libs[“xxx”]的写法是全局管理依赖,具体开发时使用以下格式即可

compile(group: 'org.postgresql', name: 'postgresql', version: '42.2.5', ext: 'pom')

build.gradle:

buildscript {    repositories {
       maven { url = "https://plugins.gradle.org/m2/" }
       maven { url = "http://maven.aliyun.com/nexus/content/groups/public/" }
       jcenter()
   }    dependencies {        classpath libs["spring-boot-gradle-plugin"]
   }
}apply plugin: "idea"apply plugin: "java"apply plugin: "maven"apply plugin: "io.spring.dependency-management"apply plugin: "org.springframework.boot"group = "com.example"version = "1.0.0-SNAPSHOT"sourceCompatibility = 1.8dependencies {    compile "org.springframework.boot:spring-boot-starter-web"   /*分页和mapper插件*/
   compile libs["pagehelper"]    compile libs["mapper"]    /**数据库驱动*/
   compile libs["postgresql"]    compile libs["mybatis-spring-boot-starter"]    /*热部署*/
   compile libs["spring-boot-devtools"]    /*单元测试*/
   testCompile libs["junit"]
   testCompile "org.springframework.boot:spring-boot-starter-test"}

核心配置

启动类

@SpringBootApplication//开启事务@EnableTransactionManagement//Spring Boot实例扫描@ComponentScan(basePackages = "com.example")//Mapper扫描@MapperScan(basePackages = "com.example.core.**.dao")public class BootApp {    public static void main(String[] args) {
       SpringApplication.run(BootApp.class, args);
   }}

application.yaml文件

server:
   port: 8080spring:
 datasource:
   driver-class-name: org.postgresql.Driver
   password: postgres
   username: postgres
   url: jdbc:postgresql://127.0.0.1:5433/postgres
 devtools:
     restart:
       enabled: false#mybatis
mybatis:
 type-aliases-package: com.example.core.**.model
 mapper-locations:  classpath*:mapper/*.xml

代码生成

  • mapper、model采用mybatis-generator-core自动解析数据库生成
  • gradle构建时src/main/java目录下的非.java结尾的文件不会被编译,所以需要将myabtis对应的xml文件移至resources目录,并在application.yaml文件配置路径

配置全局异常拦截

GlobalExceptionHandler

package com.example.config;import com.example.common.api.ApiErrorCode;import com.example.common.api.ApiException;import com.example.common.api.IErrorCode;import com.example.common.beans.ResponseJson;import lombok.extern.slf4j.Slf4j;import org.springframework.validation.BindException;import org.springframework.validation.BindingResult;import org.springframework.web.bind.annotation.ExceptionHandler;import org.springframework.web.bind.annotation.RestControllerAdvice;import java.util.ArrayList;import java.util.HashMap;import java.util.List;import java.util.Map;/**
* <p>
*
* </p>
*
* @author xiachaoyang
* @version V1.0
* @date 2019年01月11日 10:39
* @modificationHistory=========================逻辑或功能性重大变更记录
* @modify By: {修改人} 2019年01月11日
* @modify reason: {方法名}:{原因}
* ...
*/@Slf4j@RestControllerAdvicepublic class GlobalExceptionHandler {    /**
    * <p>
    * 自定义 REST 业务异常
    * <p>
    *
    * @param e 异常类型
    * @return
    */
   @ExceptionHandler(value = Exception.class)    public ResponseJson<Object> handleBadRequest(Exception e) {        /*
        * 业务逻辑异常
        */
       if (e instanceof ApiException) {
           IErrorCode errorCode = ((ApiException) e).getErrorCode();            if (null != errorCode) {
               log.debug("Rest request error, {}", errorCode.toString());                return new ResponseJson().failed(errorCode);
           }
           log.debug("Rest request error, {}", e.getMessage());            return new ResponseJson().failed(e.getMessage());
       }        /*
        * 参数校验异常
        */
       if (e instanceof BindException) {
           BindingResult bindingResult = ((BindException) e).getBindingResult();            if (null != bindingResult && bindingResult.hasErrors()) {
               List<Object> jsonList = new ArrayList<>();
               bindingResult.getFieldErrors().stream().forEach(fieldError -> {
                   Map<String, Object> jsonObject = new HashMap<>(2);
                   jsonObject.put("name", fieldError.getField());
                   jsonObject.put("msg", fieldError.getDefaultMessage());
                   jsonList.add(jsonObject);
               });                return new ResponseJson().failed(jsonList, ApiErrorCode.FAILED);
           }
       }        /**
        * 系统内部异常,打印异常栈
        */
       log.error("Error: handleBadRequest StackTrace : {}", e);        return new ResponseJson().failed(e.getMessage());
   }
}

ApiErrorCode

package com.example.common.api;/**
* <p>
*  REST API 错误码
* </p>
*
* @author xiachaoyang
* @version V1.0
* @date 2019年01月11日 10:48
* @modificationHistory=========================逻辑或功能性重大变更记录
* @modify By: {修改人} 2019年01月11日
* @modify reason: {方法名}:{原因}
* ...
*/public enum ApiErrorCode implements IErrorCode {    /**
    * 失败
    */
   FAILED("0", "失败"),    /**
    * 成功
    */
   SUCCESS("1", "成功");    private final String code;    private final String msg;   ApiErrorCode(final String code, final String msg) {        this.code = code;        this.msg = msg;
   }    public static ApiErrorCode fromCode(String code) {
       ApiErrorCode[] ecs = ApiErrorCode.values();        for (ApiErrorCode ec : ecs) {            if (ec.getCode().equalsIgnoreCase(code)) {                return ec;
           }
       }        return SUCCESS;
   }    @Override
   public String getCode() {        return code;
   }    @Override
   public String getMsg() {        return msg;
   }    @Override
   public String toString() {        return String.format(" ErrorCode:{code=%s, msg=%s} ", code, msg);
   }}

ApiException

package com.example.common.api;/**
* <p>
*
* </p>
*
* @author xiachaoyang
* @version V1.0
* @date 2019年01月11日 10:46
* @modificationHistory=========================逻辑或功能性重大变更记录
* @modify By: {修改人} 2019年01月11日
* @modify reason: {方法名}:{原因}
* ...
*/public class ApiException extends RuntimeException {    /**
    * 错误码
    */
   private IErrorCode errorCode;    public ApiException(IErrorCode errorCode) {        super(errorCode.getMsg());        this.errorCode = errorCode;
   }    public ApiException(String message) {        super(message);
   }    public ApiException(Throwable cause) {        super(cause);
   }    public ApiException(String message, Throwable cause) {        super(message, cause);
   }`在这里插入代码片`    public IErrorCode getErrorCode() {        return errorCode;
   }
}

IErrorCode

package com.example.common.api;/**
* <p>
*  REST API 错误码接口
* </p>
*
* @author xiachaoyang
* @version V1.0
* @date 2019年01月11日 10:46
* @modificationHistory=========================逻辑或功能性重大变更记录
* @modify By: {修改人} 2019年01月11日
* @modify reason: {方法名}:{原因}
* ...
*/public interface IErrorCode {    /**
    * 错误编码 0、失败 1、正常
    */
   String getCode();    /**
    * 错误描述
    */
   String getMsg();}

ResponseJson

package com.example.common.beans;import com.example.common.api.IErrorCode;import lombok.Data;import lombok.experimental.Accessors;/**
* <p>
*
* </p>
*
* @author xiachaoyang
* @version V1.0
* @date 2018年12月27日 17:26
* @modificationHistory=========================逻辑或功能性重大变更记录
* @modify By: {修改人} 2018年12月27日
* @modify reason: {方法名}:{原因}
* ...
*/@Data@Accessors(chain = true)public class ResponseJson<T> {    private String msg;    private String code;    private T data;    public ResponseJson<T> failed(IErrorCode errorCode) {        this.code = errorCode.getCode();        this.msg = errorCode.getMsg();        return this;
   }    public ResponseJson<T> failed(String errorMsg) {        this.code = "-1";        this.msg = errorMsg;        return this;
   }    public ResponseJson<T> ok(T data) {        this.data = data;        this.code = "0";        this.msg = "success";        return this;
   }    public ResponseJson<T> failed(T data, IErrorCode errorCode) {        this.data = data;        this.code = errorCode.getCode();        this.msg = errorCode.getMsg();        return this;
   }
}

效果(json请求参数中非数字字符串无法转数字错误)


本文分享自微信公众号 - 架构探险之道(zacsnz1314)

原文出处及转载信息见文内详细说明,如有侵权,请联系 yunjia_community@tencent.com 删除。

原始发表时间:2019-01-12

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

我来说两句

0 条评论
登录 后参与评论

相关文章

  • Centos7安装postgresql10

    版权声明:本文为博主原创文章,转载请保留出处 ...

    xyjincan
  • 从Oracle到PostgreSQL:最全控制文件

    墨墨导读:本文介绍了Oracle和PostgreSQL控制文件基本内容,对如何重建PostgreSQL控制文件进行了详细描述并进行了恢复测试。

    数据和云
  • CentOS6.7安装PostgreSQL10.9详细教程

    PostgreSQL 是一个基于 POSTGRES 的对象关系数据库管理系统(ORDBMS),版本4.2,由加州大学伯克利分校计算机科学系开发。POSTGRES...

    JiekeXu之路
  • 解读年度数据库PostgreSQL:如何巧妙地实现缓冲区管理器

    墨墨导读:PostgreSQL 已获得 DB-Engines 排行榜 2017 年和2018年的“年度数据库”称号,发展如此迅猛,它究竟有什么内幕呢?接下来,我...

    数据和云
  • PostgreSQL 与大小写的“坑”

    其实每种数据库都有自己的特色,PostgreSQL 也不例外,其中如果你留心PostgreSQL被最常问及的问题之一,就是大小写的问题。今天的讨论不涉及数据库名...

    AustinDatabases
  • 史上最全PostgreSQL体系结构

    墨墨导读:本文主要从日志文件、参数文件、控制文件、数据文件、redo日志(WAL)、后台进程这六个方面来讨论PostgreSQL的结构。

    数据和云
  • Knative 入门系列7:实战演练

    Knative 是一个基于 Kubernetes 的,用于构建、部署和管理现代 serverless 应用的平台。Getting Started with Kn...

    崔秀龙
  • Postgresql 查询中的特异功能 与 开发人员的“大爱”(感谢腾讯自媒体)

    在开始新一周的文字前,先打个广告,最近被腾讯云邀请将文章同步到云社区,很感谢。本身写这个从开始到目前都没有特别的功利心,仅仅是share 一些东西,如果大家看着...

    AustinDatabases
  • 2019全球PostgreSQL生态报告出炉,PG为何从RDBMS中脱颖而出?丨文末送书

    墨墨导读:本文是近期ScaleGrid发布的2019 PG趋势报告,从不同的角度解读了PostgreSQL如何在众多优秀的RDBMS中脱颖而出,原文:https...

    数据和云

扫码关注云+社区

领取腾讯云代金券