在 doFilter 中设置后获取 Cookie

Get Cookie after its set in doFilter

我有一个 CookieFilter class,它覆盖 doFilter 方法以在调用我的 Rest 服务之前设置 Cookie:

import javax.servlet.*;
import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.util.UUID;

public class CookieFilter implements Filter {

    @Override
    public void init(FilterConfig config) throws ServletException {}

    @Override
    public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) 
         throws IOException, ServletException {

        HttpServletRequest httpRequest = (HttpServletRequest) request;
        HttpServletResponse httpResponse = (HttpServletResponse) response;

        if (notPresent("TEST")) {
             String uuid = UUID.randomUUID().toString();
             httpResponse.addCookie(new Cookie("TEST", uuid));
        }

        chain.doFilter(request, response);
    }

    @Override
    public void destroy() {}

    private boolean notPresent(String cookieName) {
         // here are the checks
    }
}

休息服务方式:

void myRestServiceMethod(@Context HttpServletRequest request) {
   Cookie[] cookies = request.getCookies(); // has my cookie inside after second call
   // other logic bellow
}

在 doFilter 之后调用了 myRestServiceMethod,但 Cookie 不存在。

但是,我能够在对 myRestServiceMethod 的第二次客户端调用中读取 cookie(使用 JAX-RS @Context 检索 HttpServletRequest 对象),其中 Cookie(在第一次调用中设置)从客户端发送并传递给服务器。

我的问题是:在 doFilter 中设置 myRestServiceMethod 后,有没有办法在第一次调用 Cookie 时读取它?

is there a way read the Cookie in a first call to myRestServiceMethod after its set in doFilter?

没有

有2种解决方案:

  1. 添加cookie后刷新请求

    if (notPresent("TEST")) {
        String uuid = UUID.randomUUID().toString();
        httpResponse.addCookie(new Cookie("TEST", uuid));
        httpRequest.sendRedirect(httpRequest.getRequestURI()); // NOTE: you might want to add query string if necessary.
    }
    else {
        chain.doFilter(request, response);
    }
    
  2. 或者,更好的是,将其存储为请求属性。

    String uuid = getCookieValue("TEST");
    
    if (uuid == null) {
        uuid = UUID.randomUUID().toString();
        httpResponse.addCookie(new Cookie("TEST", uuid));
    }
    
    request.setAttribute("TEST", uuid);
    chain.doFilter(request, response);
    

    这样你就可以简单地做到这一点。

    String uuid = (String) request.getAttribute("TEST");
    

    如果 CDI 在环境中可用,您可以改为填充 @RequestScoped bean。

也就是说,有一个 JAX-RS 服务来(间接)处理 cookie 很奇怪。 REST 永远不会是有状态的。