篇幅較長,乾貨十足,閱讀須要花點時間,所有手打出來的字,不免出現錯別字,敬請諒解。珍惜原創,轉載請註明出處,謝謝~!html
Redis是用C語言開發的一個開源的高性能鍵值對(key-value)內存數據庫。前端
它提供五種數據類型來存儲值:字符串類型、散列類型、列表類型、集合類型、有序類型。node
它是一種NoSql數據庫。linux
2008年,意大利的一家創業公司Merzia推出了一款給予MySql的網站實時統計系統LLOOGG,然而沒過多久該公司的創始人Salvatore Sanfilippo便對MySql的性能感到失望,因而他決定親力爲LLOOGG量身定作一個數據庫,並於2009年開發完成,這個數據庫就是Redis。c++
不過Salvatore Sanfilippo並不知足只將Redis用於LLOOGG這一款產品,而是但願更多的人使用它,因而在同一年Salvatore Sanfilippo將Redis開源發佈。web
並開始和Redis的另外一名主要的代碼貢獻者Pieter Noordhuis一塊兒繼續着Redis的開發,直到今天。redis
Salvatore Sanfilippo本身也沒有想到,短短的幾年時間,Redis就擁有了龐大的用戶羣體。Hacker News在2012年發佈一份數據庫的使用請款調查,結果顯示有近12%的公司在使用Redis。國內如新浪微博、街旁網、知乎網、國外如GitHub、Stack、Overflow、Flickr等都是Redis的用戶。算法
VmWare公司從2010年開始贊助Redis的開發,Salvatore Sanfilippo和Pieter Noordhuis也分別在3月和5月加入VMware,全職開發Redis。數據庫
注:將下載後的Redis拖進Linux須要安裝下,VMware Tools,參考連接vim
yum install gcc-c++
tar -zxf redis-4.0.11.tar.gz
make
make install PREFIX=/user/local/redis
格式:make install PREFIX=安裝目錄
ctrl+c
啓動缺點:客戶端窗口關閉,則redis-server程序結束,不推薦使用
cp redis.conf /usr/local/redis/bin
格式:cp 拷貝文件夾 拷貝路徑
vim redis.conf
./redis-server redis.conf
格式:啓動服務 指定配置文件
kill -9 42126
格式:kill -9 進程號
./redis-cli shutdown
redis-server :啓動redis服務 redis-cli :進入redis命令客戶端 redis-benchmark: 性能測試的工具 redis-check-aof : aof文件進行檢查的工具 redis-check-dump : rdb文件進行檢查的工具 redis-sentinel : 啓動哨兵監控服務
./redis-cli -h 127.0.0.1 -p 6379
#bind 127.0.0.1 綁定的ip才能訪問redis服務器,註釋掉該配置 protected-mode yes 是否開啓保護模式,由yes改成no
若是不制定主機和端口號也能夠
./redis-cli 默認的主機地址是:127.0.0.1 默認的端口號是:6379
http://www.redis.cn/commands.html
注:命令不區分大小寫,而key是區分大小寫的。
語法:SET key value
語法:GET key
語法:GETSET key value
語法:INCR key
語法:INCRBY key increment
語法:DECR key
語法:DECRBY key decrement
注:該命令能夠實現分佈式鎖的功能,後續講解!!!!
語法:setnx key value
注:APPEND命令,向鍵值的末尾追加value。若是鍵不存在則該鍵的值設置爲value,即至關於set key value。返回值是追加後字符串的總長度。
注:strlen命令,返回鍵值的長度,若是鍵不存在則返回0
語法:STRLEN key
語法:
需求:商品編號、訂單號採用INCR命令生成。
設計:key明明要有必定的設計
實現:定義商品編號key:items:id
Hash叫散列類型,它提供了字段和字段值的映射。字段值只能是字符串類型,不支持散列類型、集合類型等其餘類型。
HSET命令不區分插入和更新操做,當執行插入操做時HSET命令返回1,當執行更新操做時返回0。
語法:HSET key field value
語法:HMSET key field value [field value ...]
相似HSET,區別在於如何字段存在,該命令不執行任何操做
語法:HSETNX key field value
語法:HGET key field
語法:HMGET key field [field ....]
語法:HGETALL key
能夠刪除一個或多個字段,返回值是被刪除的字段個數
語法:HDEL key field [field ...]
語法:HINCRBY key field increment
語法:HEXISTS key field
語法:
語法:HLEN key
做用:獲取hash的全部信息,包括key和value
語法:hgetall key
注意事項:存在哪些對象數據,特別是對象屬性常常發生增刪改操做的數據。
商品信息字段
【商品id,商品名稱,商品描述,商品庫存,商品好評】
定義商品信息的key
商品id爲1001的信息在Redis中的key爲:[items.1001]
ArrayList使用數組方式存儲數據,因此根據索引查詢數據速度快,而新增或者刪除元素時須要涉及到位移操做,因此比較慢。
LinkedList使用雙向鏈表方式存儲數據,每一個元素都記錄先後元素的指針,因此插入、刪除數據時只是更改先後元素的指針便可,速度很是快。而後經過下標查詢元素時須要從頭開始索引,因此比較慢,可是若是查詢前幾個元素或後幾個元素速度比較快。
Redis的列表類型(list)能夠存儲一個有序的字符串列表,經常使用的操做是向列表兩端添加元素,或者獲取列表的某一個片斷。
列表類型內部是使用雙向鏈表(double linked list)實現的,因此向列表兩端添加元素的時間複雜度爲0/1,獲取越接近兩端的元素速度就越快。意味着即便是一個有幾千萬個元素的列表,獲取頭部或尾部的10條記錄也是極快的。
語法:LPUSH key value [value ...]
語法:RPUSH key value [value ....]
語法:LRANGE key start stop
LRANGE命令是列表類型最經常使用的命令之一,獲取列表中的某一片斷,將返回start、stop之間的全部元素(包括兩端的元素),索引從0開始。索引能夠是負數,「-1」表明最後一邊的一個元素
LPOP命令從列表左邊彈出一個元素,會分兩步完成:
語法:
語法:LLEN key
LREM命令會刪除列表中前count個數爲value的元素,返回實際刪除的元素個數。根據count值不一樣,該命令的執行方式會有所不一樣。
語法:LREM key count value
語法:LINDEX key index
語法:LSET key index value
該命令首先會在列表中從左到右查詢值爲pivot的元素,而後根據第二個參數是BEFORE仍是AFTER來決定將value插入到該元素的前面仍是後面。
語法:LINSERT key BEFORE|AFTER pivot value
語法:RPOPLPUSH source destination
需求1:用戶針對某一商品發佈評論,一個商品會被不一樣的用戶進行評論,存儲商品評論時,要按時間順序排序。
須要2:用戶在前端頁面查詢該商品的評論,須要按照時間順序降序排序。
思路:
使用list存儲商品評論信息,key是該商品的id,value是商品評論信息商品編號爲1001的商品評論key【items:comment:1001】
set類型即集合類型,其中的數據時不重複且沒有順序。
集合類型和列表類型的對比:
集合類型的經常使用操做是向集合中加入或刪除元素、判斷某個元素是否存在等,因爲集合類型的Redis內部是使用值爲空散列標實現,全部這些操做的時間複雜度都爲0/1。
Redis還提供了多個集合之間的交集、並集、差集的運算。
語法:SADD key member [member ...]
語法:SREM key member [member ...]
語法:SMEMBERS key
語法:SISMEMBER key member
屬於A而且不屬於B的元素構成的集合
語法:SDIFF key [key ...]
屬於A且屬於B的元素構成的集合。
語法:SINTER key [key ...]
屬於A或者屬於B的元素構成的集合
語法:SUNION key [key ...]
語法:SCARD key
注意:集合是無序的,全部spop命令會從集合中隨機選擇一個元素彈出
語法:SPOP key
在集合類型的基礎上,有序集合爲集合中的每一個元素都關聯一個分數,這使得咱們不只能夠完成插入、刪除和判斷元素是否存在集合中,還可以得到最高或最低的前N個元素、獲取指定分數範圍內的元素等與分蘇有關的操做。
在某些方面有序集合和列表類型有些類似。
可是兩者有着很大的區別:
向有序集合中加入一個元素和該元素的分數,若是該元素已經存在則會用新的分數替換原有的分數。返回值是新加入到集合中的元素個數,不不含以前已經存在的元素。
語法:ZADD key score member [score member ...]
按照元素分數從小到大的順序返回索引從start到stop之間的全部元素(包含兩端的元素)
語法:ZRANGE key start stop [WITHSCORES]
若是須要獲取元素的分數的能夠在命令尾部加上WITHSCORES參數
語法:ZSCORE key member
移除有序集key中的一個或多個成員,不存在的成員將被忽略。
當key存在但不是有序集類型時,返回錯誤。
語法:ZREM key member [member ...]
語法:ZRANGEBYSCORE key min max [WITHSCORES] [LIMIT offset count]
返回值是更改後的分數
語法:ZINCRBY key increment member
語法:ZCARD key
語法:ZCOUNT key min max
語法:ZREMRANGEBYRANK key start stop
語法:ZREMRANGEBYSCORE key min max
從小到大
語法:ZRANK key member
從大到小
語法:ZREVRANK key member
需求:根據商品銷售對商品進行排序顯示
思路:定義商品銷售排行榜(sorted set集合),key爲items:sellsort,分數爲商品小數量。
寫入商品銷售量:
>商品編號1001的銷量是9,商品編號1002的銷量是10
>商品編號1001銷量家1
>商品銷量前10名
語法:keys pattern
語法:DEL key
做用:確認一個key是否存在
語法:exists key
Redis在實際使用過程當中更多的用做緩存,而後緩存的數據通常都是須要設置生存時間的,即:到期後數據銷燬。
EXPIRE key seconds 設置key的生存時間(單位:秒)key在多少秒後會自動刪除
TTL key 查看key生於的生存時間
PERSIST key 清除生存時間
PEXPIRE key milliseconds 生存時間設置單位爲:毫秒
例子:
192.168.101.3:7002> set test 1 設置test的值爲1
OK
192.168.101.3:7002> get test 獲取test的值
"1"
192.168.101.3:7002> EXPIRE test 5 設置test的生存時間爲5秒
(integer) 1
192.168.101.3:7002> TTL test 查看test的生於生成時間還有1秒刪除
(integer) 1
192.168.101.3:7002> TTL test
(integer) -2
192.168.101.3:7002> get test 獲取test的值,已經刪除
(nil)
做用:重命名key
語法:rename oldkey newkey
做用:顯示指定key的數據類型
語法:type key
注:用於標記事務塊的開始。
Redis會將後續的命令逐個放入隊列中,而後使用EXEC命令原子化地執行這個命令序列。
語法:MULTI
在一個事務中執行全部先前放入隊列的命令,而後恢復正常的鏈接狀態。
語法:EXEC
清楚全部先前在一個事務中放入隊列的命令,而後恢復正常的鏈接狀態。
語法:DISCARD
當某個事務須要按條件執行時,就要使用這個命令將給定的鍵設置爲受監控的狀態。
語法:WATCH key [key ....]
注:該命令能夠實現redis的樂觀鎖
清除全部先前爲一個事務監控的鍵。
語法:UNWATCH
單應用中使用鎖:單線程多線程
synchronize、Lock
分佈式應用中使用鎖:多進程
package com.cyb.redis.utils; import redis.clients.jedis.Jedis; import redis.clients.jedis.JedisPool; public class jedisUtils { private static String ip = "192.168.31.200"; private static int port = 6379; private static JedisPool pool; static { pool = new JedisPool(ip, port); } public static Jedis getJedis() { return pool.getResource(); } public static boolean getLock(String lockKey, String requestId, int timeout) { //獲取jedis對象,負責和遠程redis服務器進行鏈接 Jedis je=getJedis(); //參數3:NX和XX //參數4:EX和PX String result = je.set(lockKey, requestId, "NX", "EX", timeout); if (result=="ok") { return true; } return false; } public static synchronized boolean getLock2(String lockKey, String requestId, int timeout) { //獲取jedis對象,負責和遠程redis服務器進行鏈接 Jedis je=getJedis(); //參數3:NX和XX //參數4:EX和PX Long result = je.setnx(lockKey, requestId); if (result==1) { je.expire(lockKey, timeout); //設置有效期 return true; } return false; } }
package com.cyb.redis.utils; import redis.clients.jedis.Jedis; import redis.clients.jedis.JedisPool; public class jedisUtils { private static String ip = "192.168.31.200"; private static int port = 6379; private static JedisPool pool; static { pool = new JedisPool(ip, port); } public static Jedis getJedis() { return pool.getResource(); } /** * 釋放分佈式鎖 * @param lockKey * @param requestId */ public static void releaseLock(String lockKey, String requestId) { Jedis je=getJedis(); if (requestId.equals(je.get(lockKey))) { je.del(lockKey); } } }
Redis是一個內存數據庫,爲了保證數據的持久性,它提供了兩種持久化方案。
RDB是Redis默認採用的持久化方式。
RDB方式是經過快照(snapshotting)完成的,當符合必定條件時Redis會自動將內存中的數據進行快照並持久化到硬盤。
一、RDB持久化條件
格式:save <seconds> <changes>
示例:
save 900 1:表示15分鐘(900秒)內至少1個鍵更改則進行快照。
save 300 10:表示5分鐘(300秒)內至少10個鍵被更改則進行快照。
save 60 10000:表示1分鐘內至少10000個鍵被更改則進行快照。
二、配置dir指定rdb快照文件的位置
# Note that you must specify a directory here, not a file name.
dir ./
三、配置dbfilename指定rdb快照文件的名稱
# The filename where to dump the DB
dbfilename dump.rdb
使用RDB方式實現持久化,一旦redis異常退出,就會丟失最後一次快照之後更改的全部數據。這個時候咱們就須要根據具體的應用場景,經過組合設置自動快照條件的方式將可能發生的數據損失控制在可以接受範圍。若是數據相對來講比較重要,但願將損失降到最小,則可使用AOF方式進行持久化
RDB能夠最大化redis的性能:父進程在保存RDB文件時惟一要作的就是fork出一個字進程,而後這個子進程就會處理接下來的全部保存工做,父進程無需執行任何磁盤I/O操做。同時這個也是一個缺點,若是數據集比較大的時候,fork可能比較耗時,形成服務器在一段時間內中止處理客戶端的請求。
默認狀況下Redis沒有開啓AOF(append only file)方式的持久化
開啓AOF持久化後每執行一條會更改Redis中的數據命令,Redis就會將該命令寫入硬盤中的AOF文件,這一過程顯示會下降Redis的性能,但大部分下這個影響是可以接受的,另外使用較快的硬盤能夠提升AOF的性能。
設置appendonly參數爲yes
appendonly yes
AOF文件的保存位置和RDB文件的位置相同,都是經過dir參數設置的
dir ./
默認的文件名是appendonly.aof,能夠經過appendfilename參數修改
appendfilename appendonly.aof
Redis每次更改數據的時候,aof機制都會將命令記錄到aof文件,可是實際上因爲操做系統的緩存機制,數據並沒有實時寫入到硬盤,而是進入硬盤緩存。再經過硬盤緩存機制去刷新到保存文件中。
服務器可能在程序正在對AOF文件進行寫入時停機,若是停機形成AOF文件出錯(corrupt),那麼Redis在重啓時會拒絕載入這個AOF文件,從而確保數據的一致性不會被破壞。
當發生這種狀況時,能夠以如下方式來修復出錯的AOF文件:
一、爲現有的AOF文件建立一個備份。
二、使用Redis附帶的redis-check-aof程序,對原來的AOF文件進行修復。
三、重啓Redis服務器,等待服務器字啊如修復後的AOF文件,並進行數據恢復。
持久性保證了即便redis服務重啓也不會丟失數據,由於redis服務重啓後將硬盤上持久化的數據恢復到內存中,可是當redis服務器的硬盤損壞了可能致使數據丟失,不過經過redis的主從複製機制舊能夠避免這種單點故障,以下圖:
說明:
無需特殊配置
修改從服務器上的redis.conf文件
# slaveof <masterip> <masterport> slaveof 192.168.31.200 6379
上邊的配置說明當前【從服務器】對應的【主服務器】的ip是192.168.31.200,端口是6379.
缺點:沒有辦法對master進行動態選舉
Sentinel(哨兵)進程是用於監控redis集羣中Master主服務器工做的狀態,在Master主服務器發生故障的時候,能夠實現Master和Slave服務器的切換,保證系統的高可用,其已經被集成在redis2.6+的版本中,Redis的哨兵模式到2.8版本以後就穩定了下來。
sentinel monitor mymaster 192.168.127.129 6379 1
redis-sentinel
Redis集羣中內置了16384個哈希槽,當須要在Redis集羣中放置一個key-value時,redis先對key使用crc16算法算出一個結果,而後把結果對16384求餘數,這樣每一個key都會對應一個編號在0-16384之間的哈希槽,redis會根據節點數量大體均等的將哈希槽映射到不一樣節點。
redis集羣須要使用集羣管理腳本redis-trib.rb,它的執行相應依賴ruby環境。
yum install ruby
yum install rubygems
gem install redis-3.2.9.gem
cp redis-3.2.9/src/redis-trib.rb /usr/local/redis/ -r
Redis集羣最少須要三臺主服務器,三臺從服務器,端口號分別爲7001~7006。
./redis-trib.rb create --replicas 1 192.168.242.129:7001 192.168.242.129:7002 192.168.242.129:7003 192.168.242.129:7004 192.168.242.129:7005 192.168.242.129:7006
>>> Creating cluster
Connecting to node 192.168.242.129:7001: OK
Connecting to node 192.168.242.129:7002: OK
Connecting to node 192.168.242.129:7003: OK
Connecting to node 192.168.242.129:7004: OK
Connecting to node 192.168.242.129:7005: OK
Connecting to node 192.168.242.129:7006: OK
>>> Performing hash slots allocation on 6 nodes...
Using 3 masters:
192.168.242.129:7001
192.168.242.129:7002
192.168.242.129:7003
Adding replica 192.168.242.129:7004 to 192.168.242.129:7001
Adding replica 192.168.242.129:7005 to 192.168.242.129:7002
Adding replica 192.168.242.129:7006 to 192.168.242.129:7003
M: d8f6a0e3192c905f0aad411946f3ef9305350420 192.168.242.129:7001
slots:0-5460 (5461 slots) master
M: 7a12bc730ddc939c84a156f276c446c28acf798c 192.168.242.129:7002
slots:5461-10922 (5462 slots) master
M: 93f73d2424a796657948c660928b71edd3db881f 192.168.242.129:7003
slots:10923-16383 (5461 slots) master
S: f79802d3da6b58ef6f9f30c903db7b2f79664e61 192.168.242.129:7004
replicates d8f6a0e3192c905f0aad411946f3ef9305350420
S: 0bc78702413eb88eb6d7982833a6e040c6af05be 192.168.242.129:7005
replicates 7a12bc730ddc939c84a156f276c446c28acf798c
S: 4170a68ba6b7757e914056e2857bb84c5e10950e 192.168.242.129:7006
replicates 93f73d2424a796657948c660928b71edd3db881f
Can I set the above configuration? (type 'yes' to accept): yes
>>> Nodes configuration updated
>>> Assign a different config epoch to each node
>>> Sending CLUSTER MEET messages to join the cluster
Waiting for the cluster to join....
>>> Performing Cluster Check (using node 192.168.242.129:7001)
M: d8f6a0e3192c905f0aad411946f3ef9305350420 192.168.242.129:7001
slots:0-5460 (5461 slots) master
M: 7a12bc730ddc939c84a156f276c446c28acf798c 192.168.242.129:7002
slots:5461-10922 (5462 slots) master
M: 93f73d2424a796657948c660928b71edd3db881f 192.168.242.129:7003
slots:10923-16383 (5461 slots) master
M: f79802d3da6b58ef6f9f30c903db7b2f79664e61 192.168.242.129:7004
slots: (0 slots) master
replicates d8f6a0e3192c905f0aad411946f3ef9305350420
M: 0bc78702413eb88eb6d7982833a6e040c6af05be 192.168.242.129:7005
slots: (0 slots) master
replicates 7a12bc730ddc939c84a156f276c446c28acf798c
M: 4170a68ba6b7757e914056e2857bb84c5e10950e 192.168.242.129:7006
slots: (0 slots) master
replicates 93f73d2424a796657948c660928b71edd3db881f
[OK] All nodes agree about slots configuration.
>>> Check for open slots...
>>> Check slots coverage...
[OK] All 16384 slots covered.
[root@localhost-0723 redis]#
命令:
./redis-cli -h 127.0.0.1 -p 7001 -c
注:-c表示是以redis集羣方式進行鏈接
./redis-cli -p 7006 -c
127.0.0.1:7006> set key1 123
-> Redirected to slot [9189] located at 127.0.0.1:7002
OK
127.0.0.1:7002>
127.0.0.1:7003> cluster info
cluster_state:ok
cluster_slots_assigned:16384
cluster_slots_ok:16384
cluster_slots_pfail:0
cluster_slots_fail:0
cluster_known_nodes:6
cluster_size:3
cluster_current_epoch:6
cluster_my_epoch:3
cluster_stats_messages_sent:926
cluster_stats_messages_received:926
127.0.0.1:7003> cluster nodes
7a12bc730ddc939c84a156f276c446c28acf798c 127.0.0.1:7002 master - 0 1443601739754 2 connected 5461-10922
93f73d2424a796657948c660928b71edd3db881f 127.0.0.1:7003 myself,master - 0 0 3 connected 10923-16383
d8f6a0e3192c905f0aad411946f3ef9305350420 127.0.0.1:7001 master - 0 1443601741267 1 connected 0-5460
4170a68ba6b7757e914056e2857bb84c5e10950e 127.0.0.1:7006 slave 93f73d2424a796657948c660928b71edd3db881f 0 1443601739250 6 connected
f79802d3da6b58ef6f9f30c903db7b2f79664e61 127.0.0.1:7004 slave d8f6a0e3192c905f0aad411946f3ef9305350420 0 1443601742277 4 connected
0bc78702413eb88eb6d7982833a6e040c6af05be 127.0.0.1:7005 slave 7a12bc730ddc939c84a156f276c446c28acf798c 0 1443601740259 5 connected
127.0.0.1:7003>
集羣建立完成後能夠繼續向集羣中添加節點。
命令:./redis-trib.rb add-node 127.0.0.1:7007 127.0.0.1:7001
添加完主節點須要對主節點進行hash槽分配,這樣該主節才能夠存儲數據。
redis集羣有16384個槽,集羣中的每一個節點分配本身槽,經過查看集羣節點能夠看到槽佔用狀況。
第一步:連上集羣(鏈接集羣中任意一個可用節點都行)
./redis-trib.rb reshard 192.168.101.3:7001
第二步:輸入要分配的槽數量
輸入500,表示要分配500個槽
第三步:輸入接收槽的節點id
輸入:15b809eadae88955e36bcdbb8144f61bbbaf38fb
ps:這裏準備給7007分配槽,經過cluster node查看7007節點id爲:
15b809eadae88955e36bcdbb8144f61bbbaf38fb
第四步:輸入源節點id
輸入:all
第五步:輸入yes開始移動槽到目標節點id
輸入:yes
添加7008從節點,將7008做爲7007的從節點
命令:
./redis-trib.rb add-node --slave --master-id 主節點id 新節點的ip和端口 舊節點ip和端口
執行以下命令:
./redis-trib.rb add-node --slave --master-id cad9f7413ec6842c971dbcc2c48b4ca959eb5db4 192.168.101.3:7008 192.168.101.3:7001
cad9f7413ec6842c971dbcc2c48b4ca959eb5db4 是7007結點的id,可經過cluster nodes查看。
注意:若是原來該節點在集羣中的配置信息已經生成到cluster-config-file指定的配置文件中(若是cluster-config-file沒有指定則默認爲nodes.conf),這時可能會報錯
[ERR] Node XXXXXX is not empty. Either the node already knows other nodes (check with CLUSTER NODES) or contains some key in database 0
解決辦法是刪除生成的配置文件nodes.conf,刪除後再執行./redis-trib.rb add-node指令
命令:
./redis-trib.rb del-node 127.0.0.1:7005 4b45eb75c8b428fbd77ab979b85080146a9bc017
刪除已經佔用hash槽的節點會失敗,報錯以下
[ERR] Node 127.0.0.1:7005 is not empty! Reshard data away and try again.
須要將該節點佔用的hash槽分配出去
@Test public void testJedisCluster() throws Exception { //建立一鏈接,JedisCluster對象,在系統中是單例存在 Set<HostAndPort> nodes = new HashSet<>(); nodes.add(new HostAndPort("192.168.242.129", 7001)); nodes.add(new HostAndPort("192.168.242.129", 7002)); nodes.add(new HostAndPort("192.168.242.129", 7003)); nodes.add(new HostAndPort("192.168.242.129", 7004)); nodes.add(new HostAndPort("192.168.242.129", 7005)); nodes.add(new HostAndPort("192.168.242.129", 7006)); JedisCluster cluster = new JedisCluster(nodes); //執行JedisCluster對象中的方法,方法和redis一一對應。 cluster.set("cluster-test", "my jedis cluster test"); String result = cluster.get("cluster-test"); System.out.println(result); //程序結束時須要關閉JedisCluster對象 cluster.close(); }
<!-- 鏈接池配置 --> <bean id="jedisPoolConfig" class="redis.clients.jedis.JedisPoolConfig"> <!-- 最大鏈接數 --> <property name="maxTotal" value="30" /> <!-- 最大空閒鏈接數 --> <property name="maxIdle" value="10" /> <!-- 每次釋放鏈接的最大數目 --> <property name="numTestsPerEvictionRun" value="1024" /> <!-- 釋放鏈接的掃描間隔(毫秒) --> <property name="timeBetweenEvictionRunsMillis" value="30000" /> <!-- 鏈接最小空閒時間 --> <property name="minEvictableIdleTimeMillis" value="1800000" /> <!-- 鏈接空閒多久後釋放, 當空閒時間>該值 且 空閒鏈接>最大空閒鏈接數 時直接釋放 --> <property name="softMinEvictableIdleTimeMillis" value="10000" /> <!-- 獲取鏈接時的最大等待毫秒數,小於零:阻塞不肯定的時間,默認-1 --> <property name="maxWaitMillis" value="1500" /> <!-- 在獲取鏈接的時候檢查有效性, 默認false --> <property name="testOnBorrow" value="true" /> <!-- 在空閒時檢查有效性, 默認false --> <property name="testWhileIdle" value="true" /> <!-- 鏈接耗盡時是否阻塞, false報異常,ture阻塞直到超時, 默認true --> <property name="blockWhenExhausted" value="false" /> </bean> <!-- redis集羣 --> <bean id="jedisCluster" class="redis.clients.jedis.JedisCluster"> <constructor-arg index="0"> <set> <bean class="redis.clients.jedis.HostAndPort"> <constructor-arg index="0" value="192.168.101.3"></constructor-arg> <constructor-arg index="1" value="7001"></constructor-arg> </bean> <bean class="redis.clients.jedis.HostAndPort"> <constructor-arg index="0" value="192.168.101.3"></constructor-arg> <constructor-arg index="1" value="7002"></constructor-arg> </bean> <bean class="redis.clients.jedis.HostAndPort"> <constructor-arg index="0" value="192.168.101.3"></constructor-arg> <constructor-arg index="1" value="7003"></constructor-arg> </bean> <bean class="redis.clients.jedis.HostAndPort"> <constructor-arg index="0" value="192.168.101.3"></constructor-arg> <constructor-arg index="1" value="7004"></constructor-arg> </bean> <bean class="redis.clients.jedis.HostAndPort"> <constructor-arg index="0" value="192.168.101.3"></constructor-arg> <constructor-arg index="1" value="7005"></constructor-arg> </bean> <bean class="redis.clients.jedis.HostAndPort"> <constructor-arg index="0" value="192.168.101.3"></constructor-arg> <constructor-arg index="1" value="7006"></constructor-arg> </bean> </set> </constructor-arg> <constructor-arg index="1" ref="jedisPoolConfig"></constructor-arg> </bean>
private ApplicationContext applicationContext; @Before public void init() { applicationContext = new ClassPathXmlApplicationContext( "classpath:applicationContext.xml"); } // redis集羣 @Test public void testJedisCluster() { JedisCluster jedisCluster = (JedisCluster) applicationContext .getBean("jedisCluster"); jedisCluster.set("name", "zhangsan"); String value = jedisCluster.get("name"); System.out.println(value); }