Spring Boot 使用Redis 入门

来源:互联网 发布:阿里云先知白帽大会 编辑:程序博客网 时间:2024/04/28 15:44

在SpringBoot中使用Redis有两种方式,一种是使用Jredis,这是一个Client,得到实例后可以调用Redis的命令,使用上很简单明了,不过好像要自己处理下连接池

另一种是使用RedisTemplate,这个是被Spring封装了一次的,可以不关心连接池,在使用上又分为两种方式,一种是使用它封装的方法(类似于使用Jredis),另一种是使用注解方式


使用之前需要先添加依赖

<dependency>    <groupId>org.springframework.boot</groupId>    <artifactId>spring-boot-starter-redis</artifactId>    <version>1.4.7.RELEASE</version></dependency>


一、使用Jredis

使用Jredis需要先初始化连接池,然后从连接池中获取对象

JedisPool pool = new JedisPool("192.168.0.1",6379);
然后获取对象
Jedis jedis = jedisPool.getResource();
然后可以使用jedis调用Redis的命令
jedis.hset("hset","tem1","haha");
String str=jedis.get("string");

jedis封装了Redis的命令,命名和命令一致



二、使用RedisTeplate

使用RedisTeplate需要先创建一个他的配置类

在这里面主要求三个东西

第一个是CacheManager,在这里设置缓存的默认过期时间和某个缓存的过期时间(这个主要在使用注解方式时使用)

第二个是keyGenerator,这个是key生成规则,在这里写默认的(注解方式使用),也可以在写注解的时候定义

第三个是redisTemplate,这里谢了序列化方法,这里用的是json


import com.fasterxml.jackson.annotation.JsonAutoDetect;

