All Projects → bootsrc → Flylib Boot

bootsrc / Flylib Boot

spring boo应用的通用架构(全局异常处理等机制)

Programming Languages

java
68154 projects - #9 most used programming language

Projects that are alternatives of or similar to Flylib Boot

Spring Thrift Api Gateway
Gateway for Apache Thrift requests processing that is built on Spring Cloud stack
Stars: ✭ 38 (-15.56%)
Mutual labels:  spring-boot
Spring Jms
Spring JMS Tutorials
Stars: ✭ 42 (-6.67%)
Mutual labels:  spring-boot
Disconf Spring Boot Starter
disconf-spring-boot-starter 让你可以使用spring-boot的方式开发依赖disconf的程序 只需要关心disconfi的配置文件和配置项,省略了编写xml的麻烦
Stars: ✭ 44 (-2.22%)
Mutual labels:  spring-boot
Mastering Microservices With Java Third Edition
Mastering Microservices with Java – Third Edition, published by Packt
Stars: ✭ 39 (-13.33%)
Mutual labels:  spring-boot
Mica Example
mica 演示项目
Stars: ✭ 42 (-6.67%)
Mutual labels:  spring-boot
Juniperbot
Fluffy Discord Bot (Music, Ranking, Reminder, Vk Community bridge,WikiFur) created using JDA
Stars: ✭ 43 (-4.44%)
Mutual labels:  spring-boot
Spring Boot
spring-boot 项目实践总结
Stars: ✭ 989 (+2097.78%)
Mutual labels:  spring-boot
Mini Platform
Mini-Platform致力于更简洁易用的轻量级微服务治理平台。
Stars: ✭ 45 (+0%)
Mutual labels:  spring-boot
Gs Rest Service
Building a RESTful Web Service :: Learn how to create a RESTful web service with Spring.
Stars: ✭ 1,011 (+2146.67%)
Mutual labels:  spring-boot
Ssh Shell Spring Boot
Spring shell in spring boot application over ssh
Stars: ✭ 43 (-4.44%)
Mutual labels:  spring-boot
Depli
A handsome JVM monitoring dashboard
Stars: ✭ 39 (-13.33%)
Mutual labels:  spring-boot
Botwall4j
A botwall for Java web applications
Stars: ✭ 41 (-8.89%)
Mutual labels:  spring-boot
Dynamic Data Source Demo
基于事务的读写分离
Stars: ✭ 43 (-4.44%)
Mutual labels:  spring-boot
Ruoyi
基于SpringBoot2.1的权限管理系统 易读易懂、界面简洁美观。 核心技术采用Spring、MyBatis、Shiro没有任何其它重度依赖。直接运行即可用
Stars: ✭ 991 (+2102.22%)
Mutual labels:  spring-boot
Spring Boot React
Isomorphic React app with Spring Boot
Stars: ✭ 44 (-2.22%)
Mutual labels:  spring-boot
Jpetstore 6 Vaadin Spring Boot
This project is an exercise to port the original JPetStore-6 to Vaadin 8 and Spring Boot.
Stars: ✭ 38 (-15.56%)
Mutual labels:  spring-boot
Oidc Workshop Spring Io 2019
Workshop at Spring I/O 2019 on "Securing Microservices with OpenID Connect and Spring Security 5.1"
Stars: ✭ 43 (-4.44%)
Mutual labels:  spring-boot
Spring Boot Microservice Eureka Zuul Docker
Spring-Boot rest microservices using Eureka, Zuul, Docker. Monitoring with logstash, logback, elasticsearch, kibana
Stars: ✭ 45 (+0%)
Mutual labels:  spring-boot
Sentiment Analysis Twitter Microservices Example
A sample application that demonstrates how to build a graph processing platform to analyze sources of emotional influence on Twitter.
Stars: ✭ 45 (+0%)
Mutual labels:  spring-boot
Pacbot
PacBot (Policy as Code Bot)
Stars: ✭ 1,017 (+2160%)
Mutual labels:  spring-boot

flylib-boot简介

flylib-boot是针对springboot构建的程序的基础框架,专门用于构建程序里的比如统一 异常处理

功能

包含一个Spring Boot的一些常见的基础组件的设置

  1. 针对Handler的全局的异常处理(处理所有Controller里的Handler里抛出的异常)
  2. Filter
  3. Interceptor

