http://blog.csdn.net/it_man/article/details/9730605

2013-08-03 11:01 1786人阅读 评论(0) 收藏 举报
 
 

Memcached,对于缓存对象大小有要求,单个对象不得大于1MB,且不支持复杂的数据类型,譬如SET

等。基于这些限制,有必要考虑Redis

相关链接:

Redis实战

Redis实战之Redis + Jedis

Redis实战之征服 Redis + Jedis + Spring (一)

Redis实战之征服 Redis + Jedis + Spring (二)

Redis实战之征服 Redis + Jedis + Spring (三)

言归正传,目前Redis大概有3中基于Java语言的Client:

  • Jredis
  • Jedis
  • Redis4J

这里只说Jedis,因为它是官方提供的唯一Redis Client For Java Provider!

一、简单使用Jedis

需要Jedis就从Maven获取吧!
Maven Pom.xml

  1. <dependency>
  2. <groupId>redis.clients</groupId>
  3. <artifactId>jedis</artifactId>
  4. <version>2.1.0</version>
  5. <type>jar</type>
  6. <scope>compile</scope>
  7. </dependency>
  1. <dependency>
  2. <groupId>redis.clients</groupId>
  3. <artifactId>jedis</artifactId>
  4. <version>2.1.0</version>
  5. <type>jar</type>
  6. <scope>compile</scope>
  7. </dependency>

如果只是简单使用Jedis,以下这么几行代码足够:

  1. Jedis jedis = new Jedis("10.11.20.140");
  2. String keys = "name";
  3. // 删数据
  4. jedis.del(keys);
  5. // 存数据
  6. jedis.set(keys, "snowolf");
  7. // 取数据
  8. String value = jedis.get(keys);
  9. System.out.println(value);
  1. Jedis jedis = new Jedis("10.11.20.140");
  2. String keys = "name";
  3. // 删数据
  4. jedis.del(keys);
  5. // 存数据
  6. jedis.set(keys, "snowolf");
  7. // 取数据
  8. String value = jedis.get(keys);
  9. System.out.println(value);

二、池化使用Jedis

Jedis使用commons-pool完成池化实现。

先做个配置文件:

  1. #最大分配的对象数
  2. redis.pool.maxActive=1024
  3. #最大能够保持idel状态的对象数
  4. redis.pool.maxIdle=200
  5. #当池内没有返回对象时,最大等待时间
  6. redis.pool.maxWait=1000
  7. #当调用borrow Object方法时,是否进行有效性检查
  8. redis.pool.testOnBorrow=true
  9. #当调用return Object方法时,是否进行有效性检查
  10. redis.pool.testOnReturn=true
  11. #IP
  12. redis.ip=10.11.20.140
  13. #Port
  14. redis.port=6379

在静态代码段中完成初始化:

  1. private static JedisPool pool;
  2. static {
  3. ResourceBundle bundle = ResourceBundle.getBundle("redis");
  4. if (bundle == null) {
  5. throw new IllegalArgumentException(
  6. "[redis.properties] is not found!");
  7. }
  8. JedisPoolConfig config = new JedisPoolConfig();
  9. config.setMaxActive(Integer.valueOf(bundle
  10. .getString("redis.pool.maxActive")));
  11. config.setMaxIdle(Integer.valueOf(bundle
  12. .getString("redis.pool.maxIdle")));
  13. config.setMaxWait(Long.valueOf(bundle.getString("redis.pool.maxWait")));
  14. config.setTestOnBorrow(Boolean.valueOf(bundle
  15. .getString("redis.pool.testOnBorrow")));
  16. config.setTestOnReturn(Boolean.valueOf(bundle
  17. .getString("redis.pool.testOnReturn")));
  18. pool = new JedisPool(config, bundle.getString("redis.ip"),
  19. Integer.valueOf(bundle.getString("redis.port")));
  20. }
  1. private static JedisPool pool;
  2. static {
  3. ResourceBundle bundle = ResourceBundle.getBundle("redis");
  4. if (bundle == null) {
  5. throw new IllegalArgumentException(
  6. "[redis.properties] is not found!");
  7. }
  8. JedisPoolConfig config = new JedisPoolConfig();
  9. config.setMaxActive(Integer.valueOf(bundle
  10. .getString("redis.pool.maxActive")));
  11. config.setMaxIdle(Integer.valueOf(bundle
  12. .getString("redis.pool.maxIdle")));
  13. config.setMaxWait(Long.valueOf(bundle.getString("redis.pool.maxWait")));
  14. config.setTestOnBorrow(Boolean.valueOf(bundle
  15. .getString("redis.pool.testOnBorrow")));
  16. config.setTestOnReturn(Boolean.valueOf(bundle
  17. .getString("redis.pool.testOnReturn")));
  18. pool = new JedisPool(config, bundle.getString("redis.ip"),
  19. Integer.valueOf(bundle.getString("redis.port")));
  20. }

