java - 在 WebSocket @ServerEndpoint 中访问 HttpServletRequest 属性

标签 java servlets jakarta-ee websocket java-websocket

我需要访问 HttpServletRequest 属性以获取 javax.servlet.request.X509Certificate,其中包含用于 TLS 的 X509Certificate 证书数组请求。

从 JAX-RS ContainerRequestFilter 我可以很容易地从 ContainerRequestContext.getProperty(String property) 方法中提取它,但我找不到获取它的方法从 WebSocket SessionHandshakeRequest,我可以从中访问 HttpSession 实例,但不能访问 HttpServletRequest 实例。

注意:这不是 Accessing HttpSession from HttpServletRequest in a Web Socket @ServerEndpoint 的副本因为我需要访问 HttpServletRequest(或等同于提取 TLS 证书),而不是 HttpSession

由于 WebSocket 是 HTTP 的超集,我想它应该是可能的,希望 Java 团队已经想到了一种访问 servlet 属性的方法,但我真的找不到。有人知道这是否可能吗?

最佳答案

没有黑客:

  1. 在 URL 模式匹配 websocket 握手请求时创建 servlet 过滤器。
  2. 在过滤器中,获取感兴趣的请求属性并在继续链之前将其放入 session 中。
  3. 最后从 session 中获取它,而 session 又只能通过握手请求获得。

通过黑客攻击:

  1. 使用反射找到握手请求实例中的ServletRequest字段。
  2. 获取其 javax.servlet.request.X509Certificate 属性。

    换句话说:

    public class ServletAwareConfigurator extends Configurator {
    
        @Override
        public void modifyHandshake(ServerEndpointConfig config, HandshakeRequest request, HandshakeResponse response) {
            ServletRequest servletRequest = getField(request, ServletRequest.class);
            X509Certificate[] certificates = (X509Certificate[]) servletRequest.getAttribute("javax.servlet.request.X509Certificate");
            // ...
        }
    
        private static <I, F> F getField(I instance, Class<F> fieldType) {
            try {
                for (Class<?> type = instance.getClass(); type != Object.class; type = type.getSuperclass()) {
                    for (Field field : type.getDeclaredFields()) {
                        if (fieldType.isAssignableFrom(field.getType())) {
                            field.setAccessible(true);
                            return (F) field.get(instance);
                        }
                    }
                }
            } catch (Exception e) {
                // Handle?
            }
    
            return null;
        }
    
    }
    

关于java - 在 WebSocket @ServerEndpoint 中访问 HttpServletRequest 属性,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36184382/

相关文章:

java - 在java中计算数字的大小

java - Java MVC 模型 2 架构的示例?

java - JSP/Servlets : How do I Upload a zip file, 解压缩并提取 CSV 文件

java - MySQLIntegrityConstraintViolationException : Column 'Firstname' cannot be null

eclipse - 如何修复 "Cannot invoke Tomcat manager: Server returned HTTP response code: 403 "

java - 在同一项目中打开声明时,Eclipse 打开 .class 而不是 .java

java - 为什么在我的 Tomcat JRuby 应用程序中从未释放内存?

java - 缺少对验证(模拟)的方法调用,但是有一个吗?

java - 如何在Hibernate中添加数据库更改的监听器?

java - 相当于 <html :messages> in thymeleaf for displaying messages