注意:SpringBoot(SpringMVC)里的Handler特指@Controller注解的类里的每个处理HTTP请求的一个public method.

使用方法

  • Step 1: 进入目录flylib-boot-starter,执行mvn install
  • Step 2: 在自己的项目中添加flylib-boot-starter的maven依赖. 并留意自己使用的spring-boot版本,去修改自己的pom.xml文件
<dependency>
    <groupId>org.flylib</groupId>
    <artifactId>flylib-boot-starter</artifactId>
    <version>1.0-SNAPSHOT</version>
</dependency>

并且要注意这里spring-boot版本是1.5.0.RELEASE. 另外需要添加spring-boot-maven-plugin 实例参考spring-boot-demo项目,它的pom如下:

<?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>org.flylib</groupId>
    <artifactId>flylib-boot-demo</artifactId>
    <version>1.0-SNAPSHOT</version>
    <packaging>jar</packaging>

    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>1.5.0.RELEASE</version>
        <relativePath/> <!-- lookup parent from repository -->
    </parent>

    <properties>
        <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
        <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
        <java.version>1.8</java.version>
    </properties>

    <dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
            <scope>test</scope>
        </dependency>
        <dependency>
            <groupId>org.flylib</groupId>
            <artifactId>flylib-boot-starter</artifactId>
            <version>1.0-SNAPSHOT</version>
        </dependency>
    </dependencies>
    <build>
        <plugins>
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
            </plugin>
        </plugins>
    </build>
</project>

  • Step 3: 在自己的程序中new 一个UserException(自定义的异常类)设置捕获异常
/**
 * 用户信息的异常
 */
public class UserException extends RuntimeException{

}


@RequestMapping("")
    public String index() throws RuntimeException {
        UserException userException = new UserException();
        CustomRuntimeException cause = new CustomRuntimeException("001", "User not exists");
        userException.initCause(cause);
        throw userException;
    }
  • Step 4: 运行自己的Spring Boot项目 输出到浏览器的结果
{
    code:"001",
    message:"User not exists",
    throwable:{...}
}

实现原理

利用了@ControllerAdvice和@ExceptionHandler 实现代码是

package org.flylib.boot.starter.handler;

import org.flylib.boot.starter.exception.CustomRuntimeException;
import org.flylib.boot.starter.exception.UnknownResourceException;
import org.flylib.boot.starter.exception.ValidationRuntimeException;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.TypeMismatchException;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.MessageSource;
import org.springframework.core.env.Environment;
import org.springframework.http.HttpStatus;
import org.springframework.http.converter.HttpMessageNotReadableException;
import org.springframework.ui.Model;
import org.springframework.web.HttpMediaTypeNotAcceptableException;
import org.springframework.web.HttpMediaTypeNotSupportedException;
import org.springframework.web.HttpRequestMethodNotSupportedException;
import org.springframework.web.bind.MissingServletRequestParameterException;
import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.context.request.ServletWebRequest;
import org.springframework.web.servlet.LocaleResolver;
import org.springframework.web.servlet.mvc.multiaction.NoSuchRequestHandlingMethodException;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.util.HashMap;
import java.util.LinkedHashMap;
import java.util.Locale;
import java.util.Map;

/**
 * 说明:
 *
 * @ControllerAdvice是controller的一个辅助类,最常用的就是作为全局异常处理的切面类
 * @ControllerAdvice可以指定扫描范围
 * @ControllerAdvice约定了几种可行的返回值,如果是直接返回model类的话,需要使用@ResponseBody进行json转换 返回String,表示跳到某个view
 * 返回modelAndView
 * 返回model + @ResponseBody
 * 全局异常处理
 */
@ControllerAdvice
public class GlobalExceptionHandler {

    private static final Logger log = LoggerFactory.getLogger(GlobalExceptionHandler.class);

    @Autowired
    private Environment env;

    @Autowired(required = false)
    private MessageSource messageSource;

    @Autowired(required = false)
    private LocaleResolver localeResolver;

    private static final String defaultMoreInfoUrl = "";

    private final Map<String,HttpStatus> DEFAULT_EXCEPTION_MAPPING_DEFINITIONS;

