common.exception、annotation、node、page

说明

如果您有幸能看到,请认阅读以下内容;

  • 1、本项目临摹自abel533的Guns,他的项目 fork 自 stylefeng 的 Guns!开源的世界真好,可以学到很多知识。
  • 2、版权归原作者所有,自己只是学习使用。跟着大佬的思路,希望自己也能变成大佬。gogogo》。。
  • 3、目前只是一个后台模块,希望自己技能增强到一定时,可以把stylefeng 的 [Guns]融合进来。
  • 4、note里面是自己的学习过程,菜鸟写的,不是大佬写的。内容都是大佬的。

异常

1、首先来看所有业务异常的枚举类,看异常大概就能知道这个系统主要完成那些业务逻辑。

/*** 所有业务异常的枚举*/
public enum BizExceptionEnum {/*** 字典*/DICT_EXISTED(400,"字典已经存在"),ERROR_CREATE_DICT(500,"创建字典失败"),ERROR_WRAPPER_FIELD(500,"包装字典属性失败"),/*** 文件上传*/FILE_READING_ERROR(400,"FILE_READING_ERROR!"),FILE_NOT_FOUND(400,"FILE_NOT_FOUND!"),UPLOAD_ERROR(500,"上传图片出错"),/*** 权限和数据问题*/DB_RESOURCE_NULL(400,"数据库中没有该资源"),NO_PERMITION(405, "权限异常"),REQUEST_INVALIDATE(400,"请求数据格式不正确"),INVALID_KAPTCHA(400,"验证码不正确"),CANT_DELETE_ADMIN(600,"不能删除超级管理员"),CANT_FREEZE_ADMIN(600,"不能冻结超级管理员"),CANT_CHANGE_ADMIN(600,"不能修改超级管理员角色"),/*** 账户问题*/USER_ALREADY_REG(401,"该用户已经注册"),NO_THIS_USER(400,"没有此用户"),USER_NOT_EXISTED(400, "没有此用户"),ACCOUNT_FREEZED(401, "账号被冻结"),OLD_PWD_NOT_RIGHT(402, "原密码不正确"),TWO_PWD_NOT_MATCH(405, "两次输入密码不一致"),/*** 错误的请求*/MENU_PCODE_COINCIDENCE(400,"菜单编号和副编号不能一致"),EXISTED_THE_MENU(400,"菜单编号重复,不能添加"),DICT_MUST_BE_NUMBER(400,"字典的值必须为数字"),REQUEST_NULL(400, "请求有错误"),SESSION_TIMEOUT(400, "会话超时"),SERVER_ERROR(500, "服务器异常");BizExceptionEnum(int code, String message) {this.friendlyCode = code;this.friendlyMsg = message;}private int friendlyCode;private String friendlyMsg;private String urlPath;//Setter,Getter,Constractor略BizExceptionEnum(int code, String message) {this.friendlyCode = code;this.friendlyMsg = message;}
}

2、对业务异常的封装,首先需要注意的是继承自RuntimeException,之前讲过了点这里

/*** 业务异常的封装*/
public class BussinessException extends RuntimeException {//友好提示的code码private int friendlyCode;//友好提示private String friendlyMsg;//业务异常调整页面private String urlPath;public BussinessException(BizExceptionEnum bizExceptionEnum) {this.friendlyCode = bizExceptionEnum.getCode();this.friendlyMsg = bizExceptionEnum.getMessage();this.urlPath = bizExceptionEnum.getUrlPath();}
}

3、接下来是工具类初始化异常,需要注意serialVersionUID的作用:

  • 1、serialVersionUID 是 Java 为每个序列化类产生的版本标识,可用来保证在反序列时,发送方发送的和接受方接收的是可兼容的对象。
  • 2、如果接收方接收的类的 serialVersionUID 与发送方发送的 serialVersionUID 不一致,进行反序列时会抛出 InvalidClassException。
  • 3、序列化的类可显式声明 serialVersionUID 的值,

