(一)擷取Jedis
Jedis是基于java語言的redis_cli
maven依賴:
<!-- Redis的redis用戶端
(二)Jedis基本使用
1、Jedis直連:
Jedis直連相當于一個TCP連接配接,資料傳輸完成後關閉連接配接
//1.生成一個Jedis對象,這個對象負責和指定的Redis節點進行通信
2、Jedis構造函數參數的意義:
Jedis(String host, int port, int connectionTimeout, int soTimeout)
host:Redis節點所在的機器的IP
port:Redis節點的端口
connectionTimeout:用戶端連接配接逾時
soTimeout:用戶端讀寫逾時
3、簡單使用:
//Jedis資料類型:
(三)Jedis連接配接池基本使用
1、Jedis Pool的簡單介紹
使用Jedis線程池可以不需要建立新的Jedis對象連接配接Redis,可以大大減少對于建立和回收Redis連接配接的開銷
2、對使用線程池和使用Jedis直連兩方案的對比
3、Jedis Pool的簡單使用
通常來講JedisPool是單例的
GenericObjectPoolConfig
4、Jedis配置優化思路
規劃出連接配接池最大連接配接數,最大空閑數,最小空閑數,如果在借用池中連接配接沒有資源時,是等待還是逾時,如何控制連接配接池中的空閑對象。
1)如何确定maxTotal?
首先舉個例子:
1.指令平均執行時間0.1ms = 0.001s。
2.業務需要50000QPS
3.maxTotal理論值 = 0.001*50000=50個。但是實際設計時可能會偏大一些。
由以上可以得出,需要考慮:業務希望的Redis并發量、客戶執行指令的時間、Redis資源:例如nodes(應用個數)+maxTotal是不能超過redis的最大連接配接數的(config get maxclients)
2)如何确定合适的maxIdle和minIdle?
建議maxIdle=maxTotal,為什麼這麼說呢?假如現在maxTotal是100,maxIdle是50,那麼允許的最大空閑數是50,那麼在一個高峰期,如果連接配接池中的50個已經通過連接配接池的getResource擷取到了,這個時候第51個連接配接是要通過newJedis以及TCP三向交握建立一個新的連接配接,實際上這本身是有一定開銷的。這樣可以減少新的開銷。建議預熱minIdle,第一次getResource時是newJedis并建立TCP三向交握的,對于并發量較大的情況是無法容忍第一次開銷的,那麼可以在應用初始化的時候提前使用getResource做一些操作。
5、常見問題:
擷取連接配接逾時,主要原因在maxWaitMills這個參數:
#
解決這一類問題的思路:
1.慢查詢阻塞:連接配接池連接配接都被hang住。比如多個連接配接都在執行keys *,或者這redis本身的單線程被阻塞,當這兩種情況發生時,都會出現上面兩個問題,這就需要對每個操作設定逾時時間,對maxWaitMills進行合理配置去觀察是否合理,最重要的就是去解決這些慢查詢。
2.資源池參數不合理:比如QPS高,連接配接池小。
3.連接配接洩露(沒有close()):這類問題比較難定位,比如使用client list、netstat等,最重要的是寫合理的代碼,比如不使用try catch finally,如果中間發生了異常,close就無法執行了。
4.DNS異常也會導緻這種問題。
舉個例子(隻要将注釋内的内容取消就可以解決bug了):
public static void main(String[] args) {
JedisPoolConfig poolConfig = new JedisPoolConfig();
poolConfig.setMaxTotal(10);
poolConfig.setMaxWaitMillis(1000);
JedisPool jedisPool = new JedisPool(poolConfig, "127.0.0.1", 6379);
for (int i = 0; i < 10; i++) {
Jedis jedis = null;
try {
jedis = jedisPool.getResource();
jedis.ping();
} catch (Exception e) {
e.printStackTrace();
/*} finally {
if (jedis != null) {
jedisPool.close();
}*/
}
}
jedisPool.getResource().ping();
}