You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在WildFly 36中结合Elytron实现WSS用户名密码摘要认证

WildFly 36 + Elytron 实现WSS用户名密码摘要认证及SecurityContext访问

一、实现自定义WSS密码回调处理器

WSS用户名密码摘要认证需要实现CallbackHandler处理WSPasswordCallback,由于WildFly 36移除Spring支持且EJB注入无法生效,直接通过Elytron API获取安全域即可:

import javax.security.auth.callback.Callback;
import javax.security.auth.callback.CallbackHandler;
import javax.security.auth.callback.UnsupportedCallbackException;
import javax.xml.ws.security.WSPasswordCallback;
import org.wildfly.security.auth.server.SecurityDomain;
import org.wildfly.security.auth.server.SecurityIdentity;
import org.wildfly.security.password.Password;
import org.wildfly.security.password.interfaces.ClearPassword;
import java.io.IOException;

public class WSSPasswordCallbackHandler implements CallbackHandler {

    @Override
    public void handle(Callback[] callbacks) throws IOException, UnsupportedCallbackException {
        for (Callback callback : callbacks) {
            if (callback instanceof WSPasswordCallback wsCallback) {
                // 处理用户名令牌的摘要验证场景
                if (wsCallback.getUsage() == WSPasswordCallback.USERNAME_TOKEN_UNKNOWN) {
                    SecurityDomain securityDomain = SecurityDomain.getCurrent();
                    if (securityDomain == null) {
                        throw new IOException("Elytron SecurityDomain not found");
                    }

                    try {
                        // 通过安全域认证用户并获取身份信息
                        SecurityIdentity identity = securityDomain.getAuthenticationManager()
                                .authenticate(wsCallback.getIdentifier(), evidence -> {
                                    // 从Elytron身份存储中获取用户密码
                                    Password password = securityDomain.getRealm(wsCallback.getIdentifier())
                                            .getPassword(wsCallback.getIdentifier());
                                    return password instanceof ClearPassword ?
                                            ((ClearPassword) password).getPassword() : null;
                                });

                        // 将明文密码设置到回调,供WSS引擎做摘要比对
                        if (identity != null) {
                            ClearPassword clearPassword = identity.getCredential(ClearPassword.class);
                            if (clearPassword != null) {
                                wsCallback.setPassword(new String(clearPassword.getPassword()));
                            }
                        }
                    } catch (Exception e) {
                        throw new IOException("Failed to load password for user: " + wsCallback.getIdentifier(), e);
                    }
                }
            } else {
                throw new UnsupportedCallbackException(callback, "Unsupported callback type");
            }
        }
    }
}

二、WildFly Elytron与WSS配置

  1. 配置Elytron安全域
    在standalone.xml/domain.xml的Elytron子系统中添加安全域(示例基于properties文件存储用户):
<subsystem xmlns="urn:wildfly:elytron:13.0">
    <security-domains>
        <security-domain name="WSSecurityDomain" default-realm="WSSRealm">
            <realm name="WSSRealm">
                <properties-realm path="users.properties" relative-to="jboss.server.config.dir" plain-text="false"/>
            </realm>
        </security-domain>
    </security-domains>
</subsystem>
  1. 配置Web服务安全上下文
    在Web服务子系统中添加端点配置,关联WSS处理器和安全策略:
<subsystem xmlns="urn:jboss:domain:webservices:17.0">
    <endpoint-configurations>
        <endpoint-config name="WSSecuredEndpoint">
            <pre-handler-chain name="WSSecurityChain" protocol="SOAP11_HTTP">
                <handler name="WSAuthenticationHandler" class-name="com.sun.xml.ws.security.opt.impl.handler.WSAuthenticationHandler">
                    <handler-param name="security.config" value="${jboss.server.config.dir}/wss-config.xml"/>
                </handler>
            </pre-handler-chain>
        </endpoint-config>
    </endpoint-configurations>
</subsystem>
  1. WSS安全策略文件(wss-config.xml)
    在jboss.server.config.dir目录下创建该文件,指定回调处理器和认证规则:
<xwss:SecurityConfiguration xmlns:xwss="http://java.sun.com/xml/ns/xwss/config">
    <xwss:UsernameToken digestPassword="true" useNonce="true" useTimestamp="true"/>
    <xwss:CallbackHandler class-name="com.yourpackage.WSSPasswordCallbackHandler"/>
</xwss:SecurityConfiguration>

三、在SOAP端点中访问Elytron SecurityContext

认证通过后,Elytron会将SecurityIdentity绑定到当前线程上下文,直接通过API获取即可,无需依赖注入:

import javax.jws.WebService;
import org.wildfly.security.auth.server.SecurityDomain;
import org.wildfly.security.auth.server.SecurityIdentity;

@WebService(endpointInterface = "com.yourpackage.YourService")
public class YourServiceImpl implements YourService {

    @Override
    public String getGreeting() {
        SecurityIdentity identity = SecurityDomain.getCurrent().getCurrentSecurityIdentity();
        String username = identity.getPrincipal().getName();
        // 可进一步获取用户角色、凭证等信息
        return "Authenticated user: " + username;
    }
}

关键注意事项

  • 自定义回调处理器需打包到应用中,若需全局使用可部署为WildFly模块。
  • 生产环境避免使用明文密码存储,需配置Elytron的密码加密机制。
  • 客户端WSS配置需与服务端一致(摘要模式、nonce、timestamp开关)。

内容的提问来源于stack exchange,提问作者Markus

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.12 13:25:09