Spring-Data-Redis项目(简称SDR)对Redis的Key-Value数据存储操作提供了更高层次的抽象,类似于Spring Framework对JDBC支持一样。
项目主页:http://projects.spring.io/spring-data-redis/
项目文档:http://docs.spring.io/spring-data/redis/docs/1.5.0.RELEASE/reference/html/
本文主要介绍Spring Data Redis的实际使用。
1.Spring Data Redis 1.5新特性
增加了Redis HyperLogLog命令PFADD,PFCOUNT,PFMERGE
可以使用Jackson基于RedisSerializer对Java类型序列化
使用PropertySource配置Redis Sentinel连接,目前仅Jedis客户端支持
2.Spring Data Redis ?
Spring Data Redis使得在Spring应用中读写Redis数据库更加容易。
Spring Data Redis提供了四种Redis服务的Java客户端包的集成,分别是Jedis, JRedis, SRP and Lettuce
3.版本要求
Spring Data Redis1.2.x要求JDK1.6+,Spring Framwork3.2.8+
Key-Value存储服务Redis 2.6.x+
4.搭建环境
本文假设已经安装完成了Redis服务,并成功运行。
创建maven项目,添加依赖的Jar,本文主要使用jedis
org.springframework.data
spring-data-redis
1.5.0.RELEASE
redis.clients
jedis
2.6.2
5.连接Redis服务
在Spring Data Redis中通过org.springframework.data.redis.connection包中的RedisConnection和RedisConnectionFactory类来获取Redis连接。
5.1配置JedisConnectionFactory
注意:在配置Redis的sentinel.conf文件时注意使用外部可以访问的ip地址,因为当redis-sentinel服务和redis-server在同一台机器的时候,主服务发生变化时配置文件中将主服务ip变为127.0.0.1,这样外部就无法访问了。如果应用程序,Redis服务在同一台机器则不存在这样的隐患,具体情况则更加实际的网络环境。
配置好之后,在实例化JedisConnectionFactory之后,可见如下日志:
2015-4-1 17:29:30 redis.clients.jedis.JedisSentinelPool initSentinels
信息: Trying to find master from available Sentinels...
信息: Created JedisPool to master at 192.168.88.153:6384
实验环境中192.168.88.153:6384的Redis实例是主服务。
5.5下面通过一组代码展示具体使用
@FixMethodOrder(MethodSorters.NAME_ASCENDING)
public class TestJedis {
public static ApplicationContext ctx;
public static JedisConnectionFactory jedisConnetionFactory;
public JedisConnection jedisConnection;
@SuppressWarnings("unchecked")
@BeforeClass
public static void setBeforeClass() {
ctx = new ClassPathXmlApplicationContext("spring-redis.xml");
jedisConnetionFactory = (JedisConnectionFactory) ctx
.getBean("jedisConnectionFactory");
}
@Before
public void setBefore() {
jedisConnection = jedisConnetionFactory.getConnection();
}
@After
public void setAfter() {
jedisConnection.close();
}
private void print(Collection c) {
for (Iterator iter = c.iterator(); iter.hasNext();) {
RedisServer rs = (RedisServer) iter.next();
System.out.println(rs.getHost() + ":" + rs.getPort());
}
}
// 简单测试JedisConnection
@Ignore
@Test
public void test1() {
if (!jedisConnection.exists(new String("zz").getBytes())) {
jedisConnection.set(new String("zz").getBytes(),
new String("zz").getBytes());
}
}
@Ignore
@Test
public void test2() {
Set keys = jedisConnection.keys(new String("*").getBytes());
for (Iterator iter = keys.iterator(); iter.hasNext();) {
System.out.println(new String(iter.next()));
}
}
// 测试Sentinel
@Ignore
@Test
public void test3() throws InterruptedException {
if (jedisConnetionFactory.getSentinelConnection().isOpen()) {
Collection c = jedisConnetionFactory
.getSentinelConnection().masters();
print(c);
RedisNode rn = new RedisNode("192.168.88.153", 6380);
rn.setName("mymaster");
c = jedisConnetionFactory.getSentinelConnection().slaves(rn);
print(c);
}
for (int i = 0; i < 1000; i++) {
jedisConnection.set(new String("k" + i).getBytes(), new String("v"
+ i).getBytes());
Thread.sleep(1000);
}
Set keys = jedisConnection.keys(new String("k*").getBytes());
Assert.assertEquals(1000, keys.size());
}
}
6.RedisTemplate支持
熟悉Spring的JdbcTemplate对象的话,应该大概能猜出来RedisTemplate的作用了,RedisTemplate对象对RedisConnection进行了封装,它提供了连接管理,序列化等功能,它对Redis的交互进行了更高层次的抽象。另外还提供了Redis操作命令的操作视图,这极大的方便和简化了Redis的操作。
下表是具体的操作视图接口类介绍:
Key类型操作ValueOperationsRedis String/Value 操作ListOperationsRedis List 操作SetOperationsRedis Set 操作ZSetOperationsRedis Sort Set 操作HashOperationsRedis Hash 操作Value约束操作BoundValueOperationsRedis String/Value key 约束BoundListOperationsRedis List key 约束BoundSetOperationsRedis Set key 约束BoundZSetOperationsRedis Sort Set key 约束BoundHashOperationsRedis Hash key 约束 在org.springframework.data.redis.core包中对表中的接口都提供了相应的默认实现。
6.1RedisSerializer
Spring Data Redis提供了对Key-Value的序列号,在使用RedisTemplate对象是默认使用JdkSerializationRedisSerializer实现。还提供了其它的序列化实现如:Jackson2JsonRedisSerializer,JacksonJsonRedisSerializer,GenericToStringSerializer,StringRedisSerializer,OxmSerializer。
另外用户可以提供自己的序列化实现
6.2配置RedisTemplate
@Ignore @Test
public void test8() {
RedisAtomicInteger rai = new RedisAtomicInteger("redis:atomic",
jedisConnetionFactory);
System.out.println(rai.get());
}