memcache实现公共计数器网站

时间:2023-03-09 01:53:24
memcache实现公共计数器网站

在反问题的过程中遇到的最近项目。网上查了很多资料并没有完全实现。

因此,要找到适合自己的xmemcache client和memcache关联API和说明,我们发现了一个比较完美的实现。

键类:net.rubyeye.xmemcached.Counter

相关API

memcache实现公共计数器网站

实现思路:

获取:

获取的时候默认从memcache中获取,初次获取没获得的话载入数据库获取值,并初始化计数器的值。

更新

先从memcache中获取计数器的值,没有获取到得的话载入数据库获取值,并初始化计数器的值。

然后将计数器加1,获取操作后的返回值,假设是100的整数倍就更新到数据库

下面是关键实现类的代码

package com.liu.memcache.tools;

import java.io.IOException;

import net.rubyeye.xmemcached.Counter;
import net.rubyeye.xmemcached.MemcachedClient;
import net.rubyeye.xmemcached.MemcachedClientBuilder;
import net.rubyeye.xmemcached.XMemcachedClientBuilder;
import net.rubyeye.xmemcached.impl.KetamaMemcachedSessionLocator;
import net.rubyeye.xmemcached.utils.AddrUtil; public class MemCachedTools {
private static final MemCachedTools instance = new MemCachedTools(); /**
* instance
*
* @return
*/
public static MemCachedTools getInstance() {
return instance;
} private static String memcached_address = ConfigUtil.getInstance()
.getString("memcached_address");
private static String memcached_head=ConfigUtil.getInstance()
.getString("memcached_head"); /**
* 值添加1
* @param key
* @return
*/
public long increaseValue(String key){
long addResult=0;
String memKey=memcached_head+":"+Md5Hex.getDigestMD5(key);
try {
MemcachedClientBuilder builder = new XMemcachedClientBuilder(
AddrUtil.getAddresses(memcached_address));
builder.setSessionLocator(new KetamaMemcachedSessionLocator());
MemcachedClient memcachedClient = builder.build();
Counter counter=memcachedClient.getCounter(memKey);
addResult=counter.incrementAndGet(); try {
// close memcached client
memcachedClient.shutdown();
} catch (IOException e) {
System.err.println("Shutdown MemcachedClient fail");
e.printStackTrace();
} } catch (Exception ex) {
ex.printStackTrace();
// return ERROR;
}
System.out.println("================"+addResult);
return addResult;
} /**
* 初始化计数器
* @param key
* @param defaultValue
*/
public void initCounter(String key,long defaultValue){
String memKey=memcached_head+":"+Md5Hex.getDigestMD5(key);
try {
MemcachedClientBuilder builder = new XMemcachedClientBuilder(
AddrUtil.getAddresses(memcached_address));
builder.setSessionLocator(new KetamaMemcachedSessionLocator());
MemcachedClient memcachedClient = builder.build();
Counter counter=memcachedClient.getCounter(memKey,defaultValue);
counter.set(defaultValue);
try {
// close memcached client
memcachedClient.shutdown();
} catch (IOException e) {
System.err.println("Shutdown MemcachedClient fail");
e.printStackTrace();
} } catch (Exception ex) {
ex.printStackTrace();
// return ERROR;
}
} /**
* 获取计数器的值
* @param key
* @return
*/
public long getCounterValue(String key){
String memKey=memcached_head+":"+Md5Hex.getDigestMD5(key);
long ret=0;
try {
MemcachedClientBuilder builder = new XMemcachedClientBuilder(
AddrUtil.getAddresses(memcached_address));
builder.setSessionLocator(new KetamaMemcachedSessionLocator());
MemcachedClient memcachedClient = builder.build();
Counter counter=memcachedClient.getCounter(memKey);
ret= counter.get();
try {
// close memcached client
memcachedClient.shutdown();
} catch (IOException e) {
System.err.println("Shutdown MemcachedClient fail");
e.printStackTrace();
} } catch (Exception ex) {
ex.printStackTrace();
// return ERROR;
}
return ret;
} }

操作计数器实现类

package com.liu.counter;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory; import com.liu.memcache.tools.MemCachedTools; /**
* @author chao.liu
* @date 2015-03-06
*
*/
public class CounterService {
protected Log log = LogFactory.getLog(getClass()); public long getStatisticsData() {
String memKey = "count";
Long count = null;
try {
count = (Long) MemCachedTools.getInstance().getCounterValue(memKey);
} catch (Exception e) {
}
if (count == 0) {
try {
// TODO:从数据库载入,此处省略
count = 120L;
} catch (Exception e) {
}
MemCachedTools.getInstance().initCounter(memKey, count);
} else {
// TODO:输出到前台的处理
log.info("StatisticsService.getStatisticsData get data to memcached ...............");
}
return count;
} /**
* 更新统计数据
*
* @param channelID
* @param moduleID
* @return
*/
public String updateStatisticsData() {
String memKey = "count";
String res = "1";
Long count = null;
try {
count = (Long) MemCachedTools.getInstance().getCounterValue(memKey);
} catch (Exception e) {
}
if (count == 0) {// 空的时候从数据库载入
// TODO:从数据库载入,此处省略
count = 120L;
MemCachedTools.getInstance().initCounter(memKey, count);
}
long addRes = MemCachedTools.getInstance().increaseValue(memKey);
try {
if (addRes != 0) {
if (addRes % 100 == 0) {
// 每100条更新到数据库一次
// update to DB operation
}
}
} catch (Exception e) {
res = "0";
}
return res;
} public static void main(String[] args) {
CounterService ss=new CounterService();
System.out.println("当前计数条数是:"+ss.getStatisticsData());
ss.updateStatisticsData();
System.out.println("加1后计数条数是:"+ss.getStatisticsData());
}
}

执行效果:

当前计数条数是:123

================124

加1后计数条数是:124

代码下载:

http://download.****.net/detail/shanhuhau/8508929

版权声明:本文博主原创文章。博客,未经同意不得转载。