然后,修改前面那段jedis操作Redis

  1. // 从池中获取一个Jedis对象
  2. Jedis jedis = pool.getResource();
  3. String keys = "name";
  4. // 删数据
  5. jedis.del(keys);
  6. // 存数据
  7. jedis.set(keys, "snowolf");
  8. // 取数据
  9. String value = jedis.get(keys);
  10. System.out.println(value);
  11. // 释放对象池
  12. pool.returnResource(jedis);
  1. // 从池中获取一个Jedis对象
  2. Jedis jedis = pool.getResource();
  3. String keys = "name";
  4. // 删数据
  5. jedis.del(keys);
  6. // 存数据
  7. jedis.set(keys, "snowolf");
  8. // 取数据
  9. String value = jedis.get(keys);
  10. System.out.println(value);
  11. // 释放对象池
  12. pool.returnResource(jedis);

改为从对象池中,获取Jedis实例:

  1. // 从池中获取一个Jedis对象
  2. Jedis jedis = pool.getResource();
  1. // 从池中获取一个Jedis对象
  2. Jedis jedis = pool.getResource();

切记,最后使用后,释放Jedis对象:

  1. // 释放对象池
  2. pool.returnResource(jedis);
  1. // 释放对象池
  2. pool.returnResource(jedis);

三、一致性哈希

Memcached完全基于分布式集群,而RedisMaster-Slave,如果想把Reids,做成集群模式,无外乎多做几套Master-Slave,每套Master-Slave完成各自的容灾处理,通过Client工具,完成一致性哈希。

PS:Memcached是在Server端完成ShardingRedis只能依靠各个ClientSharding。可能会在Redis 3.0系列支持ServerSharding

保留前面的JedisPoolConfig,新增两个Redis的IP(redis1.ip,redis2.ip),完成两个JedisShardInfo实例,并将其丢进List中:

  1. JedisShardInfo jedisShardInfo1 = new JedisShardInfo(
  2. bundle.getString("redis1.ip"), Integer.valueOf(bundle                       .getString("redis.port")));
  3. JedisShardInfo jedisShardInfo2 = new JedisShardInfo(
  4. bundle.getString("redis2.ip"), Integer.valueOf(bundle                       .getString("redis.port")));
  5. List<JedisShardInfo> list = new LinkedList<JedisShardInfo>();
  6. list.add(jedisShardInfo1);
  7. list.add(jedisShardInfo2);
  1. JedisShardInfo jedisShardInfo1 = new JedisShardInfo(
  2. bundle.getString("redis1.ip"), Integer.valueOf(bundle                       .getString("redis.port")));
  3. JedisShardInfo jedisShardInfo2 = new JedisShardInfo(
  4. bundle.getString("redis2.ip"), Integer.valueOf(bundle                       .getString("redis.port")));
  5. List<JedisShardInfo> list = new LinkedList<JedisShardInfo>();
  6. list.add(jedisShardInfo1);
  7. list.add(jedisShardInfo2);

