废话不多说,就说一句:在 JFinal 中集成 EhCache,可以提高系统的并发访问速度。

可能有人会问 JFinal 是什么,EhCache 是什么,简单解释一下。

JFinal 是一个基于Java 语言的极速 Web 开发框架,用起来非常爽,谁用谁知道。EhCache 是一个纯 Java 的进程内缓存框架,具有快速、精干的特点,用起来非常爽,谁用谁知道。

JFinal 本身已经集成了 EhCache 这个缓存插件,但默认是没有启用的。那怎么启用呢?

请随我来。

01、在 pom.xml 中加入 EhCache 依赖

<dependency>
    <groupId>net.sf.ehcache</groupId>
    <artifactId>ehcache-core</artifactId>
    <version>2.6.11</version>
</dependency>

02、在 JFinalConfig 中配置 EhCachePlugin

public class DemoConfig extends JFinalConfig {
  public void configPlugin(Plugins me) {
    me.add(new EhCachePlugin());
  }
}

基于 JFinal 的 Web 项目需要创建一个继承自 JFinalConfig 类的子类,该类用于对整个 Web 项目进行配置。

03、添加 ehcache.xml

在项目的 src 目录 / resources 目录下添加 ehcache.xml 文件,该文件的初始内容如下所示。

<?xml version="1.0" encoding="UTF-8"?>
<ehcache xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:noNamespaceSchemaLocation="ehcache.xsd"
         updateCheck="false" monitoring="autodetect"
         dynamicConfig="true">     <diskStore path="java.io.tmpdir"/>     <defaultCache
            maxEntriesLocalHeap="10000"
            eternal="false"
            timeToIdleSeconds="120"
            timeToLiveSeconds="120"             diskSpoolBufferSizeMB="30"
            maxEntriesLocalDisk="10000000"
            diskExpiryThreadIntervalSeconds="120"
            memoryStoreEvictionPolicy="LRU"
            statistics="false">
        <persistence strategy="localTempSwap"/>
    </defaultCache> </ehcache>

简单解释一下常用的配置项,否则大家在配置的时候容易犹豫不决。

1)maxEntriesLocalHeap:内存中最大缓存对象数

2)eternal:true 表示对象永不过期,此时会忽略 timeToIdleSeconds 和 timeToLiveSeconds 属性,默认为 false

3)timeToIdleSeconds:对象最近一次被访问后的闲置时间,如果闲置的时间超过了 timeToIdleSeconds 属性值,这个对象就会过期,EhCache 将把它从缓存中清空;即缓存被创建后,最后一次访问时间到缓存失效的时候之间的间隔,单位为秒(s)

4)timeToLiveSeconds:对象被存放到缓存中后存活时间,如果存活时间超过了 timeToLiveSeconds 属性值,这个对象就会过期,EhCache 将把它从缓存中清除;即缓存被创建后,能够存活的最长时间,单位为秒(s)

假如我们现在增加以下配置:

<cache name="keywordsCache"
       maxEntriesLocalHeap="500"
       eternal="false"
       overflowToDisk="true"
       diskPersistent="true"
       timeToIdleSeconds="300"
       timeToLiveSeconds="600">
</cache>

结合之前的默认缓存配置,再来对比介绍下,大家就完全掌握了。

1)name 为该缓存的名字,后续使用缓存的时候要用到。

2)overflowToDisk:true 表示内存中缓存的对象数目达到了 maxEntriesLocalHeap 界限后,会把溢出的对象写到硬盘缓存中。此时的对象必须实现要实现 Serializable 接口(为什么?欢迎查看我以前的文章 Java Serializable:明明就一个空的接口嘛)。

3)diskPersistent:是否缓存虚拟机重启时的数据

再来理解一下 timeToIdleSeconds 和 timeToLiveSeconds 这两个配置项。

timeToIdleSeconds="300"
timeToLiveSeconds="600"

以上表示,一个数据被添加进缓存后,该数据能够在缓存中存活的最长时间为 600 秒()timeToLiveSeconds);在这 600 秒内,假设不止一次去缓存中取该数据,那么相邻 2 次获取数据的时间间隔如果小于 300 秒(timeToIdleSeconds),则能成功获取到数据;但如果最近一次获取到下一次获取的时间间隔超过了 300 秒,那么,将得到 null,因为此时该数据已经被移出缓存了。

