详解SSH框架和Redis的整合
一个已有的struts+spring+hibernate项目,以前使用mysql数据库,现在想把redis也整合进去。
1. 相关jar文件
下载并导入以下3个jar文件:
commons-pool2-2.4.2.jar、jedis-2.3.1.jar、spring-data-redis-1.3.4.release.jar。
2. redis配置文件
在src文件夹下面新建一个redis.properties文件,设置连接redis的一些属性。
redis.host=127.0.0.1 redis.port=6379 redis.default.db=1 redis.timeout=100000 redis.maxactive=300 redis.maxidle=100 redis.maxwait=1000 redis.testonborrow=true
再新建一个redis.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:p="http://www.springframework.org/schema/p" xmlns:context="http://www.springframework.org/schema/context" xsi:schemalocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-4.0.xsd"> <context:property-placeholder location="classpath:redis.properties"/> <bean id="propertyconfigurerredis" class="org.springframework.beans.factory.config.propertyplaceholderconfigurer"> <property name="order" value="1" /> <property name="ignoreunresolvableplaceholders" value="true" /> <property name="systempropertiesmode" value="1" /> <property name="searchsystemenvironment" value="true" /> <property name="locations"> <list> <value>classpath:redis.properties</value> </list> </property> </bean> <bean id="jedispoolconfig" class="redis.clients.jedis.jedispoolconfig"> <property name="maxidle" value="${redis.maxidle}" /> <property name="testonborrow" value="${redis.testonborrow}" /> </bean> <bean id="jedisconnectionfactory" class="org.springframework.data.redis.connection.jedis.jedisconnectionfactory"> <property name="usepool" value="true"></property> <property name="hostname" value="${redis.host}" /> <property name="port" value="${redis.port}" /> <property name="timeout" value="${redis.timeout}" /> <property name="database" value="${redis.default.db}"></property> <constructor-arg index="0" ref="jedispoolconfig" /> </bean> <bean id="redistemplate" class="org.springframework.data.redis.core.stringredistemplate" p:connectionfactory-ref="jedisconnectionfactory" > </bean> <bean id="redisbase" abstract="true"> <property name="template" ref="redistemplate"/> </bean> <context:component-scan base-package="com.school.redisclient" /> </beans>
3. redis类
新建一个com.school.redisclient包,结构如下:
接口iredisservice:
public interface iredisservice<k, v> { public void set(k key, v value, long expiredtime); public v get(k key); public object gethash(k key, string name); public void del(k key); }
抽象类abstractredisservice,主要是对redistemplate进行操作:
public abstract class abstractredisservice<k, v> implements iredisservice<k, v> { @autowired private redistemplate<k, v> redistemplate; public redistemplate<k, v> getredistemplate() { return redistemplate; } public void setredistemplate(redistemplate<k, v> redistemplate) { this.redistemplate = redistemplate; } @override public void set(final k key, final v value, final long expiredtime) { boundvalueoperations<k, v> valueoper = redistemplate.boundvalueops(key); if (expiredtime <= 0) { valueoper.set(value); } else { valueoper.set(value, expiredtime, timeunit.milliseconds); } } @override public v get(final k key) { boundvalueoperations<k, v> valueoper = redistemplate.boundvalueops(key); return valueoper.get(); } @override public object gethash(k key, string name){ object res = redistemplate.boundhashops(key).get(name); return res; } @override public void del(k key) { if (redistemplate.haskey(key)) { redistemplate.delete(key); } } }
实现类redisservice:
@service("redisservice") public class redisservice extends abstractredisservice<string, string> { }
工具类redistool:
public class redistool { private static applicationcontext factory; private static redisservice redisservice; public static applicationcontext getfactory(){ if (factory == null){ factory = new classpathxmlapplicationcontext("classpath:redis.xml"); } return factory; } public static redisservice getredisservice(){ if (redisservice == null){ redisservice = (redisservice) getfactory().getbean("redisservice"); } return redisservice; } }
4. 查询功能的实现
新建一个action:rclasqueryaction,返回redis里面所有的课程数据。
@suppresswarnings("serial") public class rclasqueryaction extends actionsupport { redisservice rs = redistool.getredisservice(); list<clas> claslist = new arraylist<clas>(); clas c; public string execute(){ if (rs != null){ system.out.println("redisservice : " + rs); getallclas(); } servletactioncontext.getrequest().setattribute("claslist", claslist); return success; } private void getallclas(){ claslist = new arraylist<clas>(); int num = integer.parseint(rs.get("clas:count")); for (int i=0; i<num; i++){ string cid = "clas:" + (i+1); c = new clas(); int id = integer.parseint(string.valueof(rs.gethash(cid, "id"))); c.setid(id); system.out.println("id:" + id); string name = (string) rs.gethash(cid, "name"); c.setname(name); system.out.println("name:" + name); string comment = (string) rs.gethash(cid, "comment"); c.setcomment(comment); system.out.println("comment:" + comment); claslist.add(c); } } }
struts的设置和jsp文件就不详细讲了。
5. redis数据库
redis数据库里面的内容(使用的是redis desktop manager):
最后是运行结果:
当然,这只是实现了从redis查询数据,还没有实现将redis作为mysql的缓存。
5. 添加功能的实现
新建一个action:rclasaction,实现向redis添加课程数据,并同步到mysql。
package com.school.action; import java.util.arraylist; import java.util.hashmap; import java.util.list; import org.springframework.beans.factory.annotation.autowired; import com.opensymphony.xwork2.actionsupport; import com.school.entity.clas; import com.school.redisclient.redisservice; import com.school.redisclient.redistool; import com.school.service.classervice; @suppresswarnings("serial") public class rclasaction extends actionsupport { @autowired private classervice classervice; redisservice rs = redistool.getredisservice(); list<clas> claslist = new arraylist<clas>(); private clas clas; public clas getclas() { return clas; } public void setclas(clas clas) { this.clas = clas; } public string execute(){ saveclas(clas); return success; } @suppresswarnings({ "rawtypes", "unchecked" }) private void saveclas(clas c){ list<string> ids = rs.getlist("clas:id"); // clas:id int num = ids.size(); int id = integer.parseint(ids.get(num-1)) + 1; rs.rightpushlist("clas:id", string.valueof(id)); // clas:count int count = integer.parseint(rs.get("clas:count")); rs.set("clas:count", string.valueof(count+1), -1); // 增加 hashmap hashmap = new hashmap(); hashmap.put("id", string.valueof(id)); hashmap.put("name", clas.getname()); hashmap.put("comment", clas.getcomment()); rs.addhash("clas:" + id, hashmap); // 同步到mysql classervice.saveclas(clas); } }
clas:id是一个list类型的key-value,记录了所有的课程id,取出最后一个id,再+1,作为增加的课程的id,同时clas:count的值也要+1。使用addhash()方法向redis添加了一个hash类型的key-value(也就是一门课程):
@suppresswarnings({ "unchecked", "rawtypes" }) public synchronized void addhash(k key, hashmap map){ redistemplate.opsforhash().putall(key, map); }
同时将该门课程增加到mysql。
6. 删除功能的实现
新建一个action:rclasdeleteaction,实现删除redis的课程数据,并同步到mysql。
package com.school.action; import org.springframework.beans.factory.annotation.autowired; import com.opensymphony.xwork2.actionsupport; import com.school.redisclient.redisservice; import com.school.redisclient.redistool; import com.school.service.classervice; @suppresswarnings("serial") public class rclasdeleteaction extends actionsupport { @autowired private classervice classervice; redisservice rs = redistool.getredisservice() private int id; public int getid(){ return id; } public void setid(int id){ this.id=id; } public string execute(){ deleteclas(id); // 同步到mysql classervice.deleteclas(id); return success; } private void deleteclas(int id){ // 删除 rs.del("clas:" + id); // clas:count int count = integer.parseint(rs.get("clas:count")); rs.set("clas:count", string.valueof(count-1), -1); // clas:id rs.dellistitem("clas:id", string.valueof(id)); } }
直接删除clas:id,再将clas:count的值-1,这两步比较简单,复杂的是从clas:id中删除该课程的id,使用了dellistitem()方法来实现:
@override public synchronized void dellistitem(k key, v value){ redistemplate.opsforlist().remove(key, 1, value); }
redistemplate.opsforlist().remove()方法类似于lrem命令。最后在mysql中也删除相同的课程。
7. 修改功能的实现
新建一个action:rclasupdateaction,实现删除redis的课程数据,并同步到mysql。
package com.school.action; import java.util.hashmap; import org.springframework.beans.factory.annotation.autowired; import com.opensymphony.xwork2.actionsupport; import com.school.entity.clas; import com.school.redisclient.redisservice; import com.school.redisclient.redistool; import com.school.service.classervice; @suppresswarnings("serial") public class rclasupdateaction extends actionsupport{ @autowired private classervice classervice; redisservice rs = redistool.getredisservice(); private clas clas; public clas getclas() { return clas; } public void setclas(clas clas) { this.clas = clas; } @suppresswarnings({ "unchecked", "rawtypes" }) public string execute(){ hashmap hashmap = new hashmap(); hashmap.put("id", string.valueof(clas.getid())); hashmap.put("name", clas.getname()); hashmap.put("comment", clas.getcomment()); rs.puthash("clas:" + clas.getid(), hashmap); // 同步到mysql classervice.updateclas(clas); return success; } }
使用了puthash()方法来更新:
@suppresswarnings({ "rawtypes", "unchecked" }) @override public synchronized void puthash(k key, hashmap map){ redistemplate.boundhashops(key).putall(map); }
同时在mysql做相同的更新操作。
以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持。