这个中定义异常和PayMap中定义方式几乎一样。

/*** 工具类初始化*/
public class ToolBoxException extends RuntimeException {//serialVersionUID 是 Java 为每个序列化类产生的版本标识,可用来保证在反序列时,发送方发送的和接受方接收的是可兼容的对象。// 如果接收方接收的类的 serialVersionUID 与发送方发送的 serialVersionUID 不一致,进行反序列时会抛出 InvalidClassException。序列化的类可显式声明 serialVersionUID 的值,private static final long serialVersionUID = 8247610319171014183L;public ToolBoxException(Throwable e) {super(e.getMessage(),e);}public ToolBoxException(String message) {super(message);}public ToolBoxException(String message, Throwable throwable) {super(message,throwable);}public ToolBoxException(String messageTemplate, Object...params) {super(StrKit.format(messageTemplate,params));}
}
--------------------------------------------------------------------------------
/*** 验证码错误异常** @Author guo             //这个模板不错* @Date 2018-03-04 12:04.*/
public class InvalidKaptchaException extends RuntimeException {
}

注解

4、最后在看下自定义注解

元注解:

元注解的作用就是负责注解其他注解。Java5.0定义了4个标准的meta-annotation类型,它们被用提供对其他annotation类型的说明。

  • 1、@Target
  • 2、@Retention
  • 3、@Documented
  • 4、@Inherited

-
@Target

作用:用于描述注解的使用范围(即:被描述的注解可以用在什么地方)

取值(ElementType)有:

  • 1.CONSTRUCTOR:用于描述构造器
  • 2.FIELD:用于描述域
  • 3.LOCAL_VARIABLE:用于描述局部变量
  • 4.METHOD:用于描述方法
  • 5.PACKAGE:用于描述包
  • 6.PARAMETER:用于描述参数
  • 7.TYPE:用于描述类、接口(包括注解类型) 或enum声明

@Retention

作用:表示需要在什么级别保存该注释信息,用于描述注解的生命周期(即:被描述的注解在什么范围内有效)

取值(RetentionPoicy)有:

  • 1.SOURCE:在源文件中有效(即源文件保留)
  • 2.CLASS:在class文件中有效(即class保留)
  • 3.RUNTIME:在运行时有效(即运行时保留)

@Documented

作用:用于描述其它类型的annotation应该被作为被标注的程序成员的公共API,因此可以被例如javadoc此类的工具文档化。

@Inherited

@Inherited元注解是一个标记注解,@Inherited阐述了某个被标注的类型是被继承的。如果一个使用了@Inherited修饰的annotation类型被用于一个class,则这个annotation将被用于该class的子类。

接下来,我们在看自定义注解

/*** 权限注解,用于检查权限 规定访问权限*/
@Inherited
@Retention(RetentionPolicy.RUNTIME)   //运行时有效
@Target({ElementType.METHOD})         //方法范围
public @interface Permission {String[] value() default {};
}
-------------------------------------------------------
/*** 多数据源标识*/
@Inherited
@Retention(RetentionPolicy.RUNTIME)
@Target({ ElementType.METHOD })
public @interface DataSource {
}
---------------------------------------------------------
/*** 标记需要做业务日志的方法*/
@Inherited
@Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.METHOD})
public @interface BussinessLog {/*** 业务的名称,例如:"修改菜单"*/String value() default "";/*** 被修改的实体的唯一标识,例如:菜单实体的唯一标识为"id"*/String key() default "id";/*** 字典(用于查找key的中文名称和字段的中文名称)*/String dict() default "SystemDict";
}

5、先来看Node类的定义吧,

ZTree is an advanced jQuery 'tree plug-in'. The performance is excellent, it is easy to configurw (with a full set of options), and has many advanced features (that usually only come with paid software).

