struts-menu的扩展问题

项目中用到了struts-menu的VelocityMenuDisplayer.因为在部署到服务器上后会报两个velocity的异常(1.Formatter class not found;2 cannot find menuMacros.vm)虽然不致命,但总归看起来不舒服.于是想把它去掉.看了一下source code发现VMD的initialize方法里初始化了velocity, 载入velocity的两个配置文件(default,custom),于是很自然的想用一个自己写的velocity配置.ok,继承 VMD 然后改两个名字.

不成功.

仔细一看才发现,VMD的initialize方法是静态的, 会被MenuRepository这么调用:

public void addMenuDisplayerMapping(MenuDisplayerMapping displayerMapping) {
displayers.put(displayerMapping.getName(), displayerMapping);
if (displayerMapping.getType().equals(“net.sf.navigator.displayer.VelocityMenuDisplayer”)) {
if (servletContext == null) {
log.error(“ServletContext not set – can’t initialize Velocity”);
} else {
VelocityMenuDisplayer.initialize(servletContext);
}
}
}

真够狠的,怎么扩展啊.总不至于把MenuRepository也改了吧.

acegi整合struts-menu时filter-mapping的问题

今天在整合acegi和struts-menu的时候老是有问题,跟进源代码发现struts-menu的RolesPermissionsAdapter 中:

public boolean isAllowed(MenuComponent menu) {
if (menu.getRoles() == null) {
return true; // no roles define, allow everyone
} else {
// Get the list of roles this menu allows
String[] allowedRoles = delimiters.split(menu.getRoles());
for (int i=0; i < allowedRoles.length; i++) {
if (request.isUserInRole(allowedRoles[i])) {
return true;
}
}
}
return false;
}

request.isUserInRole(allowedRoles[i])返回是false. – 因为这个request是sitemesh的pageinforequestWrapper!!!
(之前找了各种可能都没有发现异常,试了无数种 可能的原因)

为什么会这样,之前做的也是完全一样啊?仔细比较了以前写的和现在的,发现 filter-mapping的顺序不一样:

之前写的是acegi的filter-mapping在第一个,试着把现在的filtermapping 放到第一个.成功!

原来filter-mapping的顺序也是有讲究的.如果先mapping sitemesh的filter,request就会被sitemesh的pageinforequestwrapper(?) 包裹,然后就不能被acegi的filter包装成SecurityContextHolderAwareRequestWrapper.

这样在调用isUserInRole时候就出问题了,因为使用的不是acegi的实现.

记录下来.