JetCache源码解析——配置加载

2024-01-07 01:20

本文主要是介绍JetCache源码解析——配置加载,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

JetCache自动化配置加载

JetCache的配置加载主要是在jetcache-autoconfigure模块中完成的,无论是使用内存缓存LinkedHashMap和caffeine,亦或是通过lettuce、redisson和spring-data-redis来操作Redis服务缓存数据,其自动加载配置的操作基本上都是相似的。

例如LinkedHashMapAutoConfiguration完成LinkedHashMap类型的缓存初始化操作,源码如下:

/*** LinkedHashMap自动配置类*/
@Component
@Conditional(LinkedHashMapAutoConfiguration.LinkedHashMapCondition.class)
public class LinkedHashMapAutoConfiguration extends EmbeddedCacheAutoInit {public LinkedHashMapAutoConfiguration() {super("linkedhashmap");}@Override/*** 初始化缓存* @param ct            配置树* @param cacheAreaWithPrefix    缓存区域名称(包括前缀)* @return              初始化后的缓存*/protected CacheBuilder initCache(ConfigTree ct, String cacheAreaWithPrefix) {LinkedHashMapCacheBuilder builder = LinkedHashMapCacheBuilder.createLinkedHashMapCacheBuilder();parseGeneralConfig(builder, ct);return builder;}/*** LinkedHashMap条件类*/public static class LinkedHashMapCondition extends JetCacheCondition {public LinkedHashMapCondition() {super("linkedhashmap");}}
}

其中LinkedHashMapCondition是一个自定义的条件类,如果spring boot项目的application.yml文件中jetcache.local.${areaName} .type或jetcache.remote.${areaName}.type为linkedhashmap时,就会构建LinkedHashMapAutoConfiguration对应的bean,JetCacheCondition类的源码如下:

public abstract class JetCacheCondition extends SpringBootCondition {/*** 缓存类型数组*/private String[] cacheTypes;/*** 构造方法* @param cacheTypes 缓存类型数组*/protected JetCacheCondition(String... cacheTypes) {Objects.requireNonNull(cacheTypes, "cacheTypes can't be null");Assert.isTrue(cacheTypes.length > 0, "cacheTypes length is 0");this.cacheTypes = cacheTypes;}/*** 判断条件是否匹配* @param conditionContext 条件上下文* @param annotatedTypeMetadata 注解类型元数据* @return 匹配结果*/@Overridepublic ConditionOutcome getMatchOutcome(ConditionContext conditionContext, AnnotatedTypeMetadata annotatedTypeMetadata) {ConfigTree ct = new ConfigTree((ConfigurableEnvironment) conditionContext.getEnvironment(), "jetcache.");if (match(ct, "local.") || match(ct, "remote.")) {return ConditionOutcome.match();} else {return ConditionOutcome.noMatch("no match for " + cacheTypes[0]);}}/*** 判断是否匹配指定前缀* @param ct 配置树* @param prefix 前缀* @return 是否匹配*/private boolean match(ConfigTree ct, String prefix) {Map<String, Object> m = ct.subTree(prefix).getProperties();Set<String> cacheAreaNames = m.keySet().stream().map((s) -> s.substring(0, s.indexOf('.'))).collect(Collectors.toSet());final List<String> cacheTypesList = Arrays.asList(cacheTypes);return cacheAreaNames.stream().anyMatch((s) -> cacheTypesList.contains(m.get(s + ".type")));}
}

同理,如果想要使用redisson或lettuce中间件来进行远程缓存的处理,则对应的自动化配置类的源码如下:

@Configuration
@Conditional(RedissonAutoConfiguration.RedissonCondition.class)
public class RedissonAutoConfiguration {private static final String CACHE_TYPE = "redisson";public static class RedissonCondition extends JetCacheCondition {public RedissonCondition() {super(CACHE_TYPE);}}@Beanpublic RedissonAutoInit redissonAutoInit() {return new RedissonAutoInit();}
}

在上面的RedissonAutoConfiguration.RedissonCondition条件类中对应的cacheTypes为redisson,即当spring boot项目的application.yml文件中jetcache.local.${areaName} .type或jetcache.remote.${areaName}.type为redisson时,就会构建RedissonAutoConfiguration对应的bean。

同理,加载lettuce对应的自动化加载的源码如下:

