如何在生产中安全地更改会话 cookie 域或名称? [英] How to safely change the session cookie DOMAIN or name in production?

查看:60
本文介绍了如何在生产中安全地更改会话 cookie 域或名称?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我们最近意识到我们的会话 cookie 被写入我们网站的完全限定域名,www.myapp.com,例如:

We recently realized that our session cookie is being written out to the fully qualified domain name of our site, www.myapp.com, for example:

MYAPPCOOKIE: 79D5DB83..., domain: www.myapp.com

我们希望将其切换为可以跨子域共享的 cookie,因此 myapp.com 上的任何服务器也可以使用会话 cookie.例如,我们希望我们的 cookie 像这样存储:

We want to switch this to being a cookie that can be shared cross subdomain, so any server at myapp.com can use the session cookie as well. For example, we'd like our cookie to store like so:

MYAPPCOOKIE: 79D5DB83..., domain: .myapp.com

我们尝试更改会话 cookie 以使用该域,如下所示:

We tried just changing our session cookie to use that domain like so:

   Cookie sessionCookie = sessionManager.getSessionIdCookie();
   sessionCookie.setDomain(".myapp.com");                

这在大多数情况下都可以正常工作.

and this works fine in most cases.

我们发现在某些情况下,部分用户在部署此新代码后无法登录.当用户:

We're finding some users can't login after deploying this new code in some situations. The problem arises when a user:

  • 已在当前浏览器会话中登录到我们的网站,但当前未登录.
  • 他们再次尝试登录

他们的浏览器中似乎有 2 个会话 cookie:

It appears there are 2 session cookies in their browser:

  • 来自他们之前会话的陈旧 cookie,带有完全限定的域名

  • a stale cookie from their previous session, with the fully qualified domain name

MYAPPCOOKIE: 79D5DB83..., domain: www.myapp.com

  • 他们刚刚登录的会话的新会话 cookie,带有新的域设置

  • the new session cookie for the session they just logged into, with the new domain setting

    MYAPPCOOKIE: 79D5DB83..., domain: .myapp.com
    

  • 管理这个旧饼干的最佳方法是什么?如果用户没有会话,我们已经尝试添加一些代码来删除旧的 cookie,但是我们的应用程序的某些路径似乎不起作用.

    What's the best way to manage this old cookie being around? We've tried adding some code to delete the old cookie if a user doesn't have a session, but there are some paths into our app where this doesn't seem to work.

    如果可行,我们愿意重命名 cookie,并且正在寻找其他人可能有的任何建议.谢谢!

    We're open to renaming the cookie if that might work, and are looking for any suggestions others may have. Thanks!

    推荐答案

    以下方法通过将会话 cookie 重命名为新名称,并在需要时将旧值复制到新 cookie 名称来解决该问题.

    The following approach solves the problem by renaming the session cookie to something new, copying the old value to the new cookie name if required.

    它使用了一些 Apache 模块(mod_headersmod_setenvif) 将旧 cookie 值复制到新 cookie 名称时不存在.

    It uses some Apache modules (mod_headers and mod_setenvif) to copy the old cookie value to the new cookie name when the new cookie doesn't already exist.

      # We only want to copy the old cookie to the new cookie name
      # when it doesnt already exist in the request. To do so, we
      # set a "per request" flag which is used to determine if we need
      # to do the "cookie copy operation".
    
      <IfModule mod_setenvif.c>
        SetEnvIf Cookie "NEW_SESSION_ID=" HAS_NEW_SESSION_ID
      </IfModule mod_setenvif.c>
    
      # If the cookie "NEW_SESSION_ID" doesnt exist in the request, copy 
      # the old cookie value to the new cookie name. This allows seamless 
      # switching to the new cookie for users with existing sessions, and
      # also ensure that if we have to rollback our code change for some 
      # reason, the old cookie will still be ok. Of course if new sessions 
      # are created with the new cookie, then they wouldn't be copied over on
      # rollback, but a similar approach could be used if someone 
      # wanted to do so
    
      <IfModule mod_headers.c>
         RequestHeader edit Cookie "OLD_SESSION_ID=([0-9a-zA-Z\-]*)" "NEW_SESSION_ID=$1 DEBUG_MSG_FOR_REPLACING=TRUE; OLD_SESSION_ID=$1" env=!HAS_NEW_SESSION_ID
      </IfModule mod_headers.c>
    

    请注意,您可以通过查找 DEBUG_MSG_FOR_REPLACING cookie 值来测试替换是否有效,该值是我在替换完成后为调试目的而添加的.

    Note that you can test if the replace is working by looking for the DEBUG_MSG_FOR_REPLACING cookie value, which I've added for debugging purposes when the replace is done.

    以下是端点的一些示例代码,它只是将 cookie 标头的值转储到响应中,您可以在调试 Apache 更改时使用这些代码:

    The following is some sample code for an endpoint that just dumps the value of the cookies header to the response, which you could use when debugging your Apache changes:

    @GET
    @Path("dump_cookies")
    public Object dumpCookies(@Context HttpServletRequest request)
    {
      String result = request.getHeader("Cookie");
      String cookies = result.replace("; ", "<br/>");
    
      String html = "<h1>Raw</h1>" + result;
    
      html += "<hr/>";
      html += "<h1>Cookies</h1>" + cookies;
    
      return html;
    }
    

    请注意,由于业务原因阻止我们重命名 cookie,我们最终并未使用此解决方案.我们最终使用了这个解决方案,这让我们可以保持我们的 cookie 名称相同.

    Note that we didn't end up using this solution because of business reasons that stopped us from renaming the cookie. We ended up using this solution instead which allowed us to keep our cookie name the same.

    这篇关于如何在生产中安全地更改会话 cookie 域或名称?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

    查看全文
    登录 关闭
    扫码关注1秒登录
    发送“验证码”获取 | 15天全站免登陆