zTree is open source and uses the MIT license.

  • Supports JSON data.
  • Supports both static and asynchronous (Ajax) data loading.
  • Supports multiple instances of zTree in one page.
  • zTree3.0 can use lazy loading for large data, it can easily load tens of thousands of nodes in seconds even in the IE6 browser.
  • ...

The most important is the official document to the very full(English is very important, important and important.)

ZTreeNode定义:

/*** jquery ztree 插件的节点*/
public class ZTreeNode {/*** 节点id*/private Integer id;/*** 父节点id*/private Integer pId;/*** 节点名称*/private String name;/*** 是否打开节点*/private Boolean open;/*** 是否被选中*/private Boolean checked;//Setter、Getter、Constructor、toString忽略
}

MenuNode实现了Compareable接口,重写了compareTo()方法完整代码在这


@Override
public int compareTo(Object o) {MenuNode menuNode = (MenuNode) o;Integer num = menuNode.getNum();if (num == null) {num = 0;}return this.num.compareTo(num);
}
/**** 菜单的节点*/
public class MenuNode implements Comparable {/*** 节点id*/private Integer id;/*** 父节点*/private Integer parentId;/*** 节点名称*/private String name;/*** 按钮级别*/private Integer levels;/*** 按钮级别*/private Integer ismenu;/*** 按钮的排序*/private Integer num;/*** 节点的url*/private String url;/*** 节点图标*/private String icon;/*** 子节点的集合*/private List<MenuNode> children;/*** 查询子节点时候的临时集合*/private List<MenuNode> linkedList = new ArrayList<MenuNode>();
}

