redis怎么使用,redis怎么用在项目上

1.简介当我们对redis的基本知识有一定的了解后,我们再通过实战的角度学习一下在SpringBoot环境下,如何优雅的使用redis。我们通过使用SpringBoot内置的Redis注解(文章最后有

1. 简介

当我们对redis的基本知识有一定的了解后,我们再通过实战的角度学习一下在SpringBoot环境下,如何优雅的使用redis。

我们通过使用SpringBoot内置的Redis注解(文章最后有解释)来操作User相关的信息。

再通过Redis工具类的方式操作Role相关信息来全面的学习Redis的使用。

1下载安装文件,选择稳定版本 2解压后找到bin目录下的release下的redis-2.8.17 3点击安装exe文件,进行安装。选择好路径,一直到安装结束即可。 4点击Service查看Redis服务是否正确的安装。Windows--》Service.msc。默认的端口。

redis怎么使用

嫌篇幅太长的 可以直接跳到2.6查看具体逻辑即可。

2. 开撸

2.1 项目结构

结构说明:

├── src│ └── main│ ├── java│ │ └── com│ │ └── ldx│ │ └── redis│ │ ├── RedisApplication.javaredis 配置类│ │ ├── constant│ │ │ └── CacheConstant.java角色管理控制器│ │ │ └── UserController.java角色entity│ │ │ └── SysUser.java角色持久层│ │ │ └── SysUserMapper.java角色接口层│ │ │ ├── SysUserService.java角色接口实现层│ │ │ └── SysUserServiceImpl.javaredis 工具类│ └── resources│ └── application.yaml依赖管理

2.2 导入依赖

<?xml version=&34; encoding=&34;?><project xmlns=&34;; xsi:schemaLocation=& redis 配置redis: 端口,默认为6379port: 6379 连接超时时间timeout: 10slettuce:pool: 连接池中的最大空闲连接max-idle: 8设置Mapper接口所对应的XML文件位置,如果你在Mapper接口中有自定义方法,需要进行该配置mapper-locations: classpath*:mapper/*.xml 控制台sql打印log-impl: org.apache.ibatis.logging.stdout.StdOutImpl# 日志配置logging:level:com.ldx.redis.service.impl: debugorg.springframework: warn

2.3.2 启动类

@EnableCaching :激活缓存支持

@MapperScan : 扫描mapper接口层

import org.mybatis.spring.annotation.MapperScan;import org.springframework.boot.SpringApplication;import org.springframework.boot.autoconfigure.SpringBootApplication;import org.springframework.cache.annotation.EnableCaching;/** * 启动类 * @author ludangxin * @date 2021/8/11 */@EnableCaching@MapperScan(basePackages = &34;)@SpringBootApplicationpublic class RedisApplication {public static void main(String[] args) {SpringApplication.run(RedisApplication.class,args);}}

如果单纯地要解决这个问题的话,可以在设置value的时候使用一个随机数,释放锁的时候,先判断这个随机数是否一致,如果一致再删除锁,否则就退出。但是判断value和删除key也不是一个原子操作,这时候就需要使用lua脚本了。上面。

2.4 redis配置

2.4.1 RedisConfig

redis怎么使用

我们除了在application.yaml中加入redis的基本配置外,redis怎么用在项目上,一般还需要配置redis key和value的序列化方式,如下:

注解:

其默认的序列化方式为 JdkSerializationRedisSerializer ,这种方式跨语言和可读性都不太好,我们将其切换为 Jackson2JsonRedisSerializer 。

import com.fasterxml.jackson.annotation.JsonAutoDetect;import com.fasterxml.jackson.annotation.PropertyAccessor;import com.fasterxml.jackson.databind.ObjectMapper;import com.ldx.redis.constant.CacheConstant;import org.springframework.context.annotation.Bean;import org.springframework.context.annotation.Configuration;import org.springframework.data.redis.cache.RedisCacheConfiguration;import org.springframework.data.redis.cache.RedisCacheManager;import org.springframework.data.redis.cache.RedisCacheWriter;import org.springframework.data.redis.connection.RedisConnectionFactory;import org.springframework.data.redis.core.RedisTemplate;import org.springframework.data.redis.serializer.Jackson2JsonRedisSerializer;import org.springframework.data.redis.serializer.RedisSerializationContext;import org.springframework.data.redis.serializer.StringRedisSerializer;import java.time.Duration;import java.util.HashMap;import java.util.Map;/** * redis配置类 * @author ludangxin * @date 2021/8/11 */@Configurationpublic class RedisConfig {@Beanpublic RedisCacheManager cacheManager(RedisConnectionFactory connectionFactory) {//设置不同cacheName的过期时间Map<String,RedisCacheConfiguration> configurations = new HashMap<>(16);// 序列化方式Jackson2JsonRedisSerializer<Object> jsonRedisSerializer = getJsonRedisSerializer();RedisSerializationContext.SerializationPair<Object> serializationPair = RedisSerializationContext.SerializationPair.fromSerializer(jsonRedisSerializer);// 默认的缓存时间Duration defaultTtl = Duration.ofSeconds(20L);// 用户模块的缓存时间Duration userTtl = Duration.ofSeconds(50L);// 默认的缓存配置RedisCacheConfiguration redisCacheConfiguration = RedisCacheConfiguration.defaultCacheConfig() //.entryTtl(defaultTtl) .serializeValuesWith(serializationPair);// 自定义用户模块的缓存配置 自定义的配置可以覆盖默认配置(当前的模块)configurations.put(CacheConstant.USER_CACHE_NAME,RedisCacheConfiguration.defaultCacheConfig() //.entryTtl(userTtl) .serializeValuesWith(serializationPair));return RedisCacheManager.builder(RedisCacheWriter.nonLockingRedisCacheWriter(connectionFactory)) .cacheDefaults(redisCacheConfiguration) .withInitialCacheConfigurations(configurations) // 事物支持.transactionAware() .build();}@Beanpublic RedisTemplate<Object,Object> redisTemplate(RedisConnectionFactory factory) {RedisTemplate<Object,Object> template = new RedisTemplate<>();template.setConnectionFactory(factory);Jackson2JsonRedisSerializer<Object> jsonRedisSerializer = getJsonRedisSerializer();StringRedisSerializer stringRedisSerializer = new StringRedisSerializer();// key采用String的序列化方式template.setKeySerializer(stringRedisSerializer);// hash的key也采用String的序列化方式template.setHashKeySerializer(stringRedisSerializer);// value序列化方式采用jacksontemplate.setValueSerializer(jsonRedisSerializer);// hash的value序列化方式采用jacksontemplate.setHashValueSerializer(jsonRedisSerializer);// 支持事物//template.setEnableTransactionSupport(true);template.afterPropertiesSet();return template;}/** * 设置jackson的序列化方式 */private Jackson2JsonRedisSerializer<Object> getJsonRedisSerializer() {Jackson2JsonRedisSerializer<Object> redisSerializer = new Jackson2JsonRedisSerializer<>(Object.class);ObjectMapper om = new ObjectMapper();om.setVisibility(PropertyAccessor.ALL,JsonAutoDetect.Visibility.ANY);redisSerializer.setObjectMapper(om);return redisSerializer;}}

2.4.1 CacheConstant

我们为了防止redis中key的重复,尽量会给不同的数据主体加上不同的前缀,这样我们在查看和统计的时候也方便操作。

** * 缓存key 常量类 * @author ludangxin * @date 2021/8/11 */public interface CacheConstant { /*** 用户cache name*/ String USER_CACHE_NAME = &34;; /*** 用户信息缓存key前缀*/ String USER_CACHE_KEY_PREFIX = &34;; /*** 角色cache name*/ String ROLE_CACHE_NAME = &34;; /*** 角色信息缓存key前缀*/ String ROLE_CACHE_KEY_PREFIX = &34;; /*** 获取角色cache key* @param suffix 后缀* @return key*/ static String getRoleCacheKey(String suffix) {return ROLE_CACHE_NAME + &34; + ROLE_CACHE_KEY_PREFIX + suffix; }}

2.4.2 RedisUtil

import lombok.RequiredArgsConstructor;import org.springframework.data.redis.core.*;import org.springframework.stereotype.Component;import java.util.*;import java.util.concurrent.TimeUnit;/** * spring redis 工具类 * @author ludangxin **/@Component@RequiredArgsConstructor@SuppressWarnings(value = { &34;,&34; })public class RedisUtil {public final RedisTemplate redisTemplate;/** * 缓存基本的对象,Integer、String、实体类等 * @param key 缓存的键值 * @param value 缓存的值 * @return 缓存的对象 */public <T> ValueOperations<String,T> setCacheObject(String key,T value) {ValueOperations<String,T> operation = redisTemplate.opsForValue();operation.set(key,value);return operation;}/** * 缓存基本的对象,Integer、String、实体类等 * @param key 缓存的键值 * @param value 缓存的值 * @param timeout 时间 * @param timeUnit 时间颗粒度 * @return 缓存的对象 */public <T> ValueOperations<String,T> setCacheObject(String key,T value,Integer timeout,TimeUnit timeUnit) {ValueOperations<String,T> operation = redisTemplate.opsForValue();operation.set(key,value,timeout,timeUnit);return operation;}/** * 获得缓存的基本对象。 * @param key 缓存键值 * @return 缓存键值对应的数据 */public <T> T getCacheObject(String key) {ValueOperations<String,T> operation = redisTemplate.opsForValue();return operation.get(key);}/** * 删除单个对象 * @param key */public void deleteObject(String key) {redisTemplate.delete(key);}/** * 删除集合对象 * @param collection */public void deleteObject(Collection collection) {redisTemplate.delete(collection);}/** * 缓存List数据 * @param key 缓存的键值 * @param dataList 待缓存的List数据 * @return 缓存的对象 */public <T> ListOperations<String,T> setCacheList(String key,List<T> dataList) {ListOperations listOperation = redisTemplate.opsForList();if (null != dataList) {int size = dataList.size();for (int i = 0; i < size; i++) {listOperation.leftPush(key,dataList.get(i));}}return listOperation;}/** * 获得缓存的list对象 * @param key 缓存的键值 * @return 缓存键值对应的数据 */public <T> List<T> getCacheList(String key) {List<T> dataList = new ArrayList<T>();ListOperations<String,T> listOperation = redisTemplate.opsForList();Long size = listOperation.size(key);for (int i = 0; i < size; i++) {dataList.add(listOperation.index(key,i));}return dataList;}/** * 缓存Set * @param key 缓存键值 * @param dataSet 缓存的数据 * @return 缓存数据的对象 */public <T> BoundSetOperations<String,T> setCacheSet(String key,Set<T> dataSet) {BoundSetOperations<String,T> setOperation = redisTemplate.boundSetOps(key);Iterator<T> it = dataSet.iterator();while (it.hasNext()) {setOperation.add(it.next());}return setOperation;}/** * 获得缓存的set * @param key * @return */public <T> Set<T> getCacheSet(String key) {Set<T> dataSet = new HashSet<T>();BoundSetOperations<String,T> operation = redisTemplate.boundSetOps(key);dataSet = operation.members();return dataSet;}/** * 缓存Map * @param key * @param dataMap * @return */public <T> HashOperations<String,String,T> setCacheMap(String key,Map<String,T> dataMap) {HashOperations hashOperations = redisTemplate.opsForHash();if (null != dataMap) {for (Map.Entry<String,T> entry : dataMap.entrySet()) {hashOperations.put(key,entry.getKey(),entry.getValue());}}return hashOperations;}/** * 获得缓存的Map * @param key * @return */public <T> Map<String,T> getCacheMap(String key) {Map<String,T> map = redisTemplate.opsForHash().entries(key);return map;}/** * 获得缓存的基本对象列表 * @param pattern 字符串前缀 * @return 对象列表 */public Collection<String> keys(String pattern) {return redisTemplate.keys(pattern);}}

2.5 controller

一:1、先进到redis安装目录的bin目录下,本人的机器安装在这里,即/data/redis/bin 2、在/data/redis/bin目录下可以发现有一个redis-cli文件,执行该文件后即可进入命令为:./redis-cli,由于有密码,要输入密码,命令为。

2.5.1 UserController

2.5.2 RoleController

import com.ldx.redis.entity.SysRole;import com.ldx.redis.service.SysRoleService;import lombok.RequiredArgsConstructor;import org.springframework.web.bind.annotation.*;import java.util.List;/** * 角色管理 * @author ludangxin * @date 2021/8/12 */@RestController@RequestMapping(&34;)@RequiredArgsConstructorpublic class RoleController { private final SysRoleService roleService; @GetMapping public List<SysRole> queryAll() {return roleService.queryAll(); } @GetMapping(&34;) public SysRole getUserInfo(@PathVariable Long roleId) {return roleService.getRoleInfo(roleId); } @PostMapping public String add(@RequestBody SysRole role) {roleService.add(role);return &34;; } @PutMapping(&34;) public String update(@PathVariable Long roleId,@RequestBody SysRole role) {roleService.update(roleId,role);return &34;; } @DeleteMapping(&34;) public String del(@PathVariable Long roleId) {roleService.delete(roleId);return &34;; }}

推荐使用项目名:业务名称:时间构成,如:baike:login-name-code:20201228,百科项目登录验证码,与不同的开发人员定义相同时间的概率很低,时间可以按照不同情况定义到天、时、分、秒。

2.6 service.impl

2.6.1 UserServiceImpl

优雅的使用redis注解实现对数据的缓存

@Cacheable:unless :当 unless 成立时则不缓存。这里判断 size 主要是不想将空值存入redis。

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;import com.ldx.redis.constant.CacheConstant;import com.ldx.redis.entity.SysUser;import com.ldx.redis.mapper.SysUserMapper;import com.ldx.redis.service.SysUserService;import lombok.RequiredArgsConstructor;import lombok.extern.slf4j.Slf4j;import org.springframework.cache.annotation.CacheConfig;import org.springframework.cache.annotation.CacheEvict;import org.springframework.cache.annotation.Cacheable;import org.springframework.cache.annotation.Caching;import org.springframework.stereotype.Service;import java.util.List;/** * 用户管理实现 * @author ludangxin * @date 2021/8/11 */@Slf4j@Service@RequiredArgsConstructor@CacheConfig(cacheNames = CacheConstant.USER_CACHE_NAME)public class SysUserServiceImpl implements SysUserService { private final SysUserMapper userMapper; @Override @Cacheable(key = &39;&34;all&34;,unless = &result.size() == 0&34;查询全部用户信息~&34;&34; + CacheConstant.USER_CACHE_KEY_PREFIX + &39; + 34;,unless = &result == null&34;查询用户:{} 详情&34;&34; + CacheConstant.USER_CACHE_KEY_PREFIX + &39;&34;新增用户:{}&34;&34; + CacheConstant.USER_CACHE_KEY_PREFIX + &39;&34;&34; + CacheConstant.USER_CACHE_KEY_PREFIX + &39; + 34;) }) public void update(Long userId,SysUser user) {log.debug(&34;,user.getNickName());user.setId(userId);userMapper.updateById(user); } @Override @Caching(evict = {@CacheEvict(key = &39;&34;all&34;),@CacheEvict(key = &39;&34;&userId&34;删除用户:{}",userId);userMapper.deleteById(userId); }}

2.6.2 SysRoleServiceImpl

使用redis工具类实现对数据的缓存。

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;import com.ldx.redis.constant.CacheConstant;import com.ldx.redis.entity.SysRole;import com.ldx.redis.mapper.SysRoleMapper;import com.ldx.redis.service.SysRoleService;import com.ldx.redis.util.RedisUtil;import lombok.RequiredArgsConstructor;import lombok.extern.slf4j.Slf4j;import org.springframework.stereotype.Service;import org.springframework.util.CollectionUtils;import java.util.Collections;import java.util.List;import java.util.Objects;/** * 角色管理 * @author ludangxin * @date 2021/8/11 */@Slf4j@Service@RequiredArgsConstructorpublic class SysRoleServiceImpl implements SysRoleService { private final SysRoleMapper roleMapper; private final RedisUtil redisUtil; String allKey = CacheConstant.getRoleCacheKey(&34;); @Override public List<SysRole> queryAll() {List<SysRole> roles = redisUtil.getCacheList(allKey);if(!CollectionUtils.isEmpty(roles)) { return roles;}log.debug(&34;);LambdaQueryWrapper<SysRole> queryWrapper = new LambdaQueryWrapper<>();List<SysRole> sysRoles = roleMapper.selectList(queryWrapper);if(CollectionUtils.isEmpty(sysRoles)) { return Collections.emptyList();}redisUtil.setCacheList(allKey,sysRoles);return sysRoles; } @Override public SysRole getRoleInfo(Long roleId) {String roleCacheKey = CacheConstant.getRoleCacheKey(String.valueOf(roleId));SysRole role = redisUtil.getCacheObject(roleCacheKey);if(Objects.nonNull(role)) { return role;}log.debug(&34;,roleId);SysRole sysRole = roleMapper.selectById(roleId);if(Objects.isNull(sysRole)) { return null;}redisUtil.setCacheObject(roleCacheKey,sysRole);return sysRole; } @Override public void add(SysRole role) {log.debug(&34;,role.getName());roleMapper.insert(role);redisUtil.deleteObject(allKey); } @Override public void update(Long roleId,SysRole role) {log.debug(&34;,role.getName());String roleCacheKey = CacheConstant.getRoleCacheKey(String.valueOf(roleId));role.setId(roleId);roleMapper.updateById(role);// 更新缓存redisUtil.setCacheObject(roleCacheKey,role);// 清除缓存redisUtil.deleteObject(allKey); } @Override public void delete(Long roleId) {log.debug(&34;,roleId);roleMapper.deleteById(roleId);// 清除缓存redisUtil.deleteObject(CacheConstant.getRoleCacheKey(String.valueOf(roleId)));redisUtil.deleteObject(allKey); }}

2.7 启动测试

这里只测试了user模块(都测试并且贴图会显得篇幅太长且繁琐),role模块本人测试后结果正确。

查询列表:

调用接口返回全部数据并缓存完成,再次调用无查询日志输出,符合预期。

​ 接口调用:

​ 查看缓存:

查看用户详情:

​ 接口调用返回用户详情信息并缓存完成,再次调用无查询日志输出,符合预期。

​ 接口调用:

​ 查看缓存:

更新数据:

​ 接口调用返回更新成功,并且查看全部的缓存被清除。符合预期。

​ 接口调用:

​ 查看缓存:

3. 内置缓存注解

3.1 @CacheConfig

@Cacheable()里面都有一个value=“xxx”的属性,这显然如果方法多了,写起来也是挺累的,如果可以一次性

3.2 @Cacheable

3.3 @CachePut

3.4 @CacheEvict

@CachEvict 的作用 主要针对方法配置,能够根据一定的条件对缓存进行清空。

/ 清空当前cache name下的所有key@CachEvict(allEntries = true)

3.5 @Caching

@Caching可以使注解组合使用,比如根据id查询用户信息,查询完的结果为{key = id,value = userInfo},但我们现在为了方遍,想用用户的手机号,邮箱等缓存对应用户的信息,这时候我们就要使用@Caching。例:

上一篇 2023年03月04 18:25
下一篇 2023年02月09 03:28

相关推荐

  • oppoa57能卖多少钱,老款oppoa57现在卖多少钱

    跟往常一样,OPPO旗下的A系列新机又一次低调更新,全新的OPPOA57已经上新。不过由于产品力过硬,老款oppoa57现在卖多少钱,即便是低调发布,OPPOA57依旧是吸引了众多消费者的关注。而在4

    2023年04月05 297
  • 新挖掘机多少钱一台,小型挖掘机要多少元

    记者杜楠十多天前,一台小型挖掘机停在海港区石门寨镇孤石峪村村委会门口时,村民们都有些激动。小型挖掘机的价格大概在每台几万元,便宜的有一两万元。不同类别的小型挖掘机,价格也不尽相同。就类别而言,开发性设

    2023年03月20 215
  • 机顶盒分辨率多少合适,机顶盒设置1080还是720

    问:为什么中国电视机都4K高清了还要背一个机顶盒?答:电视机4K超高清是电视本身可以播放这种品质的影像,但需要网络信号源时是需要网络机顶盒来实现解码才能转换为视频流媒体文件,电视才能播放。而需要4K超

    2023年04月05 289
  • 淘宝换货怎么操作,淘宝换货是直接寄回去吗

    在这之前已经写了3篇跟订单售后的相关的文章,大家有兴趣的话也可以移步去看看(文章如下),本篇给大家介绍另一个售后类型——换货,废话不多说,直接看干货。一、售后触发的节点对于电商平台来说,不同的运营模式

    2023年02月05 288
  • 一寸照片的分辨率是多少,ps怎么弄一寸照片电子版

    很多同学都想自己制作证件照片,但是不知道尺寸。今天就把证件照尺寸整理出来,ps怎么弄一寸照片电子版,以及如何自制证件照。别再被照相馆割韭菜啦!,1、1寸证件照尺寸为:25mm×35mm,8张照片排列在

    2023年03月31 279
  • 为什么别人给我打电话老在通话中,苹果手机一打就正在通话中

    现在骚扰电话层出不穷,不仅座机号码多,现在手机号的也日益增多了,不接怕是客户打来的,接了又怕是诈骗电话。今天我总结了一些常用的辨别小方法,可以轻松解决电话骚扰问题。一、响一声的要警惕。一般响一声的陌生

    2023年04月12 291
  • 传真怎么接收,别人给我发传真怎么接收

    法官,我的判决书怎么还没寄到?法官,是不是寄错了法官,调解书怎么寄这么慢法官......每个法官都熟悉的电话内容也是每个法官都经历过的夺命连环催因为当事人从知道裁判文书寄出后便要时时关注快递派送电话生

    2023年02月13 232
  • 6s换电池多少钱,苹果6s换非原装电池

    为平息“降频门”,苹果宣布在2018年一整年下调iPhone6(含)之后所有产品的官换电池价格,美国是从79美元降为29美元,国行则是从608元调整到218元。同时,苹果昨日对外确认,此次换电池活动将

    2023年02月19 246
  • 怎么找回密码,怎么找回锁屏密码

    1.如果开启了手机找回,可以通过这个功能找回密码;2.安全模式;3.强制恢复出厂设置。如果以下方法无法解决,建议带购机发票到服务网点检修。您也可以尝试登录华为云空间官网(cloud.huawei.co

    2023年02月08 298
  • 光威内存条怎么样,内存条为什么不建议光威

    文|周澄澄责编|吕东兴总编|唐迪内存条为什么不建议光威,这款光威天策系列-皓月白时速可达5200MT/S,PMIC电源架构,电压至1.25v,高效散热,性价比之选,感兴趣的可点击链接了解。这款光威天策

    2023年02月06 294
  • 怎么截屏长图,怎么截屏长图苹果手机

    平时使用手机的时候,如果想和好朋友分享长的聊天记录,一张一张图截实在太麻烦了,这时候如果可以截长图就好办了~现在很多手机也有自带的截长屏功能,今天我们就一起来看看都是怎么轻松截长图的吧!一、常用方法方

    2023年02月12 266
  • 捷信利息多少,捷信到底合不合法

    下面就给大家说一下关于捷信退息的技巧和具体操作方法。第一步:微信关注公众号(聚投诉),在里面提交投诉,然后捷信客服就会联系你让你撤案,捷信到底合不合法,那么这就可以开始进入协商了。,微信关注公众号(聚

    2023年02月25 249
  • 夕阳怎么拍,夕阳怎么拍手机专业模式

    对摄影人来说,日落是永不过时的拍摄主题日落的时刻,周围一切变得祥和而微妙火焰的般的余晖笼罩大地,天边一抹彩霞又平添许多温柔,站在秋日黄昏的微风里,身心都得到了安慰用手机怎么去拍摄才能展现日落独特的氛围

    2023年02月10 220
关注微信