zoukankan      html  css  js  c++  java
  • netcore 实现跨应用的分布式session

    • 需求场景

      • 网站a,域名为 a.site.com
      • 网站b, 域名为 b.site.com
      • 需要在a、b两个站点之间共享session
    • 解决方案

      • 使用redis作为分布式缓存存储
      • 设置sessionId cookie 保存的域名,使得两个网站钧能够读取到相同的sessionId
      services.AddDistributedRedisCache(options => //使用redis
      {
          options.Configuration = $"{conf},defaultDatabase={dbId}";
      });
      
      services.AddSession(options =>
      {
          options.IdleTimeout = TimeSpan.FromMinutes(30);
          options.Cookie.Domain = "site.com";
      });
      
      • 自定义SessionMiddleware

        • 由于Asp.net 自带的SessionMiddleware中间中对sessionid做了加密处理,导致不同应用虽然sessionId相同,但是并不能成功的共享Session,具体详件SessionMiddleware源码,其中使用了CookieProtection类的对sessionId进行了加密

        • public async Task Invoke(HttpContext context)
          {
              ....
              if (string.IsNullOrWhiteSpace(sessionKey) || sessionKey.Length != SessionKeyLength)
              {
                  // No valid cookie, new session.
                  var guidBytes = new byte[16];
                  CryptoRandom.GetBytes(guidBytes);
                  sessionKey = new Guid(guidBytes).ToString();
                  cookieValue = CookieProtection.Protect(_dataProtector, sessionKey);
                  var establisher = new SessionEstablisher(context, cookieValue, _options);
                  tryEstablishSession = establisher.TryEstablishSession;
                  isNewSessionKey = true;
              }
              ...
          }
          
        • 由于SessionMiddleware是直接依赖类CookieProtection,因此需要重新实现自己的中间件来处理session,比如实现一个MySessionMiddleware,即可实现session共享

          public async Task Invoke(HttpContext context)
          {
              ....
              if (string.IsNullOrWhiteSpace(sessionKey) || sessionKey.Length != SessionKeyLength)
              {
                  // No valid cookie, new session.
                  var guidBytes = new byte[16];
                  CryptoRandom.GetBytes(guidBytes);
                  sessionKey = new Guid(guidBytes).ToString();
                  cookieValue = Md5(sessionKey);//此处可以使用自己的加密规则,重要的是保证不同的应用,通过加密规则生成的值是相同的
                  var establisher = new SessionEstablisher(context, cookieValue, _options);
                  tryEstablishSession = establisher.TryEstablishSession;
                  isNewSessionKey = true;
              }
              ...
          }
          
  • 相关阅读:
    PHP调试的时候出现了警告:
    快报滚动
    js foreach、map函数
    箭头函数和普通函数的区别
    flex布局
    react+propTypes
    手机尺寸
    less的使用
    发现是在IE6-IE9下,下列元素table,thead,tfoot,tbody,tr,col,colgroup,html,title,style,frameset的innerHTML属性是只读的
    div+css 组织结构
  • 原文地址:https://www.cnblogs.com/zcode/p/11563334.html
Copyright © 2011-2022 走看看