在较高的层次上,我有一个MemcachedPoolService类,该类具有两个方法:getClientInstance()和returnClientInstance(client)。如预期的那样,getClientInstance()将MemcachedClient的一个实例(spymemcachced)返回给调用者,而returnClientInstance(client)将MemcachedClient返回给池。 MemcachedPoolService必须可供所有都需要访问Memcached的其他@Stateless服务(注入)使用。
目前,我已将MemcachedPoolService标记为@Singleton,但是当多个客户端尝试访问该应用程序时出现以下错误:
[0m[31m16:54:22,968 ERROR [org.jboss.as.ejb3.invocation] (http-/0.0.0.0:8080-10)
JBAS014134: EJB Invocation failed on component MemcachedPoolService for method public
net.spy.memcached.MemcachedClient com.apexlab.cache.MemcachedPoolService.getClientInstance():
javax.ejb.EJBTransactionRolledbackException: JBAS014373: EJB 3.1 PFD2 4.8.5.5.1 concurrent
access timeout on org.jboss.invocation.InterceptorContext$Invocation@24bf375e - could not
obtain lock within 5000MILLISECONDS
为生产环境设置MemcachedPoolService(通常是Web应用程序)以避免收到并发超时异常的最佳方法是什么?
最佳答案
首先,MemcachedPoolService是无状态服务,因此,如果您不进行任何需要一致性的数据库更新(这就是为什么它仍然是@Singleton,否则您将使用@Stateless),然后只需将类标记为
@Singleton
@Lock(LockType.READ)
public class MemcachedPoolService{}
要么
@Singleton
public class MemcachedPoolService{
@Lock(LockType.READ)
public void myPossibleMultiAccessMethod(){}
}
如果那不是一个选择,那么:
@Singleton
public class MemcachedPoolService{
@AccessTimeout(Integer.MORE_THAN_5000_MILLIS)
public void myPossibleMultiAccessMethod(){}
}