Redis介绍及实践分享
生活随笔
收集整理的這篇文章主要介紹了
Redis介绍及实践分享
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
1、Redis是什么1)Redis是REmote DIctionary Server的縮寫,是一個key-value存儲系統2)Redis提供了一些豐富的數據結構,包括Strings,Lists,Hashes,Sets和Ordered Sets以及Hashes。包括對這些數據結構的操作支持3)Redis可以替代Memcached,并且解決了斷電后數據完全丟失的問題4)Redis官方網站: http://redis.io ? ? Redis作者Blog: http://antirez.com
2、Redis安裝Download, extract and compile Redis with:$ wget http://download.redis.io/releases/redis-3.2.5.tar.gz $ tar xzf redis-3.2.5.tar.gz$ cd redis-3.2.5$ make
The binaries that are now compiled are available in the src directory:Run Redis with:
$ src/redis-serverYou can interact with Redis using the built-in client:$ src/redis-cliredis> set foo barOKredis> get foo"bar"
3、Redis優點1)性能極高,Redis能支持10萬每秒的讀寫頻率2)豐富的數據類型及對應的操作3)Redis的所有操作都是原子性的,同時Redis還支持對幾個操作合并后的原子性執行,也即支持事務4)豐富的特性,Redis還支持publish/subscribe,key過期等特性
4、Redis性能以下摘自官方測試描述:在50個并發的情況下請求10W次,寫的速度是11W次/s,讀的速度是8.1w次/s
測試環境:1)50個并發,請求10W次2)讀和寫大小為256bytes的字符串3)Linux2.6 Xeon X3320 2.5GHz的服務器上4)通過本機的loopback interface接口上執行
5、Redis數據類型redis常用五種數據類型:string,hash,list,set,sorted setRedis內部使用一個redisObject對象來表示所有的key和value,redisObject最主要的信息如上圖所示:type代表一個value對象具體是何種數據類型,encoding是不同數據類型在redis內部的存儲方式,比如:type=string代表value存儲的是一個普通字符串,那么對應的encoding可以是raw或者是int,如果是int則代表實際redis內部是按數值型類存儲和表示這個字符串的
Commands 集合: http://redis.io/commands
5.1 String常用命令:set,get,decr,incr,mget 等
應用場景:String是最常用的一種數據類型,普通的key/value存儲
實現方式:String在redis內部存儲默認就是一個字符串,被redisObject所引用,當遇到incr,decr等操作時會轉成數值型進行計算,此時redisObject的encoding字段為int
5.2 Hash常用命令:hget,hset,hgetall 等
應用場景:比如,我們存儲供應商酒店價格的時候可以采取此結構,用酒店編碼作為Key,RatePlan+RoomType作為Filed,價格信息作為Value
實現方式:Hash對應Value內部實際就是一個HashMap,實際這里會有2種不同實現,這個Hash的成員比較少時Redis為了節省內存會采用類似一維數組的方式來緊湊存儲,而不會采用真正的HashMap結構,對應的value redisObject的encoding為zipmap;當成員數量增大時會自動轉成真正的HashMap,此時encoding為ht
5.3 List常用命令:lpush,rpush,lpop,rpop,lrang等
應用場景:Redis list應用場景非常多,也是Redis最重要的數據結構之一,比如twitter的關注列表,粉絲列表等都可以用Redis的list結構來實現
實現方式:Redis list的實現為一個雙向鏈表,即可以支持反向查找和遍歷,更方便操作,不過帶來了部分額外的內存開銷,Redis內部的很多實現,包括發送緩沖隊列等也都是用的這個數據結構
5.4 Set常用命令:sadd,spop,smembers,sunion 等
應用場景:Set對外提供的功能與list類似,當你需要存儲一個列表數據,又不希望出現重復數據時,set 是一個很好的選擇,并且set提供了判斷某個成員是否在一個set集合內的接口,這個也是list所不能提供的
實現方式:Set 的內部實現是一個value永遠為null的HashMap,實際就是通過計算hash的方式來快速排除重復的,這也是set能提供判斷一個成員是否在集合內的原因
5.5 Sorted set常用命令:zadd,zrange,zrem,zcard等
使用場景:Sorted set的使用場景與set類似,區別是set不是自動有序的,而sorted set可以通過用戶額外提供一個優先級(score)的參數來為成員排序,并且是插入有序的,即自動排序.當你需要一個有序的并且不重復的集合列表,那么可以選擇sorted?set數據結構
實現方式:Sorted set的內部使用HashMap和跳躍表(SkipList)來保證數據的存儲和有序,HashMap里放的是成員到score的映射,而跳躍表里存放的是所有的成員,排序依據是HashMap里存的score,使用跳躍表的結構可以獲得比較高的查找效率
5.6 內存優化Redis為不同數據類型分別提供了一組參數來控制內存使用,我們在前面提到過Redis Hash的value內部是一個HashMap,如果該Map的成員數比較少,則會采用一維數組的方式來緊湊存儲該Map,即省去了大量指針的內存開銷,這個參數在redis.conf配置文件中下面2項:? ??hash-max-zipmap-entries ? 64? ??hash-max-zipmap-value ? ? 512
含義是當value這個Map內部不超過多少個成員時會采用線性緊湊格式存儲,默認是64,即value內部有64個以下的成員就是使用線性緊湊存儲,超過該值自動轉成真正的HashMaphash-max-zipmap-value 含義是當value這個Map內部的每個成員值長度不超過多少字節就會采用線性緊湊存儲來節省空間
以上2個條件任意一個條件超 過設置值都會轉換成真正的HashMap,也就不會再節省內存了,那么這個值是不是設置的越大越好呢,答案當然是否定的,HashMap的優勢就是查找和操作的時間復雜度都是O(1)的,而放棄Hash采用一維存儲則是O(n)的時間復雜度,如果成員數量很少,則影響不大,否則會嚴重影響性能,所以要權衡好這個值的設置,總體上還是時間成本和空間成本上的權衡
6、Redis發布/訂閱Redis的發布/訂閱(Publish/Subscribe)功能類似于傳統的消息路由功能,發布者發布消息,訂閱者接收消息,溝通發布者和訂閱者之間的橋梁是訂閱的Channel或者Pattern
訂閱者和發布者之間的關系是松耦合的,發布者不指定哪個訂閱者才能接收消息,訂閱者不只接收特定發布者的消息
7、Redis數據過期設置Redis可以按key設置過期時間,過期后將被自動刪除,這個特性讓Redis很適合用來存儲酒店動態流量和價格信息
用TTL命令可以獲取某個key值的過期時間,-1表示不會過期
8、Redis事務支持Redis目前對事務支持還比較簡單,也即支持一些簡單的組合型的命令,只能保證一個client發起的事務中的命令可以連續的執行,而中間不會插入其他client的命令:由于Redis是單線程來處理所有client的請求的所以做到這點是很容易的
事務的執行過程中,如果redis意外的掛了,這時候事務可能只被執行了一半,可以用redis-check-aof 工具進行修復
9、Redis數據存儲9.1 數據快照數據快照的原理是將整個Redis內存中存的所有數據遍歷一遍后,保存到一個擴展名為rdb的數據文件中。通過SAVE命令可以調用這個過程
9.2 數據快照配置save 900 1save 300 10save 60 10000以上在redis.conf中的配置指出在多長時間內,有多少次更新操作,就將數據同步到數據文件,這個可以多個條件配合.上面的含義是900秒后有一個key發生改變就執行save,300秒后有10個key發生改變執行save,60秒有10000個key發生改變執行save
10、Redis AOF10.1 數據快照的缺點是持久化之后如果出現crash則會丟失一段數據,因此作者增加了另外一種追加式的操作日志記錄,叫append only?file,其日志文件以aof結尾,我們一般稱為aof文件。要開啟aof日志的記錄,需要在配置文件中進行如下設置:appendonly yes
10.2 appendonly配置如果不開啟,可能會在斷電時導致一段時間內的數據丟失。因為redis本身同步數據文件是按save條件來同步的,所以有的數據會在一段時間內只存在于內存中appendfsync no/always/everysec1)no:表示等操作系統進行數據緩存同步到磁盤2)always:表示每次更新操作后手動調用fsync() 將數據寫到磁盤3)everysec:表示每秒同步一次。一般用everysec
10.3 AOF文件只增不減會導致文件越來越大,重寫過程如下1)Redis通過fork產生子進程2)子進程將當前所有數據寫入一個臨時文件3)父子進程是并行執行的,在子進程遍歷并寫臨時文件的時候,父進程在照常接收請求,處理請求,寫AOF,不過這時他是把新來的AOF寫在一個緩沖區中4)子進程寫完臨時文件后就會退出.這時父進程會接收到子進程退出的消息,他會把自己現在收集在緩沖區中的所有AOF追加在臨時文件中5)最后把臨時文件rename一下,改名為appendonly.aof, 這時原來的aof文件被覆蓋。整個過程完成
11、Redis數據恢復當Redis服務器掛掉時,重啟時將按以下優先級恢復數據到內存中:1)如果只配置了AOF,重啟時加載AOF文件恢復數據2)如果同時配置了RBD和AOF,啟動時只加載AOF文件恢復數據3)如果只配置了RDB,啟動時將加載dump文件恢復數據
12、Redis主從復制
12.1?Master/Slave配置Master IP:175.41.209.118Master Redis Server Port:6379
Slave配置很簡單,只需要在slave服務器的redis.conf加入:slaveof 175.41.209.118 6379啟動master和slave,然后寫入數據到master,讀取slave,可以看到數據被復制到slave了
用途:讀寫分離,數據備份,災難恢復等
12.2 Redis主從復制過程配置好slave后,slave與master建立連接,然后發送sync命令。無論是第一次連接還是重新連接,master都會啟動一個后臺進程,將數據庫快照保存到文件中,同時master主進程會開始收集新的寫命令并緩存;后臺進程完成寫文件后,master就發送文件給slave,slave將文件保存到硬盤上,再加載到內存中, 接著master就會把緩存的命令轉發給slave,后續master將收到的寫命令發送給slave;如果master同時收到多個slave發來的同步連接命令,master只會啟動一個進程來寫數據庫鏡像, 然后發送給所有的slave
12.3 Redis主從復制特點1)master可以擁有多個slave2)多個slave可以連接同一個master外,還可以連接到其他slave3)主從復制不會阻塞master,在同步數據時,master可以繼續處理client請求4)可以在master禁用數據持久化,注釋掉master配置文件中的所有save配置,只需在slave上配置數據持久化5)提高系統的伸縮性
12.4 Redis主從復制速度? ??? ??官方提供了一個數據, Slave在21秒即完成了對Amazon網站 10G key set的復制
13、Redis客戶端13.1 Redis的客戶端非常豐富,幾乎所有流行的語言都有客戶端客戶端列表:http://redis.io/clientsJava客戶端推薦Jedis: https://github.com/xetorthio/jedis
13.2 Jedis目前Release版本是3.2.5,支持的特性如下,一句話概括,該有的都有了,不該有的也有了? Sorting? Connection handling? Commands operating on any kind of values? Commands operating on string values? Commands operating on hashes? Commands operating on lists? Commands operating on sets? Commands operating on sorted sets? Transactions? Pipelining? Publish/Subscribe? Persistence control commands? Remote server control commands? Connection pooling? Sharding (MD5, MurmureHash)? Key-tags for sharding? Sharding with pipelining
13.3 Jedis使用添加Maven依賴:<dependency><groupId>redis.clients</groupId><artifactId>jedis</artifactId><version>2.9.0</version><type>jar</type><scope>compile</scope></dependency>
最簡單的使用方式:Jedis jedis = new Jedis("localhost");jedis.set("foo", "bar");String value = jedis.get("foo");
更多高級用法參考:https://github.com/xetorthio/jedis/wiki
14、Redis shard14.1 目前,Redis server沒有提供shard功能,只能在client端實現Redis有些客戶端實現了shard,比如Java客戶端Jedis.
Jedis使用一致性哈希算法實現shard,提供JedisPool,JedisPoolConfig,JedisSharedInfo,ShardedJedisPool等相關類來使用shared功能
14.2 Jedis shardedJedisPool的創建例子<bean id="dataJedisPoolConfig" class="redis.clients.jedis.JedisPoolConfig"><property name="maxActive" value="200"/><property name="maxIdle" value="200"/><property name="maxWait" value="1000"/><property name="testOnBorrow" value="true"/></bean><bean id="dataJedisShardInfo" class="redis.clients.jedis.JedisShardInfo"><constructor-arg index="0" value="${redis.host}"/><constructor-arg index="1" value="${redis.port}"/><constructor-arg index="2" value="10000"/></bean><bean id="dataShardedJedisPool" class="redis.clients.jedis.ShardedJedisPool"><constructor-arg index="0" ref="dataJedisPoolConfig"/><constructor-arg index="1"><list><ref bean="dataJedisShardInfo"/></list></constructor-arg></bean>
14.3 Jedis shardedJedisPool的使用ShardedJedis shardedJedis = shardedJedisPool.getResource();//xxooshardedJedisPool.returnResource(shardedJedis);
15、Redis cluster穩定版本的redis(2.4.5)只支持簡單的master-slave replication: 一個master寫,多個slave讀。只能通過客戶端一致性哈希自己做sharding
Redis cluster是下一階段最重要的功能之一,會有集群的自動sharding,多節點容錯等:集群功將在3.0版本推出
16、Redis Use In ChoiceHotels
16.1 Choice的Redis Server是一主一從,使用亞馬遜AWS虛擬機,機器配置如下:7.5 GB memory4 EC2 Compute Units (2 virtual cores with 2EC2 Compute Units each)64-bit platformI/O Performance: High
16.2 現狀:每天約更新30萬左右的數據,現在庫里有400W條紀錄(400W個Key,使用的是Hash結構存儲),每條數據都設有過期時間,占用了2.5G的內存
為了提高讀寫性能Master關閉了Persistence功能,Slave只負責同步備份Master的數據,不對外提供服務另一種可選方案是用Master提供寫服務,Slave提供讀服務來實現讀寫分離
16.3 Master開啟Save功能的影響:在dump過程中,除了磁盤有大量的IO操作以外,Redis是fork一個子進程來dump數據到硬盤,原有進程占用30%+的CPU,dump數據的子進程單獨另外占用一個CPU
Master開啟Save對性能的直接影響:TPS大概減少30%Choice Master Redis服務器開啟Save功能后的明顯影響是:機器Load一直居高不下,大量請求超時:關閉Save功能后服務器壓力銳減,基本無請求超時情況發生
16.4 Redis開啟AOF日志功能的影響:對性能有影響,但是由于每次追加的數據量小,所以對性能的影響相對小很多Choice Master Reids開啟AOF功能后,機器load微升,對性能無明顯影響
16.5 bgrewriteaof對性能的影響:為了定時減小AOF文件的大小,Redis2.4以后增加了自動的bgrewriteaof的功能,Redis會選擇一個自認為負載低的情況下執行bgrewriteaof,這個重寫AOF文件的過程是很影響性能的Choice Master開啟自動bgrewriteaof功能對系統的明顯影響是:高并發時段有請求超時,機器load 明顯上升幾倍
16.6 目前較好的方案是:Mater關閉Save功能,關閉AOF日志功能,以求達到性能最佳:Slave開啟Save并開啟AOF日志功能,并開啟bgrewriteaof功能,不對外提供服務,這樣Slave的負載總體上會一直略高于Master負載,但Master性能達到最好
16.7 總結:從目前使用的情況來看,總體效果還是比較理想的, ChoiceHotels的價格存儲使用Redis的Hash結構也非常適合,HotelCode+Date最為key, 這樣的key很容易設置過期,RatePlan+RoomType作為Filed, 價格和流量是Value目前每天從GTA到Choice大約500w個請求,整個過程80%的請求在500毫秒內返回,基本無超時現象發生
16.8 Redis Master Inforedis_version:2.4.4connected_clients:171connected_slaves:1used_memory_human:2.37Gused_memory_peak_human:2.46Gaof_enabled:0expired_keys:1595004keyspace_hits:2611419705keyspace_misses:55827727role:masteraof_current_size:3874203906aof_base_size:3850549480db0:keys=4073286,expires=4073286
來自為知筆記(Wiz)
2、Redis安裝Download, extract and compile Redis with:$ wget http://download.redis.io/releases/redis-3.2.5.tar.gz $ tar xzf redis-3.2.5.tar.gz$ cd redis-3.2.5$ make
The binaries that are now compiled are available in the src directory:Run Redis with:
$ src/redis-serverYou can interact with Redis using the built-in client:$ src/redis-cliredis> set foo barOKredis> get foo"bar"
3、Redis優點1)性能極高,Redis能支持10萬每秒的讀寫頻率2)豐富的數據類型及對應的操作3)Redis的所有操作都是原子性的,同時Redis還支持對幾個操作合并后的原子性執行,也即支持事務4)豐富的特性,Redis還支持publish/subscribe,key過期等特性
4、Redis性能以下摘自官方測試描述:在50個并發的情況下請求10W次,寫的速度是11W次/s,讀的速度是8.1w次/s
測試環境:1)50個并發,請求10W次2)讀和寫大小為256bytes的字符串3)Linux2.6 Xeon X3320 2.5GHz的服務器上4)通過本機的loopback interface接口上執行
5、Redis數據類型redis常用五種數據類型:string,hash,list,set,sorted setRedis內部使用一個redisObject對象來表示所有的key和value,redisObject最主要的信息如上圖所示:type代表一個value對象具體是何種數據類型,encoding是不同數據類型在redis內部的存儲方式,比如:type=string代表value存儲的是一個普通字符串,那么對應的encoding可以是raw或者是int,如果是int則代表實際redis內部是按數值型類存儲和表示這個字符串的
Commands 集合: http://redis.io/commands
5.1 String常用命令:set,get,decr,incr,mget 等
應用場景:String是最常用的一種數據類型,普通的key/value存儲
實現方式:String在redis內部存儲默認就是一個字符串,被redisObject所引用,當遇到incr,decr等操作時會轉成數值型進行計算,此時redisObject的encoding字段為int
5.2 Hash常用命令:hget,hset,hgetall 等
應用場景:比如,我們存儲供應商酒店價格的時候可以采取此結構,用酒店編碼作為Key,RatePlan+RoomType作為Filed,價格信息作為Value
實現方式:Hash對應Value內部實際就是一個HashMap,實際這里會有2種不同實現,這個Hash的成員比較少時Redis為了節省內存會采用類似一維數組的方式來緊湊存儲,而不會采用真正的HashMap結構,對應的value redisObject的encoding為zipmap;當成員數量增大時會自動轉成真正的HashMap,此時encoding為ht
5.3 List常用命令:lpush,rpush,lpop,rpop,lrang等
應用場景:Redis list應用場景非常多,也是Redis最重要的數據結構之一,比如twitter的關注列表,粉絲列表等都可以用Redis的list結構來實現
實現方式:Redis list的實現為一個雙向鏈表,即可以支持反向查找和遍歷,更方便操作,不過帶來了部分額外的內存開銷,Redis內部的很多實現,包括發送緩沖隊列等也都是用的這個數據結構
5.4 Set常用命令:sadd,spop,smembers,sunion 等
應用場景:Set對外提供的功能與list類似,當你需要存儲一個列表數據,又不希望出現重復數據時,set 是一個很好的選擇,并且set提供了判斷某個成員是否在一個set集合內的接口,這個也是list所不能提供的
實現方式:Set 的內部實現是一個value永遠為null的HashMap,實際就是通過計算hash的方式來快速排除重復的,這也是set能提供判斷一個成員是否在集合內的原因
5.5 Sorted set常用命令:zadd,zrange,zrem,zcard等
使用場景:Sorted set的使用場景與set類似,區別是set不是自動有序的,而sorted set可以通過用戶額外提供一個優先級(score)的參數來為成員排序,并且是插入有序的,即自動排序.當你需要一個有序的并且不重復的集合列表,那么可以選擇sorted?set數據結構
實現方式:Sorted set的內部使用HashMap和跳躍表(SkipList)來保證數據的存儲和有序,HashMap里放的是成員到score的映射,而跳躍表里存放的是所有的成員,排序依據是HashMap里存的score,使用跳躍表的結構可以獲得比較高的查找效率
5.6 內存優化Redis為不同數據類型分別提供了一組參數來控制內存使用,我們在前面提到過Redis Hash的value內部是一個HashMap,如果該Map的成員數比較少,則會采用一維數組的方式來緊湊存儲該Map,即省去了大量指針的內存開銷,這個參數在redis.conf配置文件中下面2項:? ??hash-max-zipmap-entries ? 64? ??hash-max-zipmap-value ? ? 512
含義是當value這個Map內部不超過多少個成員時會采用線性緊湊格式存儲,默認是64,即value內部有64個以下的成員就是使用線性緊湊存儲,超過該值自動轉成真正的HashMaphash-max-zipmap-value 含義是當value這個Map內部的每個成員值長度不超過多少字節就會采用線性緊湊存儲來節省空間
以上2個條件任意一個條件超 過設置值都會轉換成真正的HashMap,也就不會再節省內存了,那么這個值是不是設置的越大越好呢,答案當然是否定的,HashMap的優勢就是查找和操作的時間復雜度都是O(1)的,而放棄Hash采用一維存儲則是O(n)的時間復雜度,如果成員數量很少,則影響不大,否則會嚴重影響性能,所以要權衡好這個值的設置,總體上還是時間成本和空間成本上的權衡
6、Redis發布/訂閱Redis的發布/訂閱(Publish/Subscribe)功能類似于傳統的消息路由功能,發布者發布消息,訂閱者接收消息,溝通發布者和訂閱者之間的橋梁是訂閱的Channel或者Pattern
訂閱者和發布者之間的關系是松耦合的,發布者不指定哪個訂閱者才能接收消息,訂閱者不只接收特定發布者的消息
7、Redis數據過期設置Redis可以按key設置過期時間,過期后將被自動刪除,這個特性讓Redis很適合用來存儲酒店動態流量和價格信息
用TTL命令可以獲取某個key值的過期時間,-1表示不會過期
8、Redis事務支持Redis目前對事務支持還比較簡單,也即支持一些簡單的組合型的命令,只能保證一個client發起的事務中的命令可以連續的執行,而中間不會插入其他client的命令:由于Redis是單線程來處理所有client的請求的所以做到這點是很容易的
事務的執行過程中,如果redis意外的掛了,這時候事務可能只被執行了一半,可以用redis-check-aof 工具進行修復
9、Redis數據存儲9.1 數據快照數據快照的原理是將整個Redis內存中存的所有數據遍歷一遍后,保存到一個擴展名為rdb的數據文件中。通過SAVE命令可以調用這個過程
9.2 數據快照配置save 900 1save 300 10save 60 10000以上在redis.conf中的配置指出在多長時間內,有多少次更新操作,就將數據同步到數據文件,這個可以多個條件配合.上面的含義是900秒后有一個key發生改變就執行save,300秒后有10個key發生改變執行save,60秒有10000個key發生改變執行save
10、Redis AOF10.1 數據快照的缺點是持久化之后如果出現crash則會丟失一段數據,因此作者增加了另外一種追加式的操作日志記錄,叫append only?file,其日志文件以aof結尾,我們一般稱為aof文件。要開啟aof日志的記錄,需要在配置文件中進行如下設置:appendonly yes
10.2 appendonly配置如果不開啟,可能會在斷電時導致一段時間內的數據丟失。因為redis本身同步數據文件是按save條件來同步的,所以有的數據會在一段時間內只存在于內存中appendfsync no/always/everysec1)no:表示等操作系統進行數據緩存同步到磁盤2)always:表示每次更新操作后手動調用fsync() 將數據寫到磁盤3)everysec:表示每秒同步一次。一般用everysec
10.3 AOF文件只增不減會導致文件越來越大,重寫過程如下1)Redis通過fork產生子進程2)子進程將當前所有數據寫入一個臨時文件3)父子進程是并行執行的,在子進程遍歷并寫臨時文件的時候,父進程在照常接收請求,處理請求,寫AOF,不過這時他是把新來的AOF寫在一個緩沖區中4)子進程寫完臨時文件后就會退出.這時父進程會接收到子進程退出的消息,他會把自己現在收集在緩沖區中的所有AOF追加在臨時文件中5)最后把臨時文件rename一下,改名為appendonly.aof, 這時原來的aof文件被覆蓋。整個過程完成
11、Redis數據恢復當Redis服務器掛掉時,重啟時將按以下優先級恢復數據到內存中:1)如果只配置了AOF,重啟時加載AOF文件恢復數據2)如果同時配置了RBD和AOF,啟動時只加載AOF文件恢復數據3)如果只配置了RDB,啟動時將加載dump文件恢復數據
12、Redis主從復制
12.1?Master/Slave配置Master IP:175.41.209.118Master Redis Server Port:6379
Slave配置很簡單,只需要在slave服務器的redis.conf加入:slaveof 175.41.209.118 6379啟動master和slave,然后寫入數據到master,讀取slave,可以看到數據被復制到slave了
用途:讀寫分離,數據備份,災難恢復等
12.2 Redis主從復制過程配置好slave后,slave與master建立連接,然后發送sync命令。無論是第一次連接還是重新連接,master都會啟動一個后臺進程,將數據庫快照保存到文件中,同時master主進程會開始收集新的寫命令并緩存;后臺進程完成寫文件后,master就發送文件給slave,slave將文件保存到硬盤上,再加載到內存中, 接著master就會把緩存的命令轉發給slave,后續master將收到的寫命令發送給slave;如果master同時收到多個slave發來的同步連接命令,master只會啟動一個進程來寫數據庫鏡像, 然后發送給所有的slave
12.3 Redis主從復制特點1)master可以擁有多個slave2)多個slave可以連接同一個master外,還可以連接到其他slave3)主從復制不會阻塞master,在同步數據時,master可以繼續處理client請求4)可以在master禁用數據持久化,注釋掉master配置文件中的所有save配置,只需在slave上配置數據持久化5)提高系統的伸縮性
12.4 Redis主從復制速度? ??? ??官方提供了一個數據, Slave在21秒即完成了對Amazon網站 10G key set的復制
13、Redis客戶端13.1 Redis的客戶端非常豐富,幾乎所有流行的語言都有客戶端客戶端列表:http://redis.io/clientsJava客戶端推薦Jedis: https://github.com/xetorthio/jedis
13.2 Jedis目前Release版本是3.2.5,支持的特性如下,一句話概括,該有的都有了,不該有的也有了? Sorting? Connection handling? Commands operating on any kind of values? Commands operating on string values? Commands operating on hashes? Commands operating on lists? Commands operating on sets? Commands operating on sorted sets? Transactions? Pipelining? Publish/Subscribe? Persistence control commands? Remote server control commands? Connection pooling? Sharding (MD5, MurmureHash)? Key-tags for sharding? Sharding with pipelining
13.3 Jedis使用添加Maven依賴:<dependency><groupId>redis.clients</groupId><artifactId>jedis</artifactId><version>2.9.0</version><type>jar</type><scope>compile</scope></dependency>
最簡單的使用方式:Jedis jedis = new Jedis("localhost");jedis.set("foo", "bar");String value = jedis.get("foo");
更多高級用法參考:https://github.com/xetorthio/jedis/wiki
14、Redis shard14.1 目前,Redis server沒有提供shard功能,只能在client端實現Redis有些客戶端實現了shard,比如Java客戶端Jedis.
Jedis使用一致性哈希算法實現shard,提供JedisPool,JedisPoolConfig,JedisSharedInfo,ShardedJedisPool等相關類來使用shared功能
14.2 Jedis shardedJedisPool的創建例子<bean id="dataJedisPoolConfig" class="redis.clients.jedis.JedisPoolConfig"><property name="maxActive" value="200"/><property name="maxIdle" value="200"/><property name="maxWait" value="1000"/><property name="testOnBorrow" value="true"/></bean><bean id="dataJedisShardInfo" class="redis.clients.jedis.JedisShardInfo"><constructor-arg index="0" value="${redis.host}"/><constructor-arg index="1" value="${redis.port}"/><constructor-arg index="2" value="10000"/></bean><bean id="dataShardedJedisPool" class="redis.clients.jedis.ShardedJedisPool"><constructor-arg index="0" ref="dataJedisPoolConfig"/><constructor-arg index="1"><list><ref bean="dataJedisShardInfo"/></list></constructor-arg></bean>
14.3 Jedis shardedJedisPool的使用ShardedJedis shardedJedis = shardedJedisPool.getResource();//xxooshardedJedisPool.returnResource(shardedJedis);
15、Redis cluster穩定版本的redis(2.4.5)只支持簡單的master-slave replication: 一個master寫,多個slave讀。只能通過客戶端一致性哈希自己做sharding
Redis cluster是下一階段最重要的功能之一,會有集群的自動sharding,多節點容錯等:集群功將在3.0版本推出
16、Redis Use In ChoiceHotels
16.1 Choice的Redis Server是一主一從,使用亞馬遜AWS虛擬機,機器配置如下:7.5 GB memory4 EC2 Compute Units (2 virtual cores with 2EC2 Compute Units each)64-bit platformI/O Performance: High
16.2 現狀:每天約更新30萬左右的數據,現在庫里有400W條紀錄(400W個Key,使用的是Hash結構存儲),每條數據都設有過期時間,占用了2.5G的內存
為了提高讀寫性能Master關閉了Persistence功能,Slave只負責同步備份Master的數據,不對外提供服務另一種可選方案是用Master提供寫服務,Slave提供讀服務來實現讀寫分離
16.3 Master開啟Save功能的影響:在dump過程中,除了磁盤有大量的IO操作以外,Redis是fork一個子進程來dump數據到硬盤,原有進程占用30%+的CPU,dump數據的子進程單獨另外占用一個CPU
Master開啟Save對性能的直接影響:TPS大概減少30%Choice Master Redis服務器開啟Save功能后的明顯影響是:機器Load一直居高不下,大量請求超時:關閉Save功能后服務器壓力銳減,基本無請求超時情況發生
16.4 Redis開啟AOF日志功能的影響:對性能有影響,但是由于每次追加的數據量小,所以對性能的影響相對小很多Choice Master Reids開啟AOF功能后,機器load微升,對性能無明顯影響
16.5 bgrewriteaof對性能的影響:為了定時減小AOF文件的大小,Redis2.4以后增加了自動的bgrewriteaof的功能,Redis會選擇一個自認為負載低的情況下執行bgrewriteaof,這個重寫AOF文件的過程是很影響性能的Choice Master開啟自動bgrewriteaof功能對系統的明顯影響是:高并發時段有請求超時,機器load 明顯上升幾倍
16.6 目前較好的方案是:Mater關閉Save功能,關閉AOF日志功能,以求達到性能最佳:Slave開啟Save并開啟AOF日志功能,并開啟bgrewriteaof功能,不對外提供服務,這樣Slave的負載總體上會一直略高于Master負載,但Master性能達到最好
16.7 總結:從目前使用的情況來看,總體效果還是比較理想的, ChoiceHotels的價格存儲使用Redis的Hash結構也非常適合,HotelCode+Date最為key, 這樣的key很容易設置過期,RatePlan+RoomType作為Filed, 價格和流量是Value目前每天從GTA到Choice大約500w個請求,整個過程80%的請求在500毫秒內返回,基本無超時現象發生
16.8 Redis Master Inforedis_version:2.4.4connected_clients:171connected_slaves:1used_memory_human:2.37Gused_memory_peak_human:2.46Gaof_enabled:0expired_keys:1595004keyspace_hits:2611419705keyspace_misses:55827727role:masteraof_current_size:3874203906aof_base_size:3850549480db0:keys=4073286,expires=4073286
來自為知筆記(Wiz)
總結
以上是生活随笔為你收集整理的Redis介绍及实践分享的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: python学习笔记(12)-pytho
- 下一篇: 利用mycat实现mysql数据库读写分