04、使用 CacheKit 操作缓存

CacheKit 类是 JFinal 提供的缓存操作工具类,使用起来非常简便。

Map<String, Keywords> map = CacheKit.get("keywordsCache", "keywordMap");
if (map == null) {
    map = new HashMap<>();     List<Keywords> keywordList = dao.findAll();
    for (Keywords item : keywordList) {
        map.put(item.getKeyword(), item);
    }     CacheKit.put("keywordsCache", "keywordMap", map);
}

CacheKit 中有两个最重要的方法:

1)get(String cacheName, Object key),从 cache 中取数据。

2)put(String cacheName, Object key, Object value) ,将数据放入 cache 中。

参数 cacheName 与 ehcache.xml 中的 <cache name="keywordsCache" …> name 属性值对应,这个很好理解。

参数 key 是指取值用到的 key;参数 value 是被缓存的数据,这个其实也好理解。比如在上面的代码中,我们使用了 keywordsCache 这个配置项,在里面放了一个 HashMap,key 为 keywordMap,value 就是 map 这个对象。

JFinal 内部提供了很多使用 Ehcache 的工具方法,比如:

List<Keywords> keywordList = dao.findByCache("keywordsCache", "keywordList", "select * from keywords");

这段代码的作用就是,当我们要从数据库中查询 Keywords 的时候,先从 Ehcache 缓存中取,如果缓存失效的话,再从数据库中取。

我是怎么知道的呢?当然不是靠猜的,我们来看一下源码。

public List<M> findByCache(String cacheName, Object key, String sql, Object... paras) {
    Config config = _getConfig();
    ICache cache = config.getCache();
    List<M> result = cache.get(cacheName, key);
    if (result == null) {
        result = find(config, sql, paras);
        cache.put(cacheName, key, result);
    }
    return result;
}

05、最后

当数据的查询频率很高,远大于修改的频率,就要使用缓存了,这可以在很大程度上提高系统的性能。那现在我就提一个问题了,假如现在要修改一下数据,是先更新 DB,还是先更新缓存呢?

谢谢大家的阅读,原创不易,喜欢就点个赞,这将是我最强的写作动力。如果你觉得文章对你有所帮助,也蛮有趣的,就关注一下我的公众号,谢谢。

如果有人问你 JFinal 如何集成 EhCache,把这篇文章甩给他的更多相关文章

  1. 面试官再问Redis分布式锁如何续期?这篇文章甩 他一脸

    一.真实案例 二.Redis分布式锁的正确姿势 据肥朝了解,很多同学在用分布式锁时,都是直接百度搜索找一个Redis分布式锁工具类就直接用了.关键是该工具类中还充斥着很多System.out.prin ...

  2. Java设计模式(十三) 别人再问你设计模式,叫他看这篇文章

    原创文章,转载请务注明出处 OOP三大基本特性 封装 封装,也就是把客观事物封装成抽象的类,并且类可以把自己的属性和方法只让可信的类操作,对不可信的进行信息隐藏. 继承 继承是指这样一种能力,它可以使 ...

  3. 测试小姐姐问我 gRPC 怎么用,我直接把这篇文章甩给了她

    原文链接: 测试小姐姐问我 gRPC 怎么用,我直接把这篇文章甩给了她 上篇文章 gRPC,爆赞 直接爆了,内容主要包括:简单的 gRPC 服务,流处理模式,验证器,Token 认证和证书认证. 在多 ...

  4. 再有人问你HashMap,把这篇文章甩给他!

    声明:本文以jdk1.8为主! 搞定HashMap 作为一个Java从业者,面试的时候肯定会被问到过HashMap,因为对于HashMap来说,可以说是Java==集合中的精髓==了,如果你觉得自己对 ...

  5. 再有人问你HashMap,把这篇文章甩给他

    搞定HashMap 作为一个Java从业者,面试的时候肯定会被问到过HashMap,因为对于HashMap来说,可以说是Java==集合中的精髓==了,如果你觉得自己对它掌握的还不够好,我想今天这篇文 ...

  6. 面试官问你MyBatis SQL是如何执行的?把这篇文章甩给他

    初识 MyBatis MyBatis 是第一个支持自定义 SQL.存储过程和高级映射的类持久框架.MyBatis 消除了大部分 JDBC 的样板代码.手动设置参数以及检索结果.MyBatis 能够支持 ...

  7. 面试官再问你 HashMap 底层原理,就把这篇文章甩给他看

    前言 HashMap 源码和底层原理在现在面试中是必问的.因此,我们非常有必要搞清楚它的底层实现和思想,才能在面试中对答如流,跟面试官大战三百回合.文章较长,介绍了很多原理性的问题,希望对你有所帮助~ ...

  8. 面试官问你MySQL的优化,看这篇文章就够了

    作者:zhangqh segmentfault.com/a/1190000012155267 一.EXPLAIN 做MySQL优化,我们要善用 EXPLAIN 查看SQL执行计划. 下面来个简单的示例 ...

  9. 再有人问你volatile是什么,把这篇文章也发给他

    在上一篇文章中,我们围绕volatile关键字做了很多阐述,主要介绍了volatile的用法.原理以及特性.在上一篇文章中,我提到过:volatile只能保证可见性和有序性,无法保证原子性.关于这部分 ...

