• spring Cache + Redis 开发数据字典以及自定义标签


    一、数据库表结构

    1、  分类表:dict_type

           

    2、  子项表:dict_entry

     

    二、页面维护功能示意图:

    1、  分类管理 点击子项管理进入子项管理页面

        

    2、子项管理

        

    三、数据字典添加到缓存:

    数据字典为了读取效率高效,减少与数据库的交互,通常会把数据字典所有数据添加到缓存当中,如果是一台服务器部署,只需放到本机中就可以,如果需要部署到多台服务器分布式部署的话需要把数据字典同步到Redis服务器中。

    1、  springboot 在dictTypeService中把数据字典放到本机缓存中

    对数据字典进行增删改查时需要调用refreshDictCache()方法来刷新缓存,保证缓存中数据为最新数据

    2、  如果使用springboot + Redis做缓存的使用的方法,在dictTypeService中把数据字典放到Redis服务器中

    @Cacheable(value="dictEntry", key="T(String).valueOf('dictEntryMap')")

    使用此注解调用此方法时,系统会先从Redis服务器获取数据字典,如果取不到数据,系统会再去数据库读取。

    @CacheEvict(value="dictEntry", key="T(String).valueOf('dictTypeNameMap')")

    方法使用此注解,对数据字典进行增删改查时,系统会自动同步到Redis服务器,保证数据库数据与redis数据保持一致。

    三、把数据字典做成自定义标签

    1、  创建辅助类(自定义标签调用)

      1 package com.hydwltech.iems.epum.common.utils;
      2 
      3 import java.util.ArrayList;
      4 import java.util.List;
      5 
      6 import org.apache.commons.lang.StringUtils;
      7 
      8 import com.hydwltech.iems.epum.entity.dict.DictEntryOV;
      9 import com.hydwltech.iems.epum.service.dict.DictTypeService;
     10 
     11 /**
     12  * 数据字典工具类
     13  **/
     14 public class DictUtil {
     15     private static DictTypeService getDictTypeService() {
     16         return SpringWebContextUtil.getApplicationContext().getBean(DictTypeService.class);
     17     }
     18 
     19     /**
     20      * 根据类型编码获取子项列表
     21      * 
     22      * @param dictTypeCode 类型编码
     23      * @return List<{@link DictEntryOV}}> 子项数据对象
     24      */
     25     @SuppressWarnings("unchecked")
     26     public static List<DictEntryOV> getDictEntryList(String dictTypeCode) {
     27         return (List<DictEntryOV>) getDictTypeService().getDictEntryMap().get(dictTypeCode);
     28     }
     29 
     30     /**
     31      * 根据类型编码和子项编码获得子项名称
     32      * 
     33      * @param dictTypeCode  类型编码
     34      * @param dictEntryCode 子项编码
     35      * @return String 子项名称
     36      */
     37     public static String getDictEntryName(String dictTypeCode, String dictEntryCode) {
     38         if (StringUtils.isBlank(dictTypeCode)) {
     39             return null;
     40         }
     41         if (StringUtils.isBlank(dictEntryCode)) {
     42             return null;
     43         }
     44         List<DictEntryOV> ovlist = (List<DictEntryOV>) getDictTypeService().getDictEntryMap().get(dictTypeCode);
     45         String entryCode = null;
     46         if (isInteger(dictEntryCode)) {
     47             List<String> nameMapKeys = new ArrayList<String>();
     48             for (DictEntryOV dictOv : ovlist) {
     49                 String[] names = dictOv.getDictEntryCode().split(",");
     50                 boolean namesIsInt = true;
     51                 for (int i = 0; i < names.length; i++) {
     52                     if (!isInteger(names[i])) {
     53                         namesIsInt = false;
     54                         break;
     55                     }
     56                 }
     57                 if (namesIsInt) {
     58                     nameMapKeys.add(dictOv.getDictEntryCode());
     59                 }
     60             }
     61 
     62             for (String parm : nameMapKeys) {
     63                 if (parm.split(",").length == 1) {
     64                     int parm1 = Integer.parseInt(parm.split(",")[0]);
     65                     if (Integer.parseInt(dictEntryCode) == parm1) {
     66                         entryCode = parm;
     67                     }
     68                 } else if (parm.split(",").length == 2) {
     69                     int parm1 = Integer.parseInt(parm.split(",")[0]);
     70                     int parm2 = Integer.parseInt(parm.split(",")[1]);
     71                     if (Integer.parseInt(dictEntryCode) >= parm1 && Integer.parseInt(dictEntryCode) <= parm2) {
     72                         entryCode = parm;
     73                     }
     74                 }
     75             }
     76         } else {
     77             entryCode = dictEntryCode;
     78         }
     79 
     80         String entryName = null;
     81         if (StringUtils.isNotBlank(entryCode)) {
     82             for (DictEntryOV dictEntryOV : ovlist) {
     83                 if (entryCode.equals(dictEntryOV.getDictEntryCode())) {
     84                     entryName = dictEntryOV.getDictEntryName();
     85                 }
     86             }
     87         }
     88         
     89         return entryName;
     90     }
     91 
     92     /**
     93      * 根据类型编码和子项编码获得子项对象
     94      * 
     95      * @param dictTypeCode  类型编码
     96      * @param dictEntryCode 子项编码
     97      * @return DictEntryOV 子项名称
     98      */
     99     public static DictEntryOV getDictEntry(String dictTypeCode, String dictEntryCode) {
    100         if (StringUtils.isBlank(dictTypeCode)) {
    101             return null;
    102         }
    103         if (StringUtils.isBlank(dictEntryCode)) {
    104             return null;
    105         }
    106         List<DictEntryOV> ovlist = (List<DictEntryOV>) getDictTypeService().getDictEntryMap().get(dictTypeCode);
    107         DictEntryOV entryOv = null;
    108         for (DictEntryOV dictEntryOV : ovlist) {
    109             if (dictEntryCode.equals(dictEntryOV.getDictEntryCode())) {
    110                 entryOv = dictEntryOV;
    111             }
    112         }
    113         return entryOv;
    114     }
    115 
    116     /**
    117      * 根据类型编码和子项编码获得子项名称
    118      * 
    119      * @param dictTypeCodeAndEntryCode 类型编码和子项编码合成字符串两个变量已逗号隔开
    120      * @return String 子项名称
    121      */
    122     public static String getDictEntryNameByCodes(String dictTypeCodeAndEntryCode) {
    123         if (StringUtils.isBlank(dictTypeCodeAndEntryCode)) {
    124             return null;
    125         }
    126         String[] params = dictTypeCodeAndEntryCode.split(",");
    127         String dictTypeCode = params[0];
    128         String dictEntryCode = params[1];
    129         List<DictEntryOV> ovlist = (List<DictEntryOV>) getDictTypeService().getDictEntryMap().get(dictTypeCode);
    130         String entryName = null;
    131         for (DictEntryOV dictEntryOV : ovlist) {
    132             if (dictEntryCode.equals(dictEntryOV.getDictEntryCode())) {
    133                 entryName = dictEntryOV.getDictEntryName();
    134             }
    135         }
    136         return entryName;
    137     }
    138 
    139     /**
    140      * 根据类型编码获得类型名称
    141      * 
    142      * @param dictTypeCode 类型编码
    143      * @return String 子项名称
    144      */
    145     public static String getDictTypeName(String dictTypeCode) {
    146         if (StringUtils.isBlank(dictTypeCode)) {
    147             return null;
    148         }
    149         String type = (String) getDictTypeService().getDictTypeNameMap().get(dictTypeCode);
    150         return type;
    151 
    152     }
    153 
    154     /**
    155      * 根据类型编码和子项名称获得子项类型编码
    156      * 
    157      * @param dictTypeCode  类型编码
    158      * @param dictEntryName 子项名称
    159      * @return String 子项编码
    160      */
    161     public static String getDictEntryCodeByEntryName(String dictTypeCode, String dictEntryName) {
    162         if (StringUtils.isBlank(dictTypeCode)) {
    163             return null;
    164         }
    165         if (StringUtils.isBlank(dictEntryName)) {
    166             return null;
    167         }
    168         List<DictEntryOV> ovlist = (List<DictEntryOV>) getDictTypeService().getDictEntryMap().get(dictTypeCode);
    169         String entryCode = null;
    170         for (DictEntryOV ov : ovlist) {
    171             if (dictEntryName.equals(ov.getDictEntryName())) {
    172                 entryCode = ov.getDictEntryCode();
    173             }
    174         }
    175         return entryCode;
    176     }
    177 
    178     /** 验证是否是整数 */
    179     private static boolean isInteger(String param) {
    180         try {
    181             Integer.valueOf(param);
    182             return true;
    183         } catch (Exception e) {
    184             // TODO: handle exception
    185         }
    186         return false;
    187     }
    188 }

    2、  自定义JSTL标签类

       (1)需要定义几个标签,就写几个独立的标签类

      (2)定义标签类,在页面输出下拉菜单数据

     1 package com.hydwltech.iems.epum.common.utils.tag;
     2 
     3 import java.util.List;
     4 
     5 import javax.servlet.jsp.JspException;
     6 import javax.servlet.jsp.tagext.TagSupport;
     7 
     8 import com.hydwltech.iems.epum.common.utils.DictUtil;
     9 import com.hydwltech.iems.epum.entity.dict.DictEntryOV;
    10 
    11 public class ValueDictEntryListUtil extends TagSupport{
    12 
    13     /**
    14      * 
    15      */
    16     private static final long serialVersionUID = 1L;
    17     
    18     private String var;
    19 
    20     @Override
    21     public int doStartTag() throws JspException {
    22         try {
    23             StringBuffer strBuffer = new StringBuffer();
    24             List<DictEntryOV> ovList = DictUtil.getDictEntryList(var);
    25             for (int i = 0; i < ovList.size(); i++) {
    26                 strBuffer.append("<li>");
    27                 strBuffer.append("<a href="###" value="+ovList.get(i).getDictEntryCode()+">" + ovList.get(i).getDictEntryName() + "</a>");
    28                 strBuffer.append("</li>");
    29             }
    30             pageContext.getOut().print(strBuffer.toString());
    31         } catch (Exception e) {
    32             // TODO: handle exception
    33         }
    34         return EVAL_BODY_INCLUDE;
    35     }
    36     
    37 
    38     public String getVar() {
    39         return var;
    40     }
    41 
    42     public void setVar(String var) {
    43         this.var = var;
    44     }
    45 }

    (3)、创建tld文件

          在WEB-INF下创建tld文件 dict.tld

     1 <?xml version="1.0" encoding="UTF-8"?>  
     2 <!DOCTYPE taglib PUBLIC "-//Sun Microsystems, Inc.//DTD JSP Tag Library 1.2//EN"    
     3     "http://java.sun.com/dtd/web-jsptaglibrary_1_2.dtd">
     4 <taglib>
     5     <tlib-version>1.0</tlib-version><!-- 标签库版本 -->
     6     <jsp-version>1.2</jsp-version>  <!-- 标签库要求的JSP规范版本 -->
     7     <short-name>dict</short-name>   <!-- JSP页面编写工具可以用来创建助记名的可选名字 -->
     8     <!-- 
     9          为自定义标签库设置一个uri,uri以/开头,/后面的内容随便写,如这里的/gacl ,
    10          在Jsp页面中引用标签库时,需要通过uri找到标签库
    11          在Jsp页面中就要这样引入标签库:
    12          <%@taglib uri="/security/encrypt" prefix="encrypt"%>
    13      -->
    14     <!-- <uri>/security/encrypt</uri> -->
    15     <tag>
    16         <name>entry</name>
    17         <tag-class>com.hydwltech.iems.epum.common.utils.tag.ValueDictEntryNameUtil</tag-class>
    18         <body-content>JSP</body-content>
    19         <attribute>
    20             <name>typeCode</name>
    21             <rtexprvalue>true</rtexprvalue>
    22         </attribute>
    23         <attribute>
    24             <name>entryCode</name>
    25             <rtexprvalue>true</rtexprvalue>
    26         </attribute>
    27     </tag>
    28     
    29     <tag>
    30         <name>type</name>
    31         <tag-class>com.hydwltech.iems.epum.common.utils.tag.ValueDictTypeNameUtil</tag-class>
    32         <body-content>JSP</body-content>
    33         <attribute>
    34             <name>var</name>
    35             <rtexprvalue>true</rtexprvalue>
    36         </attribute>
    37     </tag>
    38     
    39     <tag>
    40         <name>select</name>
    41         <tag-class>com.hydwltech.iems.epum.common.utils.tag.ValueDictEntryListUtil</tag-class>
    42         <body-content>JSP</body-content>
    43         <attribute>
    44             <name>var</name>
    45             <rtexprvalue>true</rtexprvalue>
    46         </attribute>
    47     </tag>
    48 </taglib>  

    (4)、JSP页面调用标签

          A、导入自定义标签

           <%@ taglib prefix="dict" uri="/WEB-INF/tag/dict.tld"%>

          

        B、下拉菜单调用此标签

           <dict:select var="equipEablePatrol"/>

    效果如下图:

    除了下拉菜单标签,还可以根据自己的需求开发其他自定义标签。

    四、相关技术链接

          关于自定义标签转自:https://blog.csdn.net/bilahepan/article/details/54801540

          关于Springboot  + cacheable + Redis转自:https://blog.csdn.net/moshowgame/article/details/80792774

  • 相关阅读:
    Apache 流框架 Flink,Spark Streaming,Storm对比分析(1)
    Apache 流框架 Flink,Spark Streaming,Storm对比分析(2)
    spark日志配置及问题排查方式。
    Structure Streaming和spark streaming原生API访问HDFS文件数据对比
    fstream,sstream的学习记录
    控制位数和填充0
    激活windows10(已更新工具)
    7-13 统计工龄(排序)
    Insertion or Heap Sort
    Insert or Merge
  • 原文地址:https://www.cnblogs.com/wm-dv/p/11155588.html
Copyright © 2020-2023  润新知