@Configuration
@Conditional(RedisLettuceAutoConfiguration.RedisLettuceCondition.class)
public class RedisLettuceAutoConfiguration {public static final String AUTO_INIT_BEAN_NAME = "redisLettuceAutoInit";public static class RedisLettuceCondition extends JetCacheCondition {public RedisLettuceCondition() {super("redis.lettuce");}}@Bean(name = {AUTO_INIT_BEAN_NAME})public RedisLettuceAutoInit redisLettuceAutoInit() {return new RedisLettuceAutoInit();}
}

JetCache自动初始化

JetCache的自动化的类图如下:

内存缓存自动初始化

LinkedHashMapAutoConfiguration类是基于LinkedHashMap来创建的内存缓存自动配置类,该类继承自EmbeddedCacheAutoInit抽象类,该类重写了initCache方法,用于内存缓存的初始化操作,该方法会创建用于创建LinkedHashMap类型的内存缓存的创建者,并调用parseGeneralConfig方法解析JetCache的配置。源码如下:

    /*** 重写方法,用于初始化缓存* @param ct 缓存的配置树* @param cacheAreaWithPrefix 缓存区服(包括前缀)* @return 返回构建好的缓存*/@Overrideprotected CacheBuilder initCache(ConfigTree ct, String cacheAreaWithPrefix) {LinkedHashMapCacheBuilder builder = LinkedHashMapCacheBuilder.createLinkedHashMapCacheBuilder();parseGeneralConfig(builder, ct);return builder;}

创建LinkerHashMap类型的缓存构建者的源码如下:

public class LinkedHashMapCacheBuilder<T extends EmbeddedCacheBuilder<T>> extends EmbeddedCacheBuilder<T> {/*** LinkedHashMapCacheBuilder的内部类*/public static class LinkedHashMapCacheBuilderImpl extends LinkedHashMapCacheBuilder<LinkedHashMapCacheBuilderImpl> {}/*** 创建一个LinkedHashMapCacheBuilderImpl实例* * @return 返回LinkedHashMapCacheBuilderImpl实例*/public static LinkedHashMapCacheBuilderImpl createLinkedHashMapCacheBuilder() {return new LinkedHashMapCacheBuilderImpl();}/*** 私有构造方法*/protected LinkedHashMapCacheBuilder() {buildFunc((c) -> new LinkedHashMapCache((EmbeddedCacheConfig) c));}
}

在上面构建的LinkedHashMapCacheBuilder实例时,LinkedHashMapCacheBuilder的构造函数会初始化相应的缓存类LinkedHashMapCache。这里紧急简单介绍一下,后面会详细就缓存构建者进行描述。

CaffeineAutoConfiguration类是基于Caffeine来创建的内存缓存自动配置类,该类继承自EmbeddedCacheAutoInit抽象类,该类重写了initCache方法,该方法会创建用于创建Caffeine类型的内存缓存的创建者,并调用parseGeneralConfig方法解析JetCache的配置。源码如下:

@Overrideprotected CacheBuilder initCache(ConfigTree ct, String cacheAreaWithPrefix) {CaffeineCacheBuilder builder = CaffeineCacheBuilder.createCaffeineCacheBuilder();parseGeneralConfig(builder, ct);return builder;}

同样,关于构建CaffeineCacheBuilder相应的代码逻辑也放在后面再进行介绍。

内存缓存LinkedHashMap和caffeine的自动初始化类都是继承自EmbeddedCacheAutoInit抽象类,主要是解析配置的内存缓存的最大缓存数量。EmbeddedCacheAutoInit类的源码如下:

public abstract class EmbeddedCacheAutoInit extends AbstractCacheAutoInit {public EmbeddedCacheAutoInit(String... cacheTypes) {super(cacheTypes);}@Overrideprotected void parseGeneralConfig(CacheBuilder builder, ConfigTree ct) {super.parseGeneralConfig(builder, ct);EmbeddedCacheBuilder ecb = (EmbeddedCacheBuilder) builder;ecb.limit(Integer.parseInt(ct.getProperty("limit", String.valueOf(CacheConsts.DEFAULT_LOCAL_LIMIT))));}
}

解析配置文件的逻辑放到下面的JetCache配置解析章节进行讲述,这里不做过多描述。

Redis缓存自动初始化