随机推荐

  1. HDU-4857-逃生-反向拓扑排序+优先队列

    HDU-4857 题意就是做一个符合条件的排序,用到拓扑序列. 我一开始wa了多发,才发现有几个样例过不了,发现1->2->3...的顺序无法保证. 后来就想用并查集强连,还是wa: 后来 ...

  2. codeforce#483div2D-XOR-pyramid+DP

    题意:求给定区间中最大的连续异或和: 思路:DP的思想,先dp求出每个区间的异或和,再dp更新成当前这个dp[i][j]和dp[i-1][j].dp[i-1][j+1]中的最大值: 这样可以保证是同一 ...

  3. HDU1814Peaceful Commission求2-sa最小字典序

    #include <iostream> #include <cstdio> #include <vector> #include <cstring> # ...

  4. Netty源码分析 (四)----- ChannelPipeline

    netty在服务端端口绑定和新连接建立的过程中会建立相应的channel,而与channel的动作密切相关的是pipeline这个概念,pipeline像是可以看作是一条流水线,原始的原料(字节流)进 ...

  5. vue项目集成金格WebOffice2015

    下载 官网地址:http://www.goldgrid.com/jinge_download/index.aspx?num=5 解压后的文件 js文件中有两个重要的js文件iWebOffice2015 ...

  6. go 学习笔记之学习函数式编程前不要忘了函数基础

    在编程世界中向来就没有一家独大的编程风格,至少目前还是百家争鸣的春秋战国,除了众所周知的面向对象编程还有日渐流行的函数式编程,当然这也是本系列文章的重点. 越来越多的主流语言在设计的时候几乎无一例外都 ...

  7. 多场景抢红包业务引发.NETCore下使用适配器模式实现业务接口分离

    事情的起因 我们公司现有一块业务叫做抢红包,最初的想法只是实现了一个初代版本,就是给指定的好友单发红包,随着业务的发展,发红包和抢红包的场景也越来越多,目前主要应用的场景有:单聊发红包.群聊发红包.名 ...

  8. 微信小程序点击控制元素的显示与隐藏

    微信小程序点击控制元素的显示与隐藏 首先我们先来看一下单个点击效果 我们来看一下wxml中的代码: <view class="conten"> <view cla ...

  9. Winform中实现ZedGraph曲线图的图像复制到剪切板、打印预览、获取图片并保存、另存为的功能

    场景 Winforn中设置ZedGraph曲线图的属性.坐标轴属性.刻度属性: https://blog.csdn.net/BADAO_LIUMANG_QIZHI/article/details/10 ...

  10. python常用内建模块——datetime

    datetime是python处理日期和时间的标准库. 获取当前日期和时间 >>>from datetime import datetime >>>now = da ...