天天看點

Jedis源碼分析(四)-JedisSentinel與ShardedJedis介紹

Jedis源碼分析共有四個章節,以下為各章連結:

  1. Jedis源碼分析(一)-Jedis介紹
  2. Jedis源碼分析(二)-Jedis類結構及實作
  3. Jedis源碼分析(三)- JedisCluster類結構及實作
  4. Jedis源碼分析(四)-JedisSentinel與ShardedJedis介紹

1 JedisSentinel

JedisSentinel常用方式有兩種:

1.使用哨兵單節點拿到主節點,從節點的資訊

//通過哨兵節點的資訊建立Jedis執行個體,然後拿到Master節點的資訊
Jedis j = new Jedis(sentinel);
List<Map<String, String>> masters = j.sentinelMasters();
//拿到master的address,**MASTER_NAME**
List<String> masterHostAndPort = j.sentinelGetMasterAddrByName(**MASTER_NAME**);
HostAndPort masterFromSentinel = new HostAndPort(masterHostAndPort.get(0),Integer.parseInt(masterHostAndPort.get(1)));
assertEquals(master, masterFromSentinel);
//通過哨兵節點,拿到從節點的資訊
List<Map<String, String>> slaves = j.sentinelSlaves(**MASTER_NAME**);
           

2.使用哨兵節點對象池

Set<String> sentinels = new HashSet<String>();
sentinels.add(new HostAndPort("localhost", 65432).toString());
sentinels.add(new HostAndPort("localhost", 65431).toString());
JedisSentinelPool pool = new JedisSentinelPool(MASTER_NAME, sentinels);
pool.destroy();
           

​ 

JedisSentinelPool

的結構清晰,内部使用對象池存放一個個

sentinel

執行個體。圖2-12和2-13分别為

JedisSentinelPool

的類結構和初始化流程。在使用時,我們先根據,host,port等資訊,初始化一個Jedis執行個體,然後可以通過

sentinelMasters()

sentinelGetMasterAddrByName(MASTER_NAME)

sentinelSlaves(MASTER_NAME)

等方法拿到這個哨兵節點監聽的MASTER節點資訊或對應的SLAVE節點資訊。

Jedis源碼分析(四)-JedisSentinel與ShardedJedis介紹

​ 圖1.1 JedisSentinelPool 的類結構

Jedis源碼分析(四)-JedisSentinel與ShardedJedis介紹

​ 圖1.2 JedisSentinelPool 的初始化流程

2 ShardedJedis

下文為建構Jedis分片的方法(單節點與對象池的模式),

  1. 單節點模式
List<JedisShardInfo> shards = new ArrayList<JedisShardInfo>(2);
//其中一個分片
JedisShardInfo shard1 = new JedisShardInfo(redis1);
shards.add(shard1);
//另一個分片
JedisShardInfo shard2 = new JedisShardInfo(redis2);
shards.add(shard2);
@SuppressWarnings("resource")
//建立ShardedJedis執行個體
ShardedJedis shardedJedis = new ShardedJedis(shards);
shardedJedis.set("a", "bar");
//通過key可以檢視存儲在哪個jedis
JedisShardInfo ak = shardedJedis.getShardInfo("a");
assertEquals(shard2, ak);
           
  1. 對象池模式
ShardedJedisPool pool = new ShardedJedisPool(new GenericObjectPoolConfig(), shards);
ShardedJedis jedis = pool.getResource();
jedis.set("foo", "bar");
assertEquals("bar", jedis.get("foo"));
           
Jedis源碼分析(四)-JedisSentinel與ShardedJedis介紹

圖2-1 ShardedJedis的類結構

Jedis源碼分析(四)-JedisSentinel與ShardedJedis介紹

​ 圖2-2 ShardedJedis的初始化流程

​ 圖2-1為ShardedJedis的類結構(其内部儲存一個對象池,與正常的JedisPool的不同之處在于,内部的

PooledObjectFactory

實作不同),分片資訊儲存在基類

Sharded

中,

Sharded

儲存了3個重要變量:

  1. nodes是一個TreeMap,儲存了每個分片節點和對應的hash值。
  2. algo是計算hash值的函數,預設是MurmurHash,可替換。
  3. resources是一個LinkedHashMap,存放着JedisShardinfo和一個Jedis執行個體的對應關系。

​ 圖2-2為 

ShardedJedis

的初始化流程,通過傳入待分片的節點資訊,初始化好上述3個變量。在使用時,先根據key計算出hash值,在

nodes

中找到對應的分片資訊,再在

resources

中找到對應的Jedis執行個體,然後通過這個Jedis執行個體才操作redis節點。

繼續閱讀