jedis和spring-boot-data-redis区别与关系对于刚接触Spring boot data-redis 的同学,与jedis的关系很容易搞混,这里对data-redis于jedis做一个简单的说明,并提供整合方式
jedis是redis的java客户端,通过它可以对redis进行操作。与之功能相似的还包括:Lettuce等。
spring-data-redis
它依赖jedis或Lettuce,实际上是对jedis这些客户端的封装,提供一套与客户端无关的api供应用使用,从而你在从一个redis客户端切换为另一个客户端,不需要修改业务代码。
spring boot 整合data redis (默认依赖Lettuce)
spring-boot-data-redis 内部实现了对Lettuce和jedis两个客户端的封装,默认使用的是Lettuce
spring-boot-data-redis 内部实现了对Lettuce和jedis两个客户端的封装,默认使用的是Lettuce
使用RedisTemplate
(RedisTemplate是SpringDataRedis中对JedisApi的高度封装。
SpringDataRedis相对于Jedis来说可以方便地更换Redis的Java客户端,比Jedis多了自动管理连接池的特性,方便与其他Spring框架进行搭配使用如:SpringCache)
在application.yml中配置redis相关的属性org.springframework.boot spring-boot-starter-data-redis org.springframework.boot spring-boot-starter-web
spring:
datasource:
url: jdbc:mysql://127.0.0.1:3306/master1?useUnicode=true&characterEncoding=UTF-8&useSSL=false&autoReconnect=true&failOverReadonly=false&serverTimezone=GMT%2B8
username: root
password: 123456
driver-class-name: com.mysql.cj.jdbc.Driver
redis:
#redis服务器地址
host: 88.88.88.142
#redis服务器端口
port: 6379
#服务密码
password:
#连接数
#超时时间
timeout: 10000ms
lettuce:
pool:
#最大连接数 默认为8
max-active: 1024
#最小空闲连接 默认0
max-wait: 10000ms
#最大空闲连接 默认8
max-idle: 200
#最大连接阻塞等待时间
min-idle: 5
logging:
level:
com.xkcoding: debug
com.xkcoding.orm.mybatis.mapper: trace
server:
port: 8080
mybatis:
type-aliases-package: com.orm.mybatis.redis.entity
mapper-locations: classpath:mapper
@Bean //用GenericJackson2JsonRedisSerializer来序列化
public RedisTemplate redisTemplate(LettuceConnectionFactory lettuceConnectionFactory){
//我们为了自己开发方便,一般直接使用
RedisTemplate redisTemplate = new RedisTemplate<>();
// 设置键(key)的序列化采用StringRedisSerializer
StringRedisSerializer stringRedisSerializer=new StringRedisSerializer();
redisTemplate.setKeySerializer(stringRedisSerializer);
redisTemplate.setHashKeySerializer(stringRedisSerializer);
// 设置值(value)的序列化采用GenericJackson2JsonRedisSerializer
GenericJackson2JsonRedisSerializer jsonRedisSerializer = new GenericJackson2JsonRedisSerializer();
redisTemplate.setHashValueSerializer(jsonRedisSerializer);
redisTemplate.setValueSerializer(jsonRedisSerializer);
//设置连接工厂
redisTemplate.setConnectionFactory(lettuceConnectionFactory);
redisTemplate.afterPropertiesSet();
return redisTemplate;
}
// @Bean //用Jackson2JsonRedisSerializer来序列化
// public RedisTemplate redisTemplate(LettuceConnectionFactory lettuceConnectionFactory) {
// //我们为了自己开发方便,一般直接使用
// RedisTemplate redisTemplate = new RedisTemplate<>();
//
// //使用Jackson2JsonRedisSerializer来序列化和反序列化redis的value值(默认使用JDK的序列化方式)
// Jackson2JsonRedisSerializer
Jackson2JsonRedisSerializer和GenericJackson2JsonRedisSerializer的区别 https://blog.csdn.net/bai_bug/article/details/81222519
StringRedisTemplate 与 RedisTemplateRedisTemplate 对五种数据结构分别定义了操作
redisTemplate.opsForValue();
操作字符串
redisTemplate.opsForHash();
操作hash
redisTemplate.opsForList();
操作list
redisTemplate.opsForSet();
操作set
redisTemplate.opsForZSet();
操作有序set
如果操作字符串的话,建议用 StringRedisTemplate 。
StringRedisTemplate 与 RedisTemplate 的区别StringRedisTemplate 继承了 RedisTemplate。
RedisTemplate 是一个泛型类,而 StringRedisTemplate 则不是。
StringRedisTemplate 只能对 key=String,value=String 的键值对进行操作,RedisTemplate 可以对任何类型的 key-value 键值对操作。
他们各自序列化的方式不同,但最终都是得到了一个字节数组,殊途同归,StringRedisTemplate 使用的是 StringRedisSerializer 类;RedisTemplate 使用的是 JdkSerializationRedisSerializer 类。反序列化,则是一个得到 String,一个得到 Object
两者的数据是不共通的,StringRedisTemplate 只能管理 StringRedisTemplate 里面的数据,RedisTemplate 只能管理 RedisTemplate中 的数据。
package com.orm.mybatis.redis.utils;
@Component
public class RedisUtils {
@Resource
private RedisTemplate redisTemplate;
//=======================common========================
public boolean expire(String key,long time){
try {
if(time > 0){
redisTemplate.expire(key,time, TimeUnit.SECONDS);
}
return true;
} catch (Exception e) {
e.printStackTrace();
return false;
}
}
public long getExpire(String key){
return redisTemplate.getExpire(key,TimeUnit.SECONDS);
}
public boolean hasKey(String key){
try {
return redisTemplate.hasKey(key);
} catch (Exception e) {
e.printStackTrace();
return false;
}
}
public void del(String... key){
if(key != null && key.length > 0){
if(key.length == 1){
redisTemplate.delete(key[0]);
}else{
redisTemplate.delete((Collection) CollectionUtils.arrayToList(key));
}
}
}
// ============================String=============================
public Object get(String key){
return key == null ? null : redisTemplate.opsForValue().get(key);
}
public boolean set(String key,Object value){
try {
redisTemplate.opsForValue().set(key,value);
return true;
} catch (Exception e) {
e.printStackTrace();
return false;
}
}
// ============================multiSet和 multiGet=============================
public List> multiGet(ArrayList> keys){
return keys == null ? null : redisTemplate.opsForValue().multiGet(keys);
}
public Set> getPattern(String pattern){
return redisTemplate.keys(pattern);
}
public boolean multiSet(HashMap hashMap){
try {
redisTemplate.opsForValue().multiSet(hashMap);
return true;
} catch (Exception e) {
e.printStackTrace();
return false;
}
}
public boolean set(String key,Object value,long time){
try {
if(time > 0){
redisTemplate.opsForValue().set(key,value,time,TimeUnit.SECONDS);
}else{
set(key,value);
}
return true;
} catch (Exception e) {
e.printStackTrace();
return false;
}
}
public long incr(String key, long delta) {
if (delta < 0) {
throw new RuntimeException("递增因子必须大于0");
}
return redisTemplate.opsForValue().increment(key, delta);
}
public long decr(String key, long delta) {
if (delta < 0) {
throw new RuntimeException("递减因子必须大于0");
}
return redisTemplate.opsForValue().increment(key, -delta);
}
// ================================Map=================================
public Object hget(String key, String item) {
return redisTemplate.opsForHash().get(key, item);
}
public Object hMultiGet(String key, ArrayList> items) {
return redisTemplate.opsForHash().multiGet(key, items);
}
public Map
测试
package com.orm.mybatis.redis;
@SpringBootTest
class SpringbootMybatisRedisApplicationTests {
@Resource
private RedisUtils redisUtils;
@Resource
private StringRedisTemplate stringRedisTemplate;
@Test
void testStringRedisTemplate(){
ValueOperations stringStringValueOperations = stringRedisTemplate.opsForValue();
stringStringValueOperations.set("age", "20");
String age = stringStringValueOperations.get("age");
System.out.println(age);
}
@Test
void testOpsForValue(){
SimpleDateFormat format = new SimpleDateFormat();
User user = User.builder().name("andrew").password("123456")
.email("123@qq.com")
.phoneNumber("13719180727")
.salt("123456789")
.status(1)
.createTime(format.format(DateUtil.now()))
.build();
List list = new ArrayList<>();
list.add(user);
// ValueOperations ops = redisTemplate.opsForValue();
redisUtils.set("user", list);
Object user1 = redisUtils.get("user");
List list1 = (List) redisUtils.get("user");
System.out.println(user1);
System.out.println(list1);
}
@Test
void testOpsForValueMulti(){
SimpleDateFormat format = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
User user1 = User.builder().name("andrew").password("123456")
.email("123@qq.com")
.phoneNumber("13719180727")
.salt("123456789")
.status(1)
.createTime(format.format(DateUtil.now()))
.build();
User user2 = User.builder().name("andrew1").password("123456")
.email("123@qq.com")
.phoneNumber("13719180727")
.salt("123456789")
.status(1)
.createTime(format.format(DateUtil.now()))
.build();
HashMap hashMap = new HashMap<>();
hashMap.put("user1",user1);
hashMap.put("user2",user2);
// ValueOperations ops = redisTemplate.opsForValue();
redisUtils.multiSet(hashMap);
ArrayList keys = new ArrayList<>();
keys.add("user1");
keys.add("user2");
List list1 = (List) redisUtils.multiGet(keys);
list1.forEach(System.out::println);
redisUtils.del("user1");
List list2 = (List) redisUtils.multiGet(keys);
list2.forEach(System.out::println);
}
@Test
public void testHash() {
redisUtils.hset("userall", "name", "zhangsan");
Object object = redisUtils.hget("userall", "name");
System.out.println(object);
//添加多条数据
//存多条数据
HashMap map = new HashMap<>();
map.put("name", "zhangsan");
map.put("age", "14");
map.put("sex", "nan");
redisUtils.hmset("userall1", map);
//获取多条数据
//把key装入结合中
ArrayList keys = new ArrayList<>();
keys.add("name");
keys.add("age");
keys.add("sex");
//拿取多条数据
List user = (List) redisUtils.hMultiGet("userall1", keys);
user.forEach(System.out::println);
//获取hash类型的所有数据
Map entries = redisUtils.hmget("userall1");
entries.forEach((key, value) -> System.out.println(key + "-->" + value));
//hash自带的删除
redisUtils.hdel("userall", "name");
//获取hash类型的所有数据
Map entries1 = redisUtils.hmget("userall");
entries1.forEach((key, value) -> System.out.println(key + "-->" + value));
}
@Test
public void testList() {
redisUtils.del("students");
//左添加
redisUtils.lSet("students", "张三");
//第一个参数redis的key 第二个参数被左添加的数据
redisUtils.lPivotSet("students", "张三", "钱二");
redisUtils.lSet("students", "李四");
//右添加
redisUtils.lSet("students", "牛牛");
//获取数据
List students = redisUtils.lGet("students", 0, -1);
students.forEach(System.out::println);
//获取总条数
Long size = redisUtils.lGetListSize("students");
System.out.println(size);
//删除
redisUtils.lRemove("students", 1, "张三");
//左弹出 删除右边第一个
redisUtils.lPop("students");
//右弹出 删除右边第一个
redisUtils.lPop("students");
}
@Test
public void testSet() {
//添加数据
String[] arr = new String[]{"aaa", "bbb", "ccc","aaa", "ddd"};
redisUtils.sSet("letters", "111", "33", "334");
redisUtils.sSet("letters", arr);
//获取数据
Set letters = redisUtils.sGet("letters");
letters.forEach(System.out::println);
//删除
redisUtils.setRemove("letters", "aaa", "111");
}
@Test
public void testSortedSet() {
//添加数据
ZSetOperations.TypedTuple objectTypedTuple = new DefaultTypedTuple<>("zhangsan", 7D);
ZSetOperations.TypedTuple objectTypedTuple2 = new DefaultTypedTuple<>("lisi", 2D);
ZSetOperations.TypedTuple objectTypedTuple3 = new DefaultTypedTuple<>("wangwu", 9D);
ZSetOperations.TypedTuple objectTypedTuple4 = new DefaultTypedTuple<>("zhaoliu", 3D);
HashSet> tuples = new HashSet<>();
tuples.add(objectTypedTuple);
tuples.add(objectTypedTuple2);
tuples.add(objectTypedTuple3);
tuples.add(objectTypedTuple4);
redisUtils.zSSet("score", tuples);
//zSetOperations.add("name","niuniu",7D);
//获取数据
Set set = redisUtils.zSGet("score", 0, -1);
set.forEach(System.out::println);
//总条数
Long size = redisUtils.zSGetSetSize("score");
System.out.println(size);
//删除数据
redisUtils.zSetRemove("score", "zhangsan", "lisi");
}
@Test
public void testAllKeys() {
Set keys = redisUtils.getPattern("*");
keys.forEach(System.out::println);
}
@Test
public void testExpire() {
//方法一 添加key的时候设置失效时间
redisUtils.set("code", "test", 30);
//方法二 给已经存在的key设置失效时间
redisUtils.set("address", "添加时未设置失效时间");
redisUtils.expire("address", 30);
//查看失效时间
Long code = redisUtils.getExpire("code");
System.out.println(code);
Long time = redisUtils.getExpire("address");
System.out.println(time);
}
}
项目地址:
https://gitee.com/liuweiqiang12/springboot