在RedissonAutoConfiguration类中,redissonAutoInit()函数会创建RedissonAutoInit对应的bean,类RedissonAutoInit继承自ExternalCacheAutoInit类,通过重写initCache方法,该方法会创建用于创建Redisson类型的内存缓存的创建者RedissonCacheBuilder,并调用parseGeneralConfig方法解析JetCache的配置。下面会详细介绍不同类型的Redis缓存的初始化逻辑。

RedissonAutoInit

待完善…………

RedisLettuceAutoInit

待完善…………

JetCache缓存构建者

待完善…………

JetCache配置加载

待完善…………

这篇关于JetCache源码解析——配置加载的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/578274

相关文章

IntelliJ IDEA 中配置 Spring MVC 环境的详细步骤及问题解决

《IntelliJIDEA中配置SpringMVC环境的详细步骤及问题解决》:本文主要介绍IntelliJIDEA中配置SpringMVC环境的详细步骤及问题解决,本文分步骤结合实例给大... 目录步骤 1:创建 Maven Web 项目步骤 2:添加 Spring MVC 依赖1、保存后执行2、将新的依赖

SpringBoot中配置文件的加载顺序解读

《SpringBoot中配置文件的加载顺序解读》:本文主要介绍SpringBoot中配置文件的加载顺序,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教... 目录SpringBoot配置文件的加载顺序1、命令⾏参数2、Java系统属性3、操作系统环境变量5、项目【外部】的ap

Golang HashMap实现原理解析

《GolangHashMap实现原理解析》HashMap是一种基于哈希表实现的键值对存储结构,它通过哈希函数将键映射到数组的索引位置,支持高效的插入、查找和删除操作,:本文主要介绍GolangH... 目录HashMap是一种基于哈希表实现的键值对存储结构,它通过哈希函数将键映射到数组的索引位置,支持

SpringBoot基于配置实现短信服务策略的动态切换

《SpringBoot基于配置实现短信服务策略的动态切换》这篇文章主要为大家详细介绍了SpringBoot在接入多个短信服务商(如阿里云、腾讯云、华为云)后,如何根据配置或环境切换使用不同的服务商,需... 目录目标功能示例配置(application.yml)配置类绑定短信发送策略接口示例:阿里云 & 腾

如何为Yarn配置国内源的详细教程

《如何为Yarn配置国内源的详细教程》在使用Yarn进行项目开发时,由于网络原因,直接使用官方源可能会导致下载速度慢或连接失败,配置国内源可以显著提高包的下载速度和稳定性,本文将详细介绍如何为Yarn... 目录一、查询当前使用的镜像源二、设置国内源1. 设置为淘宝镜像源2. 设置为其他国内源三、还原为官方

Python使用getopt处理命令行参数示例解析(最佳实践)

《Python使用getopt处理命令行参数示例解析(最佳实践)》getopt模块是Python标准库中一个简单但强大的命令行参数处理工具,它特别适合那些需要快速实现基本命令行参数解析的场景,或者需要... 目录为什么需要处理命令行参数?getopt模块基础实际应用示例与其他参数处理方式的比较常见问http

Python利用ElementTree实现快速解析XML文件

《Python利用ElementTree实现快速解析XML文件》ElementTree是Python标准库的一部分,而且是Python标准库中用于解析和操作XML数据的模块,下面小编就来和大家详细讲讲... 目录一、XML文件解析到底有多重要二、ElementTree快速入门1. 加载XML的两种方式2.

Java的栈与队列实现代码解析

《Java的栈与队列实现代码解析》栈是常见的线性数据结构,栈的特点是以先进后出的形式,后进先出,先进后出,分为栈底和栈顶,栈应用于内存的分配,表达式求值,存储临时的数据和方法的调用等,本文给大家介绍J... 目录栈的概念(Stack)栈的实现代码队列(Queue)模拟实现队列(双链表实现)循环队列(循环数组

CentOS7更改默认SSH端口与配置指南

《CentOS7更改默认SSH端口与配置指南》SSH是Linux服务器远程管理的核心工具,其默认监听端口为22,由于端口22众所周知,这也使得服务器容易受到自动化扫描和暴力破解攻击,本文将系统性地介绍... 目录引言为什么要更改 SSH 默认端口?步骤详解:如何更改 Centos 7 的 SSH 默认端口1

java解析jwt中的payload的用法

《java解析jwt中的payload的用法》:本文主要介绍java解析jwt中的payload的用法,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教... 目录Java解析jwt中的payload1. 使用 jjwt 库步骤 1:添加依赖步骤 2:解析 JWT2. 使用 N