memcached是高性能的分佈式內存緩存服務器。許多Web應用都將數據保存到RDBMS中,應用服務器從中讀取數據並在瀏覽器中顯示。html
但隨着數據量的增大、訪問的集中,就會出現RDBMS的負擔加劇、數據庫響應惡化、 網站顯示延遲等重大影響。memcached特別適合java
用來解決上述問題,它能夠緩存數據庫查詢結果,減小數據庫訪問次數,以提升動態Web應用的速度、 提升可擴展性。本例將在前一篇中web
實現的Demo程序基礎上集成memcached客戶端。spring
一、單個服務端安裝部署sql
官網http://memcached.org/downloads上沒有提供windows版本,只有源碼,能夠本身編譯。數據庫
另外,網上找到網友分享的下載連接:apache
http://code.jellycan.com/memcached/ 這個連接彷佛有點問題,若是有人下載成功望告知。windows
http://www.jb51.net/softs/44843.html 這個能夠用。瀏覽器
1.一、解壓到指定目錄,如:C:\Memcached\memcached-win32-1.4.4-14。緩存
1.二、用cmd打開命令窗口,轉到解壓的目錄,輸入 「memcached.exe -d install」。
1.3 打開控制面板,打開服務,能夠看到memcached已經在上面可,若是沒有啓動,則手動啓動一下。
或者執行:'D:\memcached\memcached.exe -d start'啓動,這樣memcache就會做爲windows系統服務在每 次開機時啓動memcache服務。
1.4 使用telnet localhost 11211命令驗證緩存服務器是否可用。
若是是Windows7系統下,須要先經過「控制面 板」 一〉「程序」 一〉「打開或關閉windows功能」,安裝「telnet客戶端」。
1.5 開始什麼都不顯示,回車後輸入命令 stats 查看統計信息,以下圖,說明服務器運做正常。
以上安裝過程參考http://www.jb51.net/article/30334.htm。
二、在Spring框架中集成客戶端
2.1 修改gradle文件,增長依賴包,代碼以下:
apply plugin: 'idea' apply plugin: 'java' repositories { mavenCentral() maven { url "http://repo.spring.io/release" } } dependencies { compile( "org.springframework:spring-context:4.0.5.RELEASE", "org.springframework:spring-web:4.0.5.RELEASE", "org.springframework:spring-webmvc:4.0.5.RELEASE", "org.springframework:spring-context-support:4.0.5.RELEASE", "org.apache.velocity:velocity:1.7", "org.apache.velocity:velocity-tools:2.0", "org.anarres.gradle:gradle-velocity-plugin:1.0.0", "org.springframework:spring-jdbc:4.0.5.RELEASE", "commons-dbcp:commons-dbcp:1.4", "org.springframework:spring-test:4.0.5.RELEASE", "org.testng:testng:6.8.8", "org.mybatis:mybatis:3.2.7", "org.springframework:spring-tx:4.0.5.RELEASE", "org.springframework:spring-orm:4.0.5.RELEASE", "org.mybatis:mybatis-spring:1.2.2", "com.googlecode.xmemcached:xmemcached:2.0.0", "com.google.guava:guava:17.0", "org.codehaus.jackson:jackson-mapper-asl:1.9.13", "com.google.code.simple-spring-memcached:simple-spring-memcached:3.5.0", "com.google.code.simple-spring-memcached:xmemcached-provider:3.5.0" ) testCompile("org.springframework:spring-test:4.0.5.RELEASE") runtime("jstl:jstl:1.2") } task copyJars(type: Copy) { from configurations.runtime into 'lib' // 目標位置 }
運行命令:gradle copyJars下載。
2.2 修改Spring配置文件,加入如下配置:
<import resource="simplesm-context.xml" /> <import resource="xmemcached.xml"/>
2.3 在resources下添加文件xmemcached.xml,代碼以下:
<?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:aop="http://www.springframework.org/schema/aop" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-4.0.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-4.0.xsd"> <aop:aspectj-autoproxy proxy-target-class="true"/> <bean name="defaultMemcachedClient" class="com.google.code.ssm.CacheFactory"> <property name="cacheClientFactory"> <bean class="com.google.code.ssm.providers.xmemcached.MemcacheClientFactoryImpl"/> </property> <property name="addressProvider"> <bean class="com.google.code.ssm.config.DefaultAddressProvider"> <property name="address" value="127.0.0.1:11211"/> </bean> </property> <property name="configuration"> <bean class="com.google.code.ssm.providers.CacheConfiguration"> <property name="consistentHashing" value="true"/> </bean> </property> </bean> </beans>
2.4 修改domain文件夾下的User實體,修改以下:
@CacheKeyMethod public String getUserName() { return userName; }
經過@CacheKeyMethod標籤爲實體指定Key值
2.5 修改dao文件夾下的getUserByUserName函數,以下:
@ReadThroughSingleCache(namespace = NAMESPACE, expiration = 3600) @Override public User getUserByUserName(@ParameterValueKeyProvider String userName) { try { Thread.sleep(4000); } catch (InterruptedException e) { e.printStackTrace(); } return (User)sqlSession.selectOne("domain.User.getUserByUserName", userName); }
添加@ReadThroughSingleCache切入點表示:組件首先從緩存中讀取數據,取到數據則跳過查詢方法,直接返回。
取不到數據再執行查詢方法,並將查詢結果放入緩存,以便下一次獲取。
namespace參數本身指定,與其餘實體相區分便可;expiration表示緩存失效時間,單位秒。
@ParameterValueKeyProvider指定的參數,若是該參數對象中包含CacheKeyMethod註解的方法,則調用其方法,不然調用toString方法。
爲了查看測試效果,進入查詢方法後執行Thread.sleep(4000)等待4秒。
2.6 單元測試
修改getUserByUserName函數,打印出執行時間。
@Test public void getUserByUserName() { SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");//設置日期格式 System.out.println(df.format(new Date())); //×××××××××××××××1 User user = userService.getUserByUserName("admin"); System.out.println(df.format(new Date()));//×××××××××××××××2 // assertEquals(user.getUserName(), "admin"); user = userService.getUserByUserName("admin"); System.out.println(df.format(new Date()));//×××××××××××××××3 assertEquals(user.getUserName(), "admin"); }
測試結果:1,2處打印的時間間隔大於等於4秒,2,3處打印的時間間隔小於4秒,符合預期。
源碼下載:http://files.cnblogs.com/wenjingu/VelocityDemo5.0.zip lib中的jar包上傳時已刪除,請運行命令:gradle copyJars下載。