JMS微服务开发示例(五)生成短token,实现用户无状态登录

用户token,也可以利用第三方框架生成,JMS也包含了自己的token服务器。

Token的生成原理:

 部署TokenServer

这里下载 tokenserver.zip,然后部署运行TokenServer。

 微服务中编写Login函数

引用 JMS.Token nuget包

代码如下:

               /// <summary>
        /// 登陆系统
        /// </summary>
        /// <param name="userName">用户名</param>
        /// <param name="password">密码</param>
        /// <returns>用户token</returns>
        public string Login(string userName,string password)
        {
            //假设用户登陆成功,id为888
            var userid = 888;
            var tokenClient = new TokenClient("192.168.40.132", 9911);
            var token = tokenClient.BuildLongWithExpire(userid, DateTime.Now.AddMinutes(15));return token;
        }

        /// <summary>
        /// 刷新token
        /// </summary>
        /// <returns>新的用户token</returns>
        [JMS.Authorize]
public string RefreshToken()
{

                 var tokenClient = new TokenClient("192.168.40.132", 9911);
                 var token = tokenClient.BuildLongWithExpire((long)this.UserContent, DateTime.Now.AddMinutes(15));
                 return token;

        }

Program.cs中,启用JMS.Token作为身份验证

services.UseJmsTokenAuthentication(AuthorizationContentType.Long, "192.168.40.132", 9911,"auth");

Controller中,如果所有方法要求身份验证,才能调用,那么,在Controller上加上 [JMS.Authorize] 标识,如果只是某些方法要求身份验证,那么,在方法上加 [JMS.Authorize] 标识

上面代码展示了如何生成一个最短的token,如果你想在token里面放更多的信息,可以使用TokenClient.BuildForString函数生成。不过,有userid和过期时间足矣了,因为token需要每次都放在头部传输,太长只会增加网络流量。

客户端访问微服务时,把token放在header里面

            using ( var tran = CreateMST() )
            {
                tran.SetHeader("auth", token);
                .......

 AspNet中使用JMS.Token验证

nuget 引用 JMS.Token.AspNetCore

        public void ConfigureServices(IServiceCollection services)
        {
            services.AddJmsTokenAuthentication(JMS.Token.AspNetCore.TokenContentType.Longs, "127.0.0.1", 9911);

            services.AddControllers();
         
        }
        public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
        {
            if (env.IsDevelopment())
            {
                app.UseDeveloperExceptionPage();
            }

            app.UseRouting();

            //启用身份验证
            app.UseAuthentication();
            app.UseAuthorization();

            app.UseEndpoints(endpoints =>
            {
                endpoints.MapControllers();
            });
        }

Controller中获取身份信息:[Authorize]为标准的AspNet [Authorize],不是JMS.Authorize

        [Authorize]
        [HttpGet]
        public string Test()
        {
            return this.User.FindFirstValue("Content");
        }

 JS端token解码,获取过期时间

    //解码string类型的token
    function decodeJmsStringToken(token) {
        var str = window.atob(token);
        var strArr = JSON.parse(str);
        var obj = JSON.parse(strArr[0]);
        var expireTime = new Date(new Date(1970, 0, 1).getTime() + obj.e * 1000);
        return {
            content: obj.d,
            expireTime: expireTime
        };
    }

    //解码long类型的token
    function decodeJmsLongToken(token) {
        var raw = window.atob(token);
        var rawLength = raw.length;
       
        var array = new Uint8Array(new ArrayBuffer(rawLength));

        for (var i = 0; i < rawLength; i++) {
            array[i] = raw.charCodeAt(i);
        }

        var expireTime = 0;
        if (!expireTime) {
            var timeArr = array.slice(10, 18);
            for (var i = 0; i < 4; i++) {
                expireTime = expireTime | ((timeArr[i] & 0xFF) << (i * 8));
            }

            expireTime = new Date(new Date(1970, 0, 1).getTime() + expireTime * 1000);
        }
        return {
            expireTime: expireTime
        };

    }

JMS示例列表

原文地址:https://www.cnblogs.com/IWings/p/13361243.html