如何在 WildFly 中设置应用程序级 SAM
How to setup an application level SAM in WildFly
我之前有一些代码在 Glassfish 上运行,但我想将它移植到 WildFly。
但是,我似乎无法让 WildFly 调用该模块。 ServletContextListener
初始化模块如下
AuthConfigFactory.getFactory()
.registerConfigProvider(new OpenIdConnectModuleConfigProvider(options, null),
"HttpServlet", getAppContext(sce), null);
"HttpServlet"
不是 Glassfish 特有的,似乎在 https://github.com/wildfly/wildfly/blob/master/undertow/src/main/java/org/wildfly/extension/undertow/security/jaspi/JASPIAuthenticationMechanism.java?source=cc
中被引用
Glassfish 不需要 web.xml
上的 <logon-config>
块并且在 WildFly 中放置任何变体都不起作用(正如预期的那样)
我怀疑的另一个地方是我如何计算应用程序上下文标识符。对于 Glassfish,我有
private String getAppContext(final ServletContextEvent sce) {
return sce.getServletContext()
.getVirtualServerName() + " "
+ sce.getServletContext()
.getContextPath();
}
在 WildFly 中会有所不同吗?虽然我在 https://github.com/rdebusscher/secSpikeWeb/blob/master/src/main/java/org/omnifaces/security/jaspic/core/Jaspic.java#L300 中也看到了类似的代码
我也试过添加到 standalone.xml
这个块
<security-domain name="jaspi" cache-type="default">
<authentication-jaspi>
<login-module-stack name="dummy">
<login-module code="Dummy" flag="optional"/>
</login-module-stack>
<auth-module code="org.wildfly.extension.undertow.security.jaspi.modules.HTTPSchemeServerAuthModule" flag="required"/>
</authentication-jaspi>
</security-domain>
并设置<default-security-domain value="jaspi"/>
但是它没有任何效果,在模块中放置断点也没有显示它被命中。
此外,我找不到像在 glassfish-web.xml
中那样在 WildFly 中执行以下操作的方法,但这可能是另一个问题
<security-role-mapping>
<role-name>users</role-name>
<group-name>https://helloworld</group-name>
</security-role-mapping>
代码很长,但是要点可以在
中找到
https://github.com/trajano/openid-connect/tree/openid-connect-1.0.1/openid-connect-jaspic-module
和
https://github.com/trajano/openid-connect/tree/openid-connect-1.0.1/openid-connect-jaspic-sample
请注意,我在 应用程序级别 上寻找它,而不是设置全局服务器 JASPI。
"HttpServlet" is not Glassfish specific
没错,据我所知,这是一个标准标识符,表示要为 Java EE 中的哪个子系统注册身份验证模块。但是只有一个其他有效值,其中包含 "soap"(不确定)。
Could it be different in WildFly?
不,这是 standard way。
And set <default-security-domain value="jaspi"/>
在standalone.xml
中recommended的方式应该是这样的:
<security-domain name="jaspitest" cache-type="default">
<authentication-jaspi>
<login-module-stack name="dummy">
<login-module code="Dummy" flag="optional"/>
</login-module-stack>
<auth-module code="Dummy"/>
</authentication-jaspi>
</security-domain>
然后将the following放入WEB-INF/jboss-web.xml
:
<jboss-web>
<security-domain>jaspitest</security-domain>
</jboss-web>
这个应该就够了。这是我在 WildFly 8.2 和 9.0 上使用的,也是 Java EE 示例项目使用的。但是设置默认域也应该像你一样工作,你的激活码也足够接近,所以我不确定以上是否会对你的情况产生影响。
或者有一种 JBoss specific programmatic 激活 JASPIC 的方法:
String securityDomain = "other";
IdentityManager identityManager = deploymentInfo.getIdentityManager();
if (identityManager instanceof JAASIdentityManagerImpl) {
try {
Field securityDomainContextField =
JAASIdentityManagerImpl.class.getDeclaredField("securityDomainContext");
securityDomainContextField.setAccessible(true);
SecurityDomainContext securityDomainContext =
(SecurityDomainContext)
securityDomainContextField.get(identityManager);
securityDomain =
securityDomainContext.getAuthenticationManager().getSecurityDomain();
} catch (NoSuchFieldException | SecurityException |
IllegalArgumentException | IllegalAccessException e) {
throw new RuntimeException(e);
}
}
ApplicationPolicy applicationPolicy = new
ApplicationPolicy(securityDomain);
JASPIAuthenticationInfo authenticationInfo = new
JASPIAuthenticationInfo(securityDomain);
applicationPolicy.setAuthenticationInfo(authenticationInfo);
SecurityConfiguration.addApplicationPolicy(applicationPolicy);
deploymentInfo.setJaspiAuthenticationMechanism(new
JASPIAuthenticationMechanism(securityDomain, null));
deploymentInfo.setSecurityContextFactory(new
JASPICSecurityContextFactory(securityDomain));
您需要从 io.undertow.servlet.ServletExtension
执行
遗憾的是 JBoss 需要激活 JASPIC。但是上面显示的方法之一应该确实有效。我刚刚在股票 WildFly 9.0 上验证了它们并且它在那里工作。测试SAM的validateRequest
方法被正确调用。
我之前有一些代码在 Glassfish 上运行,但我想将它移植到 WildFly。
但是,我似乎无法让 WildFly 调用该模块。 ServletContextListener
初始化模块如下
AuthConfigFactory.getFactory() .registerConfigProvider(new OpenIdConnectModuleConfigProvider(options, null), "HttpServlet", getAppContext(sce), null);
"HttpServlet"
不是 Glassfish 特有的,似乎在 https://github.com/wildfly/wildfly/blob/master/undertow/src/main/java/org/wildfly/extension/undertow/security/jaspi/JASPIAuthenticationMechanism.java?source=cc
Glassfish 不需要 web.xml
上的 <logon-config>
块并且在 WildFly 中放置任何变体都不起作用(正如预期的那样)
我怀疑的另一个地方是我如何计算应用程序上下文标识符。对于 Glassfish,我有
private String getAppContext(final ServletContextEvent sce) {
return sce.getServletContext()
.getVirtualServerName() + " "
+ sce.getServletContext()
.getContextPath();
}
在 WildFly 中会有所不同吗?虽然我在 https://github.com/rdebusscher/secSpikeWeb/blob/master/src/main/java/org/omnifaces/security/jaspic/core/Jaspic.java#L300 中也看到了类似的代码
我也试过添加到 standalone.xml
这个块
<security-domain name="jaspi" cache-type="default">
<authentication-jaspi>
<login-module-stack name="dummy">
<login-module code="Dummy" flag="optional"/>
</login-module-stack>
<auth-module code="org.wildfly.extension.undertow.security.jaspi.modules.HTTPSchemeServerAuthModule" flag="required"/>
</authentication-jaspi>
</security-domain>
并设置<default-security-domain value="jaspi"/>
但是它没有任何效果,在模块中放置断点也没有显示它被命中。
此外,我找不到像在 glassfish-web.xml
中那样在 WildFly 中执行以下操作的方法,但这可能是另一个问题
<security-role-mapping>
<role-name>users</role-name>
<group-name>https://helloworld</group-name>
</security-role-mapping>
代码很长,但是要点可以在
中找到https://github.com/trajano/openid-connect/tree/openid-connect-1.0.1/openid-connect-jaspic-module
和
https://github.com/trajano/openid-connect/tree/openid-connect-1.0.1/openid-connect-jaspic-sample
请注意,我在 应用程序级别 上寻找它,而不是设置全局服务器 JASPI。
"HttpServlet" is not Glassfish specific
没错,据我所知,这是一个标准标识符,表示要为 Java EE 中的哪个子系统注册身份验证模块。但是只有一个其他有效值,其中包含 "soap"(不确定)。
Could it be different in WildFly?
不,这是 standard way。
And set
<default-security-domain value="jaspi"/>
在standalone.xml
中recommended的方式应该是这样的:
<security-domain name="jaspitest" cache-type="default">
<authentication-jaspi>
<login-module-stack name="dummy">
<login-module code="Dummy" flag="optional"/>
</login-module-stack>
<auth-module code="Dummy"/>
</authentication-jaspi>
</security-domain>
然后将the following放入WEB-INF/jboss-web.xml
:
<jboss-web>
<security-domain>jaspitest</security-domain>
</jboss-web>
这个应该就够了。这是我在 WildFly 8.2 和 9.0 上使用的,也是 Java EE 示例项目使用的。但是设置默认域也应该像你一样工作,你的激活码也足够接近,所以我不确定以上是否会对你的情况产生影响。
或者有一种 JBoss specific programmatic 激活 JASPIC 的方法:
String securityDomain = "other";
IdentityManager identityManager = deploymentInfo.getIdentityManager();
if (identityManager instanceof JAASIdentityManagerImpl) {
try {
Field securityDomainContextField =
JAASIdentityManagerImpl.class.getDeclaredField("securityDomainContext");
securityDomainContextField.setAccessible(true);
SecurityDomainContext securityDomainContext =
(SecurityDomainContext)
securityDomainContextField.get(identityManager);
securityDomain =
securityDomainContext.getAuthenticationManager().getSecurityDomain();
} catch (NoSuchFieldException | SecurityException |
IllegalArgumentException | IllegalAccessException e) {
throw new RuntimeException(e);
}
}
ApplicationPolicy applicationPolicy = new
ApplicationPolicy(securityDomain);
JASPIAuthenticationInfo authenticationInfo = new
JASPIAuthenticationInfo(securityDomain);
applicationPolicy.setAuthenticationInfo(authenticationInfo);
SecurityConfiguration.addApplicationPolicy(applicationPolicy);
deploymentInfo.setJaspiAuthenticationMechanism(new
JASPIAuthenticationMechanism(securityDomain, null));
deploymentInfo.setSecurityContextFactory(new
JASPICSecurityContextFactory(securityDomain));
您需要从 io.undertow.servlet.ServletExtension
遗憾的是 JBoss 需要激活 JASPIC。但是上面显示的方法之一应该确实有效。我刚刚在股票 WildFly 9.0 上验证了它们并且它在那里工作。测试SAM的validateRequest
方法被正确调用。