我有以下代码:
@Name("myService")
@Scope(ScopeType.APPLICATION)
@Stateless
public class MyService {
private Service service;
private Service getService() {
if (service == null) {
service = Service.create(url, new QName("URL",
"Envelope"));
}
return service;
}
public synchronized Port getPort() {
return getService().getPort();
}
}
从不同的线程调用getPort方法。 “Service.create”花费了大量时间,我发现实际上它被多次调用。因此,看起来创建了多个MyService类实例,这就是 synchronized 无效的原因。
我已将注释更改为:
@AutoCreate
@Startup
@Name("myService")
@Scope(ScopeType.APPLICATION)
现在它似乎工作正常:只创建了一个实例,并且同步了对getPort()方法的访问。
有人可以解释为什么第一个案例没有像预期的那样出现吗?
答案 0 :(得分:4)
绑定到应用程序范围的@Stateless是矛盾的
您要求Java EE提供一个没有状态的组件,以及所有用户共享的应用程序范围
当您删除@Stateless注释时,seam处理组件的实例并将其放在Application Scope中,它也在启动时创建它,因此具有单例