import com.fasterxml.jackson.annotation.PropertyAccessor;import com.fasterxml.jackson.databind.ObjectMapper;import com.payme.mbe.user.controller.UserController;import org.slf4j.Logger;import org.slf4j.LoggerFactory;import org.springframework.cache.CacheManager;import org.springframework.cache.annotation.CachingConfigurerSupport;import org.springframework.cache.annotation.EnableCaching;import org.springframework.cache.interceptor.KeyGenerator;import org.springframework.context.annotation.Bean;import org.springframework.context.annotation.Configuration;import org.springframework.data.redis.cache.RedisCacheManager;import org.springframework.data.redis.connection.RedisConnectionFactory;import org.springframework.data.redis.core.RedisTemplate;import org.springframework.data.redis.core.StringRedisTemplate;import org.springframework.data.redis.serializer.Jackson2JsonRedisSerializer;import java.lang.reflect.Method;import java.util.HashMap;import java.util.Map;@Configuration@EnableCachingpublic class RedisConfig extends CachingConfigurerSupport {    private static final Logger logger = LoggerFactory.getLogger(UserController.class);    @Bean    public KeyGenerator keyGenerator() {        return new KeyGenerator() {            @Override            public Object generate(Object target, Method method, Object... params) {                StringBuilder sb = new StringBuilder();                sb.append(target.getClass().getName());                sb.append(method.getName());                for (Object obj : params) {                    sb.append(obj.toString());                }                return sb.toString();            }        };    }    @SuppressWarnings("rawtypes")    @Bean    public CacheManager cacheManager(RedisTemplate redisTemplate) {        RedisCacheManager rcm = new RedisCacheManager(redisTemplate);        //设置默认缓存过期时间        rcm.setDefaultExpiration(3600);//秒        rcm.setExpires(this.initExpiresMap());//设置某个缓存的过期时间        return rcm;    }    private Map<String, Long> initExpiresMap()    {        Map<String, Long> map= new HashMap<String, Long>();        map.put("users",100L);        return map;    }    @Bean    public RedisTemplate<String, String> redisTemplate(RedisConnectionFactory factory) {        StringRedisTemplate template = new StringRedisTemplate(factory);        Jackson2JsonRedisSerializer jackson2JsonRedisSerializer = new Jackson2JsonRedisSerializer(Object.class);        ObjectMapper om = new ObjectMapper();        om.setVisibility(PropertyAccessor.ALL, JsonAutoDetect.Visibility.ANY);        om.enableDefaultTyping(ObjectMapper.DefaultTyping.NON_FINAL);        jackson2JsonRedisSerializer.setObjectMapper(om);        template.setValueSerializer(jackson2JsonRedisSerializer);        template.afterPropertiesSet();        return template;    }}



1、使用方法

写好上面那些之后,我们可以使用方法来操作Redis

先注入两个Template

@Autowiredprivate StringRedisTemplate stringRedisTemplate;//操作String型数据@Autowiredprivate RedisTemplate redisTemplate;//操作其它类型数据

stringRedisTemplate.opsForValue().set("aaa", "111");//添加一个key为aaa,值为111的缓存
下面是一个插入对象的

UserEntity user=new UserEntity();//UserEntity需要implements Serializableuser.setUserid(11);user.setUserName("admin");

//这两个是将User插入缓存,第二个自定义了过期时间

ValueOperations<String, UserEntity> operations=redisTemplate.opsForValue();operations.set("com.neox", user);operations.set("com.neo.f", user,10, TimeUnit.SECONDS);
//判断是否存在key

boolean exists=redisTemplate.hasKey("com.neo.f");

//操作List,方法名和命令名有些类似

redisTemplate.opsForList().rightPush("gllist","1");redisTemplate.opsForList().rightPush("gllist","2");String str = (String)redisTemplate.opsForList().leftPop("gllist");
long siz = redisTemplate.opsForList().size("testList");

//一次性在list中插入多个(List方式)

redisTemplate.opsForList().rightPushAll("testList",list);

使用这种方法的形式可以操作Redis,如果实现缓存逻辑,插入、取出、删除需要自己写,这样的方式和Jedris类似


2、使用注解

也可以使用注解的方式使用缓存,如果在一个GetInfo的方法上使用注解,方法会自动先去缓存找数据,找不到再执行方法体(去数据库找),获取后再加入缓存(如果使用上面的方式,这些逻辑要自己写)

有三个注解项

@Cacheable//这个注解放到Get方法上,实现先去缓存找数据,找不到执行方法体(数据库找数据),获取后插入到缓存
@CachePut//这个注解一般是放到更新语句上,实现的功能是更新缓存对应的值(但是注意更新这个直接把更新方法的返回值更新到缓存里,例如GetUser和UpdateUser,我们缓存的是UserInfo,但是如果UpdateUser的返回值是int,只表示成功失败,那这个注解会把UserInfo替换为int值,所以如果使用需要把函数返回值改为对象)
@CacheEvict//这个是删除对应的缓存,一般放到delete方法上(如果我们在所有修改的方法上都放这个也行,修改就删除,靠get更新缓存)

例如下面的几个方法

注解的两个参数value表示这类数据的缓存列表名称,例如上面配置了users的过期时间。key就是每个数据的缓存key值(下面方法中key定义的缓存key值最后会是"userentity1","userentity2"这样)

这个方法会先去缓存找数据,找不到执行方法获取数据,然后再插入缓存

@Cacheable(value = "users", key="'userentity'+#userID")    public UserEntity get(int userID) {       UserEntity u = userMapper.getOne(userID);//userRepository.get(userID);        if (u!=null)        {            logger.info("插入了- " + userID);        }        return u;    }



这个方法会删除缓存中对应key值得数据

    @CacheEvict(value = "users", key="'userentity'+#userID")    public int delete(int userID) {        int result = userMapper.delete(userID); //userRepository.delete(userID);        return result;    }

更新方法我同样也做了删除数据

 @CacheEvict(value = "users", key="'userentity'+#userEntity.userid")    public int update(UserEntity userEntity) {        int result = userMapper.update(userEntity);             return result;    }

到Redis里面数据会是这样


@Cacheable(value = "users", key="'userentity'+#userID")    public UserEntity get(int userID) {       UserEntity u = userMapper.getOne(userID);//userRepository.get(userID);        if (u!=null)        {            logger.info("CityServiceImpl.findCityById() : 插入了>> " + userID);        }        return u;    }