SAMCallbackHandler
是造成您麻烦的原因。
首先it.jaspic.sec.TokenConfigProvider
忽略运行时传递给它的处理程序:
public ServerAuthConfig getServerAuthConfig(String layer, String appContext, CallbackHandler handler) throws AuthException {
return serverAuthConfig;
}
然后it.jaspic.sec.TokenServerConfig
使用它自己的处理程序,它基本上什么都不做:
public TokenServerConfig() throws AuthException {
// ...
handler = new CallbackHandler() {
@Override
public void handle(Callback[] callbacks) throws IOException, UnsupportedCallbackException {
// just logs its arguments
}
};
}
因此,it.jaspic.sec.TokenSAM#validateRequest
无法将调用者的身份传达给运行时。由于它仍然错误地返回AuthStatus.SUCCESS
,从那时起它几乎是未定义的行为,至少就 JASPIC 而言。有趣的是,在这种情况下,好像 Servlet 容器试图让双方都满意,AuthStatus
一方面尊重表明成功的身份验证消息交换的 SAM,另一方面尊重应用程序<security-constraint>
。诚然,一个401
,403
或者更好的500
响应——表明身份验证机制不遵守其契约——可能不那么令人困惑。
显而易见的解决方案是将运行时提供的处理程序传递给 SAM。API 显然没有多大帮助,但对于单个消息层/单个应用程序/单个身份验证机制用例,当运行时首次通过调用请求它时,只需ServerAuthConfig
使用处理程序延迟实例化就足够了:getServerAuthConfig
public synchronized ServerAuthConfig getServerAuthConfig(String layer, String appContext, CallbackHandler handler) {
if (serverAuthConfig == null) {
serverAuthConfig = new TokenServerConfig(handler);
}
return serverAuthConfig;
}
当然,上面调用的新构造函数(它只需要存储处理程序参数)必须被引入it.jaspic.sec.TokenServerConfig
.
这两个更改应该使/services/user/userA
端点可访问。