为了方便以后查看,方法单独提出来。

    /*** 构建整个菜单树*/public void buildNodeTree(List<MenuNode> nodeList) {for (MenuNode treeNode : nodeList) {List<MenuNode> linkedList = treeNode.findChildNodes(nodeList, treeNode.getId());if (linkedList.size() > 0) {treeNode.setChildren(linkedList);}}}/*** 查询子节点的集合*/public List<MenuNode> findChildNodes(List<MenuNode> nodeList, Integer parentId) {if (nodeList == null && parentId == null)return null;for (Iterator<MenuNode> iterator = nodeList.iterator(); iterator.hasNext(); ) {MenuNode node = (MenuNode) iterator.next();// 根据传入的某个父节点ID,遍历该父节点的所有子节点if (node.getParentId() != 0 && parentId.equals(node.getParentId())) {recursionFn(nodeList, node, parentId);}}return linkedList;}
--------------------------------------------------------------------------------/*** 遍历一个节点的子节点*/public void recursionFn(List<MenuNode> nodeList, MenuNode node, Integer pId) {List<MenuNode> childList = getChildList(nodeList, node);// 得到子节点列表if (childList.size() > 0) {// 判断是否有子节点if (node.getParentId().equals(pId)) {linkedList.add(node);}Iterator<MenuNode> it = childList.iterator();while (it.hasNext()) {MenuNode n = (MenuNode) it.next();recursionFn(nodeList, n, pId);}} else {if (node.getParentId().equals(pId)) {linkedList.add(node);}}}/*** 得到子节点列表*/private List<MenuNode> getChildList(List<MenuNode> list, MenuNode node) {List<MenuNode> nodeList = new ArrayList<MenuNode>();Iterator<MenuNode> it = list.iterator();while (it.hasNext()) {MenuNode n = (MenuNode) it.next();if (n.getParentId().equals(node.getId())) {nodeList.add(n);}}return nodeList;}
--------------------------------------------------------------------------------/*** 清除掉按钮级别的资源** @param nodes* @return*/public static List<MenuNode> clearBtn(List<MenuNode> nodes) {ArrayList<MenuNode> noBtns = new ArrayList<MenuNode>();for (MenuNode node : nodes) {if(node.getIsmenu() == IsMenu.YES.getCode()){noBtns.add(node);}}return noBtns;}/*** 清除所有二级菜单** @param nodes* @return*/public static List<MenuNode> clearLevelTwo(List<MenuNode> nodes) {ArrayList<MenuNode> results = new ArrayList<MenuNode>();for (MenuNode node : nodes) {Integer levels = node.getLevels();if (levels.equals(1)) {results.add(node);}}return results;}
--------------------------------------------------------------------------------/*** 构建菜单列表*/public static List<MenuNode> buildTitle(List<MenuNode> nodes) {List<MenuNode> clearBtn = clearBtn(nodes);new MenuNode().buildNodeTree(clearBtn);List<MenuNode> menuNodes = clearLevelTwo(clearBtn);//对菜单排序Collections.sort(menuNodes);//对菜单的子菜单进行排序for (MenuNode menuNode : menuNodes) {if (menuNode.getChildren() != null && menuNode.getChildren().size() > 0) {Collections.sort(menuNode.getChildren());}}//如果关闭了接口文档,则不显示接口文档菜单GunsProperties gunsProperties = SpringContextHolder.getBean(GunsProperties.class);if (!gunsProperties.getSwaggerOpen()) {List<MenuNode> menuNodesCopy = new ArrayList<>();for (MenuNode menuNode : menuNodes) {if (Const.API_MENU_NAME.equals(menuNode.getName())) {continue;} else {menuNodesCopy.add(menuNode);}}menuNodes = menuNodesCopy;}return menuNodes;}

zTree简单使用

获取所有的选择节点、获取子节点

// 通过id号来获取这个树
var treeObj2 = $.fn.zTree.getZTreeObj("treeDemo");
// 获取所有已经选择了的节点,获得一个node列表
var nodes2 = treeObj2.getCheckedNodes(true);
// 如果是叶子节点就把id拿出来
var idlist = [];
$.each(nodes2, function (i, item) {if (!item.isParent) {//alert(item.id + ","  + item.name);idlist.push(item.id);}
});
console.log(idlist);

6、接下来,我们看看pagehelper,Mybatis通用分页插件这个插件也是本项目大佬写的。如果非要自己封装也可以,但是你用过的话就不会在自己封装了。主要是PageInfo类。

package com.guo.guns.common.page;import com.github.pagehelper.Page;import java.util.List;/*** 分页结果的封装(for Bootstrap Table)** @Author guo* @Date 2018-03-04 13:47*/
public class PageInfoBT<T> {/***  结果集*/private List<T> rows;/*** 总数*/private long total;public PageInfoBT(List<T> page) {this.rows = page;if (page instanceof Page) {this.total = ((Page) page).getTotal();} else {this.total = page.size();}}//Setter、Getter略
}

PageHelper简单使用

(1)1、查出第一页的数据,每页5条:

 PageHelper.offsetPage(0, 5);

(2)、获取总数:

PageInfo pageInfo = new PageInfo<>(cs);
System.out.println("总数:"+pageInfo.getTotal());
System.out.println(pageInfo);

基于SpringBoot的后台管理系统(异常、注解、node、page)(二)相关推荐

  1. 基于SpringBoot的后台管理系统(启动类解析,开源的世界真好)(一)

    Guns基于SpringBoot,致力于做更简洁的后台管理系统,完美整合springmvc + shiro + 分页插件PageHelper + 通用Mapper + beetl!Guns项目代码简洁 ...

  2. 主流的基于SpringBoot的后台管理系统

    项目介绍 一款 Java 语言基于 SpringBoot2.x.Layui.Thymeleaf.MybatisPlus.Shiro.MySQL等框架精心打造的一款模块化.插件化.高性能的前后端分离架构 ...

  3. 基于jsp+SpringBoot美容院后台管理系统

    <基于jsp+mysql+mybatis的SpringBoot美容院后台管理系统>该项目采用技术HTML+CSS+JavaScript+jsp+mysql+mybatis+layui+ma ...

  4. 基于SpringBoot的实习管理系统

    末尾获取源码 开发语言:Java Java开发工具:JDK1.8 后端框架:SpringBoot 前端:Vue.HTML 数据库:MySQL5.7和Navicat管理工具结合 服务器:Tomcat8. ...

  5. 基于SpringBoot的毕业论文管理系统的设计与实现(开题报告)

    基于Spring Boot的毕业论文管理系统 研究的背景与意义 随着信息化时代的到来,高校的管理工作也面临着信息化改革.目前,各大高校纷纷引入教务管理信息系统来加强和改善对学生.教师以及各种教务信息的 ...

  6. java基于springboot二手车交易管理系统附源码

    二手车交易管理系统是基于java编程语言,mysql数据库,springboot框架设计,本系统主要分为用户和管理员两个角色,其中用户的功能有用户注册和登陆系统,用户查网站新闻,查看二手车,在线预定, ...

  7. 毕业设计-基于SpringBoot小区物业管理系统

    环境:开发工具:idea,数据库:MySQL5.7 jdk1.8 架构:SpringBoot,前端HTML 主要功能 用户: 添加新投诉 添加新维修 查看个人账单 修改密码 查看我的投诉 查看我的维修 ...

  8. 基于SpringBoot框架的管理系统【完整项目源码】

    基于SpringBoot框架的管理系统 介绍 基于SpringBoot框架的管理系统 简洁版 : 实现 登录 . 注册 . 增 . 删 . 改 . 查 : 可继续完善增加前端.校验.其他功能等: 可作 ...

  9. 基于SpringBoot旅游信息管理系统

    <基于SpringBoot旅游信息管理系统>该项目采用技术: 后台使用了springboot+ssm框架 前端使用html+css+layui,界面美观大方 mysql数据库+tomcat ...

最新文章

  1. 解决Bootstrap中代码不高亮问题
  2. hbase中清空整张表的数据
  3. 相机视场角和焦距_镜头小讲堂(一)镜头的焦距
  4. 剑指Offer - 面试题10- I. 斐波那契数列
  5. 工作占用了太多私人时间_一本正经聊驾驶 | 汽车真的为我们节约时间了吗
  6. input 禁止输入特殊字符
  7. 2.熟悉LINUX的基本操作
  8. Q109:用PBRT渲染Blender导出的模型
  9. phpmyadmin创建账号授权指定表
  10. this指向问题 php,js中的this指向问题
  11. hexo搭建博客系列(六)百度,必应,谷歌收录
  12. UE4 Slate七 Slate本地化, UE4编辑器如何做的本地化
  13. Stanford机器人D-H坐标系
  14. 自媒体适合多平台发布,30+自媒体平台都可以一键发布!
  15. java poi写入excel_Java使用POI读取和写入Excel指南
  16. 电子商务网站测试总结
  17. ios客户端跟h5页面桥接
  18. JSP高校信息管理系统myeclipse开发sql数据库web结构计算机java编程
  19. 天宇,snapseed,第六课,静物人像
  20. 安霸平台_MCTF调试思路

热门文章

  1. VB如何直接显示内存中的二进制图像数据
  2. Linux中find用法整理
  3. 威刚 S102 量产成功 制作带cd-rom启动型U盘 16g USB3.0
  4. 书屋(一):读《世界是平的》有感
  5. 百度Q1营收241亿,李彦宏挥刀改革:“尽力了”没用,要确保在必须赢的战场上胜利...
  6. 蔚来2018年平均每天亏掉2641万,车辆交付预期环比腰斩
  7. 纯css 无视宽高设置垂直水平居中
  8. 极客学院腾讯 TAPD·极客开放日 [敏捷开发畅想与实战]
  9. Mybatis中Mapper.xml文件sql中动态获取----#{}和${}区别
  10. 移动应用程序框架Kendo UI Mobile发布R2 2016 SP2