Similar to the solution in the previous post, I creates a NullPrincipalAccessDeniedHandlerImpl, which extends Acegi's AccessDeniedHandlerImpl but wrap the HttpServletRequest with the NullPrincipalHttpServletRequestWrapper.
Following is the source code of NullPrincipalAccessDeniedHandlerImpl:
package au.net.ozgwei.util.spring.security;
import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServletRequest;
import org.acegisecurity.AccessDeniedException;
import org.acegisecurity.ui.AccessDeniedHandlerImpl;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import au.net.ozgwei.util.httpservlet.NullPrincipalHttpServletRequestWrapper;
/**
* An Acegi AccessDeniedHandler implementation designed specific to get around
* the bug in Sun Application Server 8.x where a custom security framework's
* implementation of Principal is casted to Sun Application Server's own
* implementation.
*
* @author Alex
* @version 1.0
*/
public class NullPrincipalAccessDeniedHandlerImpl extends
AccessDeniedHandlerImpl {
@SuppressWarnings("unused")
private static final Log log =
LogFactory.getTrace(
NullPrincipalAccessDeniedHandlerImpl.class);
/**
* Default no-arg constructor.
*/
public NullPrincipalAccessDeniedHandlerImpl() {
super();
}
@Override
public void handle(ServletRequest aRequest, ServletResponse aResponse,
AccessDeniedException aAccessDeniedException) throws IOException,
ServletException {
super.handle(new NullPrincipalHttpServletRequestWrapper(
(HttpServletRequest)aRequest), aResponse, aAccessDeniedException);
}
}
Of course, the Spring application context must be changed to replace the original AccessDeniedHandler implementation with this in the definition of the exceptionTranslationFilter bean:
<bean id="exceptionTranslationFilter"
class="org.acegisecurity.ui.ExceptionTranslationFilter">
<property name="authenticationEntryPoint">
<ref local="authenticationProcessingFilterEntryPoint"/>
</property>
<property name="accessDeniedHandler">
<bean class="au.com.cardlink.common.util.spring.security.NullPrincipalAccessDeniedHandlerImpl">
<property name="errorPage" value="/faces/ForbiddenAccess.jsp"/>
</bean>
</property>
</bean>
Now it works even if user's access to a protected URL is denied by Acegi.