初始化ShardedJedisPool代替JedisPool:

  1. ShardedJedisPool pool = new ShardedJedisPool(config, list);
  1. ShardedJedisPool pool = new ShardedJedisPool(config, list);

改由ShardedJedis,获取Jedis对象:

  1. // 从池中获取一个Jedis对象
  2. ShardedJedis jedis = pool.getResource();
  3. String keys = "name";
  4. String value = "snowolf";
  5. // 删数据
  6. jedis.del(keys);
  7. // 存数据
  8. jedis.set(keys, value);
  9. // 取数据
  10. String v = jedis.get(keys);
  11. System.out.println(v);
  12. // 释放对象池
  13. pool.returnResource(jedis);
  1. // 从池中获取一个Jedis对象
  2. ShardedJedis jedis = pool.getResource();
  3. String keys = "name";
  4. String value = "snowolf";
  5. // 删数据
  6. jedis.del(keys);
  7. // 存数据
  8. jedis.set(keys, value);
  9. // 取数据
  10. String v = jedis.get(keys);
  11. System.out.println(v);
  12. // 释放对象池
  13. pool.returnResource(jedis);

四、Spring封装参考

Ok,完成上述代码足够完成简单任务,如果有必要,可以用Spring封装初始化:

  1. <context:property-placeholder location="classpath:redis.properties" />
  2. <bean
  3. id="jedisPoolConfig"
  4. class="redis.clients.jedis.JedisPoolConfig"
  5. >
  6. <property
  7. name="maxActive"
  8. value="${redis.pool.maxActive}" />
  9. <property
  10. name="maxIdle"
  11. value="${redis.pool.maxIdle}" />
  12. <property
  13. name="maxWait"
  14. value="${redis.pool.maxWait}" />
  15. <property
  16. name="testOnBorrow"
  17. value="${redis.pool.testOnBorrow}" />
  18. </bean>
  19. <bean
  20. id="shardedJedisPool"
  21. class="redis.clients.jedis.ShardedJedisPool"
  22. >
  23. <constructor-arg
  24. index="0"
  25. ref="jedisPoolConfig" />
  26. <constructor-arg index="1">
  27. <list>
  28. <bean class="redis.clients.jedis.JedisShardInfo">
  29. <constructor-arg
  30. index="0"
  31. value="${redis1.ip}" />
  32. <constructor-arg
  33. index="1"
  34. value="${redis.port}"
  35. type="int" />
  36. </bean>
  37. <bean class="redis.clients.jedis.JedisShardInfo">
  38. <constructor-arg
  39. index="0"
  40. value="${redis2.ip}" />
  41. <constructor-arg
  42. index="1"
  43. value="${redis.port}"
  44. type="int" />
  45. </bean>
  46. </list>
  47. </constructor-arg>
  48. </bean>
  1. <context:property-placeholder location="classpath:redis.properties" />
  2. <bean
  3. id="jedisPoolConfig"
  4. class="redis.clients.jedis.JedisPoolConfig"
  5. >
  6. <property
  7. name="maxActive"
  8. value="${redis.pool.maxActive}" />
  9. <property
  10. name="maxIdle"
  11. value="${redis.pool.maxIdle}" />
  12. <property
  13. name="maxWait"
  14. value="${redis.pool.maxWait}" />
  15. <property
  16. name="testOnBorrow"
  17. value="${redis.pool.testOnBorrow}" />
  18. </bean>
  19. <bean
  20. id="shardedJedisPool"
  21. class="redis.clients.jedis.ShardedJedisPool"
  22. >
  23. <constructor-arg
  24. index="0"
  25. ref="jedisPoolConfig" />
  26. <constructor-arg index="1">
  27. <list>
  28. <bean class="redis.clients.jedis.JedisShardInfo">
  29. <constructor-arg
  30. index="0"
  31. value="${redis1.ip}" />
  32. <constructor-arg
  33. index="1"
  34. value="${redis.port}"
  35. type="int" />
  36. </bean>
  37. <bean class="redis.clients.jedis.JedisShardInfo">
  38. <constructor-arg
  39. index="0"
  40. value="${redis2.ip}" />
  41. <constructor-arg
  42. index="1"
  43. value="${redis.port}"
  44. type="int" />
  45. </bean>
  46. </list>
  47. </constructor-arg>
  48. </bean>

