redis做緩衝的簡單一實例

來源:互聯網
上載者:User

由於之前對redis有了一個系統的研究,在公司的多重專案中使用redis當做資料緩衝;所以趁著這些天晚上的時間,自己寫了一個demo;這裡僅供自己後期學習筆記參考,若有不對的地方,請輕拍磚。

redis 官網推薦給java 使用的用戶端很多:Jedis、Redisson、JRedis、JDBC-Redis 等,當然首推是jedis;可以參考redis用戶端官網查看。

接下來來講下我的這個demo,我這個案例不是通過spring進行整合的redis,這個將會在之後的demo中講到的。

(1).建立一個maven 功臣,在工程的pom 中引入jedis用戶端;還有要依賴spring管理,所以也要引入spring相關jar包。

<span style="white-space:pre"></span><dependency><groupId>redis.clients</groupId><artifactId>jedis</artifactId><version>${jedis-version}</version></dependency><dependency>

(2).一般一個(系統)項目所用的redis伺服器 多節點的叢集伺服器,所以會自己對(jedis)redis用戶端進行封裝,由於本例我自己寫的是單節點,但是我還是按多節點的思路對用戶端進行了封裝。

redisClient類

/** * redis 用戶端封裝 * @author leo * */public class RedisClient  {/** * 日誌記錄 */private static final Log LOG = LogFactory.getLog(RedisClient.class);/** * redis 串連池 */private JedisPool pool;public void setPool(JedisPool pool) {this.pool = pool;}/** * 擷取jedis  * @return */public Jedis getResource(){Jedis jedis =null;try {jedis =pool.getResource();} catch (Exception e) {LOG.info("can't  get  the redis resource");}return jedis;}/** * 關閉串連 * @param jedis */public void disconnect(Jedis jedis){jedis.disconnect();}/** * 將jedis 返還串連池 * @param jedis */public void returnResource(Jedis jedis){if(null != jedis){try {pool.returnResource(jedis);} catch (Exception e) {LOG.info("can't return jedis to jedisPool");}}}/** * 無法返還jedispool,釋放jedis用戶端對象, * @param jedis */public void brokenResource(Jedis jedis){if (jedis!=null) {try {pool.returnBrokenResource(jedis);} catch (Exception e) {LOG.info("can't release jedis Object");}}}}
然後 通過spring的bean.xml 來管理 串連池,和串連池參數配置,以及redisClient 的依賴注入。

<!-- jedis 串連池配置參數:  --><bean id="poolConfig" class="redis.clients.jedis.JedisPoolConfig"><property name="maxActive" value="100"></property><property name="maxIdle" value="25"></property><property name="maxWait" value="15000"></property><property name="testOnBorrow" value="false"></property><property name="testOnReturn" value="false"></property></bean><!-- jedis 串連池  串連本地redis服務 構造器注入--><bean id="pool" class="redis.clients.jedis.JedisPool"><constructor-arg index="0"  ref="poolConfig"/> <constructor-arg index="1" value="10.224.68.46"/> <constructor-arg index="2" value="6379"/><constructor-arg index="3" value="2000"/> </bean><!-- cleint--><bean id="redisClient" class="com.deppon.cache.redis.RedisClient"><property name="pool" ref="pool"/></bean>
(3).建立好redisClient 之後,我要創造一個儲存空間,即一個對redis操作的工具容器。由於是公用容器,所以我建立介面是的容器介面就不該是封閉的,應該是開封的,保證存入資料庫中物件類型的多態性。

儲存空間介面:

/** *  * @author leo *緩衝儲存介面 * @param <K> key * @param <V> value */public interface RedisCacheStorage<K, V> {/** * 在redis資料庫中插入 key  和value * @param key * @param value * @return */boolean set(K key,V value);/** * 在redis資料庫中插入 key  和value 並且設定到期時間 * @param key * @param value * @param exp 到期時間 s * @return */boolean set(K key, V value, int exp);/** * 根據key 去redis 中擷取value * @param key * @return */V get(K key);/** * 刪除redis庫中的資料 * @param key * @return */boolean remove(K key);/** * 設定雜湊類型資料到redis 資料庫 * @param cacheKey 可以看做一張表 * @param key表欄位 * @param value   * @return */boolean hset(String cacheKey,K key,V value);/** * 擷取雜湊表資料類型的值 * @param cacheKey * @param key * @return */V hget(String cacheKey,K key);/** * 擷取雜湊類型的資料 * @param cacheKey * @return */Map<K,V> hget(String cacheKey);
以及儲存實作類別:

/** * redis 緩衝儲存空間實現 * @author leo * * @param <V> */public class RedisCacheStorageImpl<V> implements RedisCacheStorage<String, V> {/** * 日誌記錄 */public static final Log LOG = LogFactory.getLog(RedisCacheStorageImpl.class);/** * redis 用戶端 */private RedisClient redisClient;/** * 預設過時時間 */private static final int EXPRIE_TIME =3600*24; public void setRedisClient(RedisClient redisClient) {this.redisClient = redisClient;}/** * 在redis資料庫中插入 key  和value * @param key * @param value * @return */@Overridepublic boolean set(String key, V value) {//設定預設過時時間return set(key, value, EXPRIE_TIME);}/** * 在redis資料庫中插入 key  和value 並且設定到期時間 * @param key * @param value * @param exp 到期時間 s * @return */@SuppressWarnings("finally")@Overridepublic boolean set(String key, V value, int exp) {Jedis jedis =null;//將key 和value  轉換成 json 對象String jKey =CacheUtils.toJsonString(key);String jValue =CacheUtils.toJsonString(value);//操作是否成功boolean isSucess =true;if(StringUtils.isNotEmpty(jKey)){LOG.info("key is empty");return false;}try {//擷取用戶端對象jedis =redisClient.getResource();//執行插入jedis.setex(jKey, exp, jValue);} catch (JedisException e) {LOG.info("client can't connect server");isSucess =false;if(null !=jedis){//釋放jedis對象redisClient.brokenResource(jedis);}return false;}finally{if(isSucess){//返還串連池redisClient.returnResource(jedis);}return true;}}/** * 根據key 去redis 中擷取value * @param key * @return */@SuppressWarnings("unchecked")@Overridepublic V get(String key) {Jedis jedis =null;//將key 和value  轉換成 json 對象String jKey =CacheUtils.toJsonString(key);V jValue =null;//key 不可為空if(StringUtils.isEmpty(jKey)){LOG.info("key is empty");return null;}try {//擷取用戶端對象jedis =redisClient.getResource();//執行查詢String value =jedis.get(jKey);//判斷值是否非空if(StringUtils.isEmpty(value)){return null;}else{jValue= (V) CacheUtils.jsonParseObject(value);}//返還串連池redisClient.returnResource(jedis);} catch (JedisException e) {LOG.info("client can't connect server");if(null !=jedis){//釋放jedis 對象redisClient.brokenResource(jedis);}}return jValue;}/** * 刪除redis庫中的資料 * @param key * @return */@SuppressWarnings("finally")@Overridepublic boolean remove(String key) {Jedis jedis =null;//將key 和value  轉換成 json 對象String jKey =CacheUtils.toJsonString(key);//操作是否成功boolean isSucess =true;if(StringUtils.isEmpty(jKey)){LOG.info("key is empty");return false;}try {jedis =redisClient.getResource();//執行刪除jedis.del(jKey);} catch (JedisException e) {LOG.info("client can't connect server");isSucess =false;if(null !=jedis){//釋放jedis 對象redisClient.brokenResource(jedis);}return false;}finally{if (isSucess) {//返還串連池redisClient.returnResource(jedis);}return true;}}/** * 設定雜湊類型資料到redis 資料庫 * @param cacheKey 可以看做一張表 * @param key表欄位 * @param value   * @return */@SuppressWarnings("finally")@Overridepublic boolean hset(String cacheKey, String key, V value) {Jedis jedis =null;//將key 和value  轉換成 json 對象String jKey =CacheUtils.toJsonString(key);String jCacheKey =CacheUtils.toJsonString(cacheKey);String jValue =CacheUtils.toJsonString(value);//操作是否成功boolean isSucess =true;if(StringUtils.isEmpty(jCacheKey)){LOG.info("cacheKey is empty");return false;}try {jedis =redisClient.getResource();//執行插入雜湊jedis.hset(jCacheKey, jKey, jValue);} catch (JedisException e) {LOG.info("client can't connect server");isSucess =false;if(null !=jedis){//釋放jedis 對象redisClient.brokenResource(jedis);}return false;}finally{if (isSucess) {//返還串連池redisClient.returnResource(jedis);}return true;}}/** * 擷取雜湊表資料類型的值 * @param cacheKey * @param key * @return */@SuppressWarnings("unchecked")@Overridepublic V hget(String cacheKey, String key) {Jedis jedis =null;//將key 和value  轉換成 json 對象String jKey =CacheUtils.toJsonString(key);String jCacheKey =CacheUtils.toJsonString(cacheKey);V jValue =null;if(StringUtils.isEmpty(jCacheKey)){LOG.info("cacheKey is empty");return null;}try {//擷取用戶端對象jedis =redisClient.getResource();//執行查詢String value =jedis.hget(jCacheKey, jKey);//判斷值是否非空if(StringUtils.isEmpty(value)){return null;}else{jValue= (V) CacheUtils.jsonParseObject(value);}//返還串連池redisClient.returnResource(jedis);} catch (JedisException e) {LOG.info("client can't connect server");if(null !=jedis){//釋放jedis 對象redisClient.brokenResource(jedis);}}return jValue;}/** * 擷取雜湊類型的資料 * @param cacheKey * @return */@Overridepublic Map<String, V> hget(String cacheKey) {String jCacheKey =CacheUtils.toJsonString(cacheKey);//非空校正if(StringUtils.isEmpty(jCacheKey)){LOG.info("cacheKey is empty!");return null;}Jedis jedis =null;Map<String,V> result =null;try {jedis =redisClient.getResource();//擷取列表集合Map<String,String> map = jedis.hgetAll(jCacheKey); if(null !=map){for(Map.Entry<String, String> entry : map.entrySet()){if(result ==null){result =new HashMap<String,V>();}result.put((String) CacheUtils.jsonParseObject(entry.getKey()), (V)CacheUtils.jsonParseObject(entry.getValue()));}}} catch (JedisException e) {LOG.info("client can't connect server");if(null !=jedis){//釋放jedis 對象redisClient.brokenResource(jedis);}}return result;}}
(4),接下來要把寫個具體的業務UserService,來測試redis的儲存空間在具體業務中的使用,即實現(非關係型資料庫的持久化操作)。本例中的例子是經常項目中對user的操作

建立UserEntity實體類:

/** * 使用者實體類 * @author leo * */public class UserEntity {//使用者idprivate String userId;//使用者帳號private String EmpCode;//使用者名稱稱private String EmpName;//使用者角色private String role;//職位private String title;public String getUserId() {return userId;}public void setUserId(String userId) {this.userId = userId;}public String getEmpCode() {return EmpCode;}public void setEmpCode(String empCode) {EmpCode = empCode;}public String getEmpName() {return EmpName;}public void setEmpName(String empName) {EmpName = empName;}public String getRole() {return role;}public void setRole(String role) {this.role = role;}public String getTitle() {return title;}public void setTitle(String title) {this.title = title;}
然後建立使用者操作的業務層Service;由於這裡主要是測試NOSQL的資料持久化,所以就忽略了對資料庫持久化層(DAO)的操作。

userServiceImpl類:

/** * 業務層介面實現 * @author leo * */public class UserServiceImpl implements IUserService {private static final String  cacheKey  ="userEntity";/** * 緩衝儲存 */private RedisCacheStorageImpl<UserEntity> storageCache;public void setStorageCache(RedisCacheStorageImpl<UserEntity> storageCache) {this.storageCache = storageCache;}/** * 新增 * @param entity * @return */@Overridepublic boolean addUserEntity(UserEntity entity) {//非空if(entity ==null || StringUtils.isEmpty(entity.getUserId())){return false;}/** * 做資料庫持久化,這裡就無需再申明了 */System.out.println("先插入資料庫中,.........");//然後接下來做非關係型資料庫持久化return storageCache.hset(cacheKey, entity.getUserId(), entity);}@Overridepublic boolean deleteUserEntity(UserEntity entity) {return false;}/** * 根據id 查詢 * @return */@Overridepublic UserEntity queryUserEntityByUserId(UserEntity userEntity) {//非空if(userEntity ==null || StringUtils.isEmpty(userEntity.getUserId())){return null;}//先去緩衝中查詢 是否存在,不存在在查詢 UserEntity reslut = storageCache.hget(cacheKey, userEntity.getUserId());if(reslut!=null){return reslut;}else{//查詢資料庫System.out.println("查詢資料庫");}return null;}}
以及spring-bean.xml的配置對業務層的管理:

<!-- storge Cache 儲存空間--><bean id="storageCache" class="com.deppon.cache.storage.impl.RedisCacheStorageImpl"><property name="redisClient" ref="redisClient" /></bean><bean id="userServiceImpl" class="com.deppon.cache.service.impl.UserServiceImpl"><property name="storageCache" ref="storageCache"/></bean>
(6).最後寫個junit 測下,查看是否有沒有插入到redis庫中

public class TestUserServiceImpl {/** * 使用者介面 */private IUserService userServiceImpl;public void setUserServiceImpl(IUserService userServiceImpl) {this.userServiceImpl = userServiceImpl;}@Beforepublic void setUp() throws Exception {userServiceImpl = (IUserService) SpringTestHelper.get().getBeanByClass(UserServiceImpl.class);}@Afterpublic void tearDown() throws Exception {}@Testpublic void testAdd(){UserEntity entity = new UserEntity();entity.setUserId("000001");entity.setEmpCode("130566");entity.setEmpName("leonardo-zeng");entity.setRole("Java Development Engineer");entity.setTitle("PM");boolean isTrue =userServiceImpl.addUserEntity(entity);Assert.assertTrue(isTrue);}@Testpublic void testQueryById(){UserEntity entity = new UserEntity();entity.setUserId("000001");UserEntity userEntity =userServiceImpl.queryUserEntityByUserId(entity);System.out.println(userEntity);}}
串連redis庫,查詢出來的確值在庫中存在

redis 127.0.0.1:6379> hkeys "\"userEntity\""
1) "\"000001\""
redis 127.0.0.1:6379> hget "\"userEntity\"" "\"000001\""
"{\"@type\":\"com.deppon.cache.entity.UserEntity\",\"empCode\":\"130566\",\"empN
ame\":\"leonardo-zeng\",\"role\":\"Java Development Engineer\",\"title\":\"PM\",
\"userId\":\"000001\"}"
redis 127.0.0.1:6379>
整個demo就這樣了




相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.