    public GlobalExceptionHandler() {
        DEFAULT_EXCEPTION_MAPPING_DEFINITIONS = createDefaultExceptionMappingDefinitions();
    }

    @ExceptionHandler//处理所有异常
    @ResponseBody //在返回自定义相应类的情况下必须有,这是@ControllerAdvice注解的规定
    public Map<String,Object> exceptionHandler(Throwable e, HttpServletRequest request, HttpServletResponse response, Model model) {
        //
        log.error("handle error:",e);

        HttpStatus httpStatus = DEFAULT_EXCEPTION_MAPPING_DEFINITIONS.get(e.getClass().getName());
        if(httpStatus==null){
            httpStatus = HttpStatus.INTERNAL_SERVER_ERROR;
        }
        //是否是生产环境
        boolean isProd = "prod".equals(env.getActiveProfiles()[0]);
        Map<String,Object> map = new HashMap<String,Object>();
        if(e.getCause() instanceof CustomRuntimeException){
            CustomRuntimeException exception = (CustomRuntimeException) e.getCause();
            map.put("code",String.valueOf(exception.getCode()));
            map.put("message",exception.getMessage());
        }else if(e.getCause() instanceof ValidationRuntimeException){
            ValidationRuntimeException exception = (ValidationRuntimeException) e.getCause();
            map.put("code",String.valueOf(exception.getCode()));
            map.put("message",exception.getMessage());
            httpStatus = HttpStatus.BAD_REQUEST;
        }else {
            map.put("code",String.valueOf(httpStatus.value()));
            map.put("message",httpStatus.toString());
        }


        //不是生产环境,添加调试信息
        if(!isProd){
            map.put("throwable",e);
        }
        response.setStatus(httpStatus.value());
        return map;
    }

    protected final Map<String,HttpStatus> createDefaultExceptionMappingDefinitions() {

        Map<String,HttpStatus> m = new LinkedHashMap<String, HttpStatus>();

        // 400
        applyDef(m, HttpMessageNotReadableException.class, HttpStatus.BAD_REQUEST);
        applyDef(m, MissingServletRequestParameterException.class, HttpStatus.BAD_REQUEST);
        applyDef(m, TypeMismatchException.class, HttpStatus.BAD_REQUEST);
        applyDef(m, "javax.validation.ValidationException", HttpStatus.BAD_REQUEST);

        // 404
        applyDef(m, NoSuchRequestHandlingMethodException.class, HttpStatus.NOT_FOUND);
        applyDef(m, "org.hibernate.ObjectNotFoundException", HttpStatus.NOT_FOUND);

        // 405
        applyDef(m, HttpRequestMethodNotSupportedException.class, HttpStatus.METHOD_NOT_ALLOWED);

        // 406
        applyDef(m, HttpMediaTypeNotAcceptableException.class, HttpStatus.NOT_ACCEPTABLE);

        // 409
        //can't use the class directly here as it may not be an available dependency:
        applyDef(m, "org.springframework.dao.DataIntegrityViolationException", HttpStatus.CONFLICT);

        // 415
        applyDef(m, HttpMediaTypeNotSupportedException.class, HttpStatus.UNSUPPORTED_MEDIA_TYPE);
        applyDef(m, UnknownResourceException.class, HttpStatus.NOT_FOUND);

        return m;
    }
    private void applyDef(Map<String,HttpStatus> m, Class clazz, HttpStatus status) {
        applyDef(m, clazz.getName(), status);
    }

    private void applyDef(Map<String,HttpStatus> m, String key, HttpStatus status) {
        m.put(key, status);
    }



    protected String getMessage(String msg, ServletWebRequest webRequest, Exception ex) {

        if (msg != null) {
            if (msg.equalsIgnoreCase("null") || msg.equalsIgnoreCase("off")) {
                return null;
            }
            msg = ex.getMessage();
            if (messageSource != null) {
                Locale locale = null;
                if (localeResolver != null) {
                    locale = localeResolver.resolveLocale(webRequest.getRequest());
                }
                msg = messageSource.getMessage(msg, null, msg, locale);
            }
        }

        return msg;
    }
}

Note that the project description data, including the texts, logos, images, and/or trademarks, for each open source project belongs to its rightful owner. If you wish to add or remove any projects, please contact us at [email protected].