代码可以更简洁一些:

  1. private ApplicationContext app;
  2. private ShardedJedisPool pool;
  3. @Before
  4. public void before() throws Exception {
  5. app = new ClassPathXmlApplicationContext("applicationContext.xml");
  6. pool = (ShardedJedisPool) app.getBean("shardedJedisPool");
  7. }
  8. @Test
  9. public void test() {
  10. // 从池中获取一个Jedis对象
  11. ShardedJedis jedis = pool.getResource();
  12. String keys = "name";
  13. String value = "snowolf";
  14. // 删数据
  15. jedis.del(keys);
  16. // 存数据
  17. jedis.set(keys, value);
  18. // 取数据
  19. String v = jedis.get(keys);
  20. System.out.println(v);
  21. // 释放对象池
  22. pool.returnResource(jedis);
  23. assertEquals(value, v);
  24. }
  1. private ApplicationContext app;
  2. private ShardedJedisPool pool;
  3. @Before
  4. public void before() throws Exception {
  5. app = new ClassPathXmlApplicationContext("applicationContext.xml");
  6. pool = (ShardedJedisPool) app.getBean("shardedJedisPool");
  7. }
  8. @Test
  9. public void test() {
  10. // 从池中获取一个Jedis对象
  11. ShardedJedis jedis = pool.getResource();
  12. String keys = "name";
  13. String value = "snowolf";
  14. // 删数据
  15. jedis.del(keys);
  16. // 存数据
  17. jedis.set(keys, value);
  18. // 取数据
  19. String v = jedis.get(keys);
  20. System.out.println(v);
  21. // 释放对象池
  22. pool.returnResource(jedis);
  23. assertEquals(value, v);
  24. }

当然,Spring提供了对于Redis的专门支持:spring-data-redis,以后有机会再深入研究。

相关链接:

Redis实战

Redis实战之Redis + Jedis

Redis实战之征服 Redis + Jedis + Spring (一)

Redis实战之征服 Redis + Jedis + Spring (二)

Redis实战之征服 Redis + Jedis + Spring (三)

 

Redis实战之Redis + Jedis[转]的更多相关文章

  1. Redis实战之Redis + Jedis

    用Memcached,对于缓存对象大小有要求,单个对象不得大于1MB,且不支持复杂的数据类型,譬如SET 等.基于这些限制,有必要考虑Redis! 相关链接: Redis实战 Redis实战之Redi ...

  2. 分布式缓存技术redis学习系列(五)——redis实战(redis与spring整合,分布式锁实现)

    本文是redis学习系列的第五篇,点击下面链接可回看系列文章 <redis简介以及linux上的安装> <详细讲解redis数据结构(内存模型)以及常用命令> <redi ...

  3. 分布式缓存技术redis系列(五)——redis实战(redis与spring整合,分布式锁实现)

    本文是redis学习系列的第五篇,点击下面链接可回看系列文章 <redis简介以及linux上的安装> <详细讲解redis数据结构(内存模型)以及常用命令> <redi ...

  4. Redis实战总结-Redis的高可用性

    在之前的博客<Redis实战总结-配置.持久化.复制>给出了一种Redis主从复制机制,简单地实现了Redis高可用.然后,如果Master服务器宕机,会导致整个Redis瘫痪,这种方式的 ...

  5. Redis 实战 —— 05. Redis 其他命令简介

    发布与订阅 P52 Redis 实现了发布与订阅(publish/subscribe)模式,又称 pub/sub 模式(与设计模式中的观察者模式类似).订阅者负责订阅频道,发送者负责向频道发送二进制字 ...

  6. Redis 实战 —— 14. Redis 的 Lua 脚本编程

    简介 Redis 从 2.6 版本开始引入使用 Lua 编程语言进行的服务器端脚本编程功能,这个功能可以让用户直接在 Redis 内部执行各种操作,从而达到简化代码并提高性能的作用. P248 在不编 ...

  7. .Net Redis实战——使用Redis构建Web应用

    示例介绍 示例1:借助Redis实现购物车功能 示例2:Redis实现网页缓存和数据缓存 借助Redis实现购物车功能 每个用户的购物车都是一个散列,散列存储了商品ID与商品订购数量之间的映射.订购商 ...

  8. Redis实战之Redis命令

    阅读目录 1. 字符串命令 2. 列表命令 3. 集合命令 4. 散列命令 5. 有序集合命令 6. 发布与订阅命令 7. 小试牛刀 Redis可以存储键与5种不同数据结构类型之间的映射,这5种数据结 ...

  9. Redis 实战 —— 01. Redis 数据结构简介

    一些数据库和缓存服务器的特性和功能 P4 名称 类型 数据存储选项 查询类型 附加功能 Redis 使用内存存储(in-memory)的非关系数据库 字符串.列表.哈希表.集合.有序集合 每种数据类型 ...

随机推荐

  1. Apple 公司开发者账号注册

    苹果公司开发者账号注册流程详解   这段时间在给朋友申请苹果账号,从个人开发者账号.公司账号到企业账号,申请了个遍.这里对申请流程做一下介绍,方便其他朋友,少走弯路,账号早日申请通过. 1.首先介绍下 ...

  2. Xcode 设置输出颜色

    是不是看厌了Xcode单调的Log,在此,我教大家实现带颜色的Log 一 首先你需要安装一个Xcode插件---XCode Colors 插件Github地址 https://github.com/r ...

  3. 【技术贴】解决Mysql ERROR 1045 (28000): Access denied for

    今天Mysql ERROR 1045 (28000): Access denied for user 'root'@'localhost' 肯定是密码不对了.那么重置一下密码吧. 打开 cmd 输入以 ...

  4. /etc/passwd 与 /etc/shadow

    /etc/passwd是用户数据库,其中的域给出了用户名.加密口令和用户的其他信息. /etc/shadow是在安装了影子(shadow)口令软件的系统上的影子口令文件.影子口令文件将/etc/pas ...

  5. centos网络安装中的注意点

    转自centos网络安装中的注意点 centos网络安装的教程网上很多,这里仅仅记录一下安装过程中网上别处提及很少的注意点. 1.centos默认会安装selinux,并且默认阻止ftp服务,所以要禁 ...

  6. 【BZOJ 3122】 [Sdoi2013]随机数生成器 (BSGS)

    3122: [Sdoi2013]随机数生成器 Time Limit: 10 Sec  Memory Limit: 256 MBSubmit: 1442  Solved: 552 Description ...

  7. go与rpc

    Go语言的RPC介绍(含Protobuf-RPC) http://www.open-open.com/lib/view/open1389251727289.html

  8. nyist 61 传纸条 nyist 712 探 寻 宝 藏(双线程dp问题)

    http://acm.nyist.net/JudgeOnline/problem.php?pid=61 http://acm.nyist.net/JudgeOnline/problem.php?pid ...

  9. linux上TCP connection timeout的原因查找

    linux上TCP connection timeout的原因查找 好久没有写文章了, 今天解决了一个网络连接超时的问题, 记录以备查看. 最近在线上nginx经常出现输出connection tim ...

  10. JavaScript数学函数的操作

    <script> var a=3.14; var a1=Math.ceil(a);//大于当前小数的最小整数; alert(a1); var a2=Math.floor(a);//小于当前 ...