nested Interceptor-calls
ret May 17, 2010 5:11 AMHello there,
i noticed, that nested methodcalls not raise an interception if the methods ar called from an @Interceptor-annotated method (tested for same Interceptor).
an example:
@Stateless
@Interceptors(LogInterceptor.class)
public class ParameterServiceImpl extends BaseEntityServiceImpl<Parameter> implements ParameterService, ParameterServiceLocal {
...
@Interceptors(ParameterReloader.class) // first i tried without this...
public void create(String name, String value, Company company, boolean visible, boolean readonly) {
Parameter p = new Parameter(name, value, company, visible, readonly);
this.create(p);
}
@Override
@Interceptors(ParameterReloader.class)
public void create(Parameter entity) {
super.create(entity);
}
...
}
the first method calls the create(Parameter)-method, but the 2nd methodcall does not raise Interception.
At first i tried it without annotating the first method and wondering that nothing happens (expected Action if the 2nd method get called).
So this is a bug or a feature to prevent infinite Interceptor-loops?
App-Logs:
2010-05-14 17:10:04,122 DEBUG [de.xxx.business.service.core.CompanyServiceImpl] create(Integer,String) in 10ms 2010-05-14 17:10:04,122 DEBUG [de.xxx.business.service.core.interceptor.ParameterReloader] ParameterReloader: executed method = create 2010-05-14 17:10:04,153 DEBUG [de.xxx.business.service.core.ParameterServiceImpl] findByName(String,Company) in 3ms 2010-05-14 17:10:04,153 DEBUG [de.xxx.business.service.core.ParameterHolderImpl] reload(String,Company) in 5ms
my Interceptor:
@Interceptor
public class ParameterReloader {
private Log LOG = LogFactory.getLog(this.getClass());
@Resource
private EJBContext ejbContext;
@AroundInvoke
public Object intercept(InvocationContext context) throws Exception{
LOG.debug("ParameterReloader: executed method = " + context.getMethod().getName());
try {
return context.proceed();
} finally {
try {
Object[] par = context.getParameters();
String mname = context.getMethod().getName();
// wenn Methodenname delete oder create oder update
if ("delete".equals(mname) || "create".equals(mname) || "update".equals(mname)) {
ParameterHolderLocal ph = (ParameterHolderLocal) ejbContext.lookup(ParameterHolderLocal.JNDI_BINDING);
// wenn nur ein Argument übergeben (Parameter)
if (par.length == 1 && par[0] instanceof Parameter) {
Parameter p = (Parameter) par[0];
// wenn in delete-Methode
if ("delete".equals(mname)) {
ph.unload(p);
// sonst update oder create
} else {
ph.reload(p);
}
// public void create(String name, String value, Company company, boolean visible, boolean readonly)
// public void create(String name, String value, Company company)
} else if ((par.length == 5 || par.length == 3 ) && par[0] instanceof String && par[2] instanceof Company) {
ph.reload((String) par[0], (Company) par[2]);
}
}
} catch (final Exception e) {
// Pokemon Exception Handling - gotta catch 'em all!
if (LOG.isWarnEnabled()) {
LOG.warn("cannot refresh ParameterHolder: ", e);
}
}
}
}
}