欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

利用spring的攔截器自定義緩存的實現(xiàn)實例代碼

 更新時間:2018年02月02日 15:10:16   作者:txxs  
這篇文章主要介紹了利用spring的攔截器自定義緩存的實現(xiàn)實例代碼,分享了相關(guān)代碼示例,小編覺得還是挺不錯的,具有一定借鑒價值,需要的朋友可以參考下

本文研究的主要是利用spring的攔截器自定義緩存的實現(xiàn),具體實現(xiàn)代碼如下所示。

Memcached 是一個高性能的分布式內(nèi)存對象緩存系統(tǒng),用于動態(tài)Web應(yīng)用以減輕數(shù)據(jù)庫負(fù)載。它通過在內(nèi)存中緩存數(shù)據(jù)和對象來減少讀取數(shù)據(jù)庫的次數(shù),從而提高動態(tài)、數(shù)據(jù)庫驅(qū)動網(wǎng)站的速度。本文利用Memcached 的實例和spring的攔截器實現(xiàn)緩存自定義的實現(xiàn)。利用攔截器讀取自定義的緩存標(biāo)簽,key值的生成策略。

自定義的Cacheable

package com.jeex.sci;
@Target(ElementType.METHOD)  
@Retention(RetentionPolicy.RUNTIME) 
@Inherited 
@Documented 
public @interface Cacheable {
	String namespace();
	String key() default "";
	int[] keyArgs() default {
	}
	;
	String[] keyProperties() default {
	}
	;
	String keyGenerator() default "";
	int expires() default 1800;
}

自定義的CacheEvict

package com.jeex.sci;
@Target(ElementType.METHOD)  
@Retention(RetentionPolicy.RUNTIME) 
@Inherited 
@Documented 
public @interface CacheEvict {
	String namespace();
	String key() default "";
	int[] keyArgs() default {
	}
	;
	String[] keyProperties() default {
	}
	;
	String keyGenerator() default "";
}

spring如果需要前后通知的話,一般會實現(xiàn)MethodInterceptor public Object invoke(MethodInvocation invocation) throws Throwable

public Object invoke(MethodInvocation invoction) throws Throwable {
	Method method = invoction.getMethod();
	Cacheable c = method.getAnnotation(Cacheable.class);
	if (c != null) {
		return handleCacheable(invoction, method, c);
	}
	CacheEvict ce = method.getAnnotation(CacheEvict.class);
	if (ce != null) {
		return handleCacheEvict(invoction, ce);
	}
	return invoction.proceed();
}

處理cacheable標(biāo)簽

private Object handleCacheable(MethodInvocation invoction, Method method, 
    Cacheable c) throws Throwable {
	String key = getKey(invoction, KeyInfo.fromCacheable(c));
	if (key.equals("")) {
		if (log.isDebugEnabled()){
			log.warn("Empty cache key, the method is " + method);
		}
		return invoction.proceed();
	}
	long nsTag = (long) memcachedGet(c.namespace());
	if (nsTag == null) {
		nsTag = long.valueOf(System.currentTimeMillis());
		memcachedSet(c.namespace(), 24*3600, long.valueOf(nsTag));
	}
	key = makeMemcachedKey(c.namespace(), nsTag, key);
	Object o = null;
	o = memcachedGet(key);
	if (o != null) {
		if (log.isDebugEnabled()) {
			log.debug("CACHE HIT: Cache Key = " + key);
		}
	} else {
		if (log.isDebugEnabled()) {
			log.debug("CACHE MISS: Cache Key = " + key);
		}
		o = invoction.proceed();
		memcachedSet(key, c.expires(), o);
	}
	return o;
}

處理cacheEvit標(biāo)簽

private Object handleCacheEvict(MethodInvocation invoction,  
    CacheEvict ce) throws Throwable { 
  String key = getKey(invoction, KeyInfo.fromCacheEvict(ce));    
   
  if (key.equals("")) {  
    if (log.isDebugEnabled()) { 
      log.debug("Evicting " + ce.namespace()); 
    } 
    memcachedDelete(ce.namespace()); 
  } else { 
    Long nsTag = (Long) memcachedGet(ce.namespace()); 
    if (nsTag != null) { 
      key = makeMemcachedKey(ce.namespace(), nsTag, key); 
      if (log.isDebugEnabled()) { 
        log.debug("Evicting " + key); 
      } 
      memcachedDelete(key);         
    } 
  } 
  return invoction.proceed(); 
} 

根據(jù)參數(shù)生成key

//使用攔截到方法的參數(shù)生成參數(shù) 
private String getKeyWithArgs(Object[] args, int[] argIndex) { 
  StringBuilder key = new StringBuilder(); 
  boolean first = true; 
  for (int index: argIndex) { 
    if (index < 0 || index >= args.length) { 
      throw new IllegalArgumentException("Index out of bound"); 
    } 
    if (!first) { 
      key.append(':'); 
    } else { 
      first = false; 
    } 
    key = key.append(args[index]); 
  } 
  return key.toString(); 
} 

根據(jù)屬性生成key

private String getKeyWithProperties(Object o, String props[])  
    throws Exception { 
  StringBuilder key = new StringBuilder(); 
  boolean first = true; 
  for (String prop: props) { 
    //把bean的屬性轉(zhuǎn)為獲取方法的名字 
    String methodName = "get"  
        + prop.substring(0, 1).toUpperCase()  
        + prop.substring(1); 
    Method m = o.getClass().getMethod(methodName); 
    Object r = m.invoke(o, (Object[]) null); 
    if (!first) { 
      key.append(':'); 
    } else { 
      first = false; 
    } 
    key = key.append(r); 
  } 
  return key.toString(); 
} 

利用自定義的生成器生成key

//使用生成器生成key 
private String getKeyWithGenerator(MethodInvocation invoction, String keyGenerator)  
    throws Exception { 
  Class<?> ckg = Class.forName(keyGenerator); 
  CacheKeyGenerator ikg = (CacheKeyGenerator)ckg.newInstance(); 
  return ikg.generate(invoction.getArguments()); 
} 

保存key信息的幫助類

private static class KeyInfo {
	String key;
	int[] keyArgs;
	String keyProperties[];
	String keyGenerator;
	static KeyInfo fromCacheable(Cacheable c) {
		KeyInfo ki = new KeyInfo();
		ki.key = c.key();
		ki.keyArgs = c.keyArgs();
		ki.keyGenerator = c.keyGenerator();
		ki.keyProperties = c.keyProperties();
		return ki;
	}
	static KeyInfo fromCacheEvict(CacheEvict ce) {
		KeyInfo ki = new KeyInfo();
		ki.key = ce.key();
		ki.keyArgs = ce.keyArgs();
		ki.keyGenerator = ce.keyGenerator();
		ki.keyProperties = ce.keyProperties();
		return ki;
	}
	String key() {
		return key;
	}
	int[] keyArgs() {
		return keyArgs;
	}
	String[] keyProperties() {
		return keyProperties;
	}
	String keyGenerator() {
		return keyGenerator;
	}
}

參數(shù)的設(shè)置

//使用參數(shù)設(shè)置key 
@Cacheable(namespace="BlackList", keyArgs={0, 1}) 
public int anotherMethond(int a, int b) { 
  return 100; 
} 

測試類:

package com.jeex.sci.test;
import net.spy.memcached.MemcachedClient;
import org.junit.Test;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.FileSystemXmlApplicationContext;
public class TestMain {
	public static void main(String args[]) throws InterruptedException{
		ApplicationContext ctx = new FileSystemXmlApplicationContext("/src/test/resources/beans.xml");
		MemcachedClient mc = (MemcachedClient) ctx.getBean("memcachedClient");
		BlackListDaoImpl dao = (BlackListDaoImpl)ctx.getBean("blackListDaoImpl");
		while (true) {
			System.out.println("################################GETTING START######################");
			mc.flush();
			BlackListQuery query = new BlackListQuery(1, "222.231.23.13");
			dao.searchBlackListCount(query);
			dao.searchBlackListCount2(query);
			BlackListQuery query2 = new BlackListQuery(1, "123.231.23.14");
			dao.anotherMethond(333, 444);
			dao.searchBlackListCount2(query2);
			dao.searchBlackListCount3(query2);
			dao.evict(query);
			dao.searchBlackListCount2(query);
			dao.evictAll();
			dao.searchBlackListCount3(query2);
			Thread.sleep(300);
		}
	}
}

總結(jié)

以上就是本文關(guān)于利用spring的攔截器自定義緩存的實現(xiàn)實例代碼的全部內(nèi)容,希望對大家有所幫助。感興趣的朋友可以繼續(xù)參閱本站其他相關(guān)專題,如有不足之處,歡迎留言指出。感謝朋友們對本站的支持!

相關(guān)文章

  • 如何編寫javascript的gulp插件

    如何編寫javascript的gulp插件

    本文主要介紹了使用PMD進(jìn)行代碼審查的方法,具有很好的參考價值,下面跟著小編一起來看下吧
    2017-02-02
  • Java基于Lock的生產(chǎn)者消費者模型示例

    Java基于Lock的生產(chǎn)者消費者模型示例

    這篇文章主要介紹了Java基于Lock的生產(chǎn)者消費者模型,結(jié)合實例形式分析了java基于鎖機制的生產(chǎn)者消費者模型相關(guān)實現(xiàn)與使用技巧,需要的朋友可以參考下
    2018-08-08
  • MyBatis配置的應(yīng)用與對比jdbc的優(yōu)勢

    MyBatis配置的應(yīng)用與對比jdbc的優(yōu)勢

    這篇文章主要介紹了MyBatis配置的使用與相對于jdbc的優(yōu)勢,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2022-07-07
  • Java動態(tài)代理模式的深入揭秘

    Java動態(tài)代理模式的深入揭秘

    這篇文章主要給大家介紹了關(guān)于Java動態(tài)代理模式的相關(guān)資料,文中通過示例代碼介紹的非常詳細(xì),對大家學(xué)習(xí)或者使用Java具有一定的參考學(xué)習(xí)價值,需要的朋友們下面來一起學(xué)習(xí)學(xué)習(xí)吧
    2019-08-08
  • Spring?Boot?實現(xiàn)?WebSocket?的代碼示例

    Spring?Boot?實現(xiàn)?WebSocket?的代碼示例

    WebSocket?協(xié)議是獨立的基于?TCP?協(xié)議。它與?HTTP?的唯一關(guān)系是,它的握手會被?HTTP?服務(wù)器解釋為?Upgrade?請求,接下來通過本文給大家介紹Spring?Boot?實現(xiàn)?WebSocket?示例詳解,需要的朋友可以參考下
    2022-04-04
  • SpringCloud如何實現(xiàn)Zuul集群(負(fù)載均衡)

    SpringCloud如何實現(xiàn)Zuul集群(負(fù)載均衡)

    這篇文章主要介紹了SpringCloud如何實現(xiàn)Zuul集群(負(fù)載均衡)的操作,具有很好的參考價值,希望對大家有所幫助。如有錯誤或未考慮完全的地方,望不吝賜教
    2021-07-07
  • springMVC+jersey實現(xiàn)跨服務(wù)器文件上傳

    springMVC+jersey實現(xiàn)跨服務(wù)器文件上傳

    這篇文章主要介紹了springMVC+jersey實現(xiàn)跨服務(wù)器文件上傳,具有一定的參考價值,感興趣的小伙伴們可以參考一下
    2019-08-08
  • MVC AOP面向切面編程簡單介紹及實例

    MVC AOP面向切面編程簡單介紹及實例

    這篇文章主要介紹了MVC AOP面向切面編程簡單介紹及實例的相關(guān)資料,需要的朋友可以參考下
    2016-12-12
  • springboot多個service互相調(diào)用的事務(wù)處理方式

    springboot多個service互相調(diào)用的事務(wù)處理方式

    這篇文章主要介紹了springboot多個service互相調(diào)用的事務(wù)處理方式,具有很好的參考價值,希望對大家有所幫助。如有錯誤或未考慮完全的地方,望不吝賜教
    2022-02-02
  • SpringBoot讀取yml文件中配置數(shù)組的2種方法

    SpringBoot讀取yml文件中配置數(shù)組的2種方法

    這篇文章主要介紹了SpringBoot讀取yml文件中配置數(shù)組的2種方法,具有很好的參考價值,希望對大家有所幫助。如有錯誤或未考慮完全的地方,望不吝賜教
    2021-12-12

最新評論