CrazyIter_Bin 1 年之前
父节点
当前提交
8f6c5d786a

+ 35 - 25
TEAMModelOS.SDK/Context/Attributes/Filter/ApiTokenAttribute.cs

@@ -227,40 +227,49 @@ namespace TEAMModelOS.Filter
                                         //如果是商务合作模式 则需要手动获取学校编码
                                        
 
-                                        if (path.ToString().Contains("get-schools"))
+                                        if (path.ToString().Contains("get-schools") ||path.ToString().Contains("business/sso")||path.ToString().Contains("business/notify-bind"))
                                         {
                                             pass = true;
+                                            if (path.ToString().Contains("business/sso") &&  !string.IsNullOrWhiteSpace(XAuthSchool)) 
+                                            {
+                                                pass=false;
+                                            }
                                         }
                                         else
                                         {
+                                            pass=false;
+                                        }
+                                        if (pass==false)
+                                        {
+
                                             //如果访问的接口是 business/get-schools
                                             if (!string.IsNullOrWhiteSpace(XAuthSchool))
                                             {
                                                 //访问次数记录 开始
-                                                long udate = DateTimeOffset.UtcNow.ToUnixTimeMilliseconds();
-                                                var respon = _azureCosmos.GetCosmosClient().GetContainer("TEAMModelOS", "Normal").ReadItemStreamAsync(id, new Azure.Cosmos.PartitionKey("BizVisit")).Result;
-                                                if (respon.Status == 200)
-                                                {
-                                                    BizVisitCnt bizVisit = JsonDocument.Parse(respon.Content).Deserialize<BizVisitCnt>();
-                                                    bizVisit.visit += 1;
-                                                    //var tempApi = bizVisit.apis.Find(f => f.name.Equals($"{path}"));
-                                                    //if (tempApi != null)
-                                                    //{
-                                                    //    tempApi.visit += 1;
-                                                    //    tempApi.upDate = udate;
-                                                    //}
-                                                    //else
-                                                    bizVisit.apis.Add(new APIInfo() { name = $"{path}", upDate = udate });//记录加一下
-                                                       _azureCosmos.GetCosmosClient().GetContainer("TEAMModelOS", "Normal").ReplaceItemAsync<BizVisitCnt>(bizVisit, id, new Azure.Cosmos.PartitionKey("BizVisit"));
-                                                }
-                                                else
-                                                {
-                                                    BizVisitCnt bizVisit = new() { id = id, visit = 1, apis = new List<APIInfo>() { new APIInfo() { name = $"{path}", upDate = udate } } };
-                                                  _azureCosmos.GetCosmosClient().GetContainer("TEAMModelOS", "Normal").CreateItemAsync<BizVisitCnt>(bizVisit, new Azure.Cosmos.PartitionKey("BizVisit"));
-                                                }
+                                                //long udate = DateTimeOffset.UtcNow.ToUnixTimeMilliseconds();
+                                                //var respon = _azureCosmos.GetCosmosClient().GetContainer("TEAMModelOS", "Normal").ReadItemStreamAsync(id, new Azure.Cosmos.PartitionKey("BizVisit")).Result;
+                                                //if (respon.Status == 200)
+                                                //{
+                                                //    BizVisitCnt bizVisit = JsonDocument.Parse(respon.Content).Deserialize<BizVisitCnt>();
+                                                //    bizVisit.visit += 1;
+                                                //    //var tempApi = bizVisit.apis.Find(f => f.name.Equals($"{path}"));
+                                                //    //if (tempApi != null)
+                                                //    //{
+                                                //    //    tempApi.visit += 1;
+                                                //    //    tempApi.upDate = udate;
+                                                //    //}
+                                                //    //else
+                                                //    bizVisit.apis.Add(new APIInfo() { name = $"{path}", upDate = udate });//记录加一下
+                                                //       _azureCosmos.GetCosmosClient().GetContainer("TEAMModelOS", "Normal").ReplaceItemAsync<BizVisitCnt>(bizVisit, id, new Azure.Cosmos.PartitionKey("BizVisit"));
+                                                //}
+                                                //else
+                                                //{
+                                                //    BizVisitCnt bizVisit = new() { id = id, visit = 1, apis = new List<APIInfo>() { new APIInfo() { name = $"{path}", upDate = udate } } };
+                                                //  _azureCosmos.GetCosmosClient().GetContainer("TEAMModelOS", "Normal").CreateItemAsync<BizVisitCnt>(bizVisit, new Azure.Cosmos.PartitionKey("BizVisit"));
+                                                //}
                                                 //访问次数记录 结束
 
-                                                var response =    _azureCosmos.GetCosmosClient().GetContainer("TEAMModelOS", "Normal").ReadItemStreamAsync(id, new Azure.Cosmos.PartitionKey("BizConfig")).Result;
+                                                var response = _azureCosmos.GetCosmosClient().GetContainer("TEAMModelOS", "Normal").ReadItemStreamAsync(id, new Azure.Cosmos.PartitionKey("BizConfig")).Result;
                                                 if (response.Status == 200)
                                                 {
                                                     BizConfig bizConfig = JsonDocument.Parse(response.Content).Deserialize<BizConfig>();
@@ -270,7 +279,8 @@ namespace TEAMModelOS.Filter
                                                         school = XAuthSchool;
                                                         pass = true;
                                                     }
-                                                    else {
+                                                    else
+                                                    {
                                                         if (bizConfig.schools.IsNotEmpty() && bizConfig.schools.Select(z => z.id).Contains(XAuthSchool))
                                                         {
                                                             if (bizConfig.jti.Equals(jti))
@@ -290,7 +300,7 @@ namespace TEAMModelOS.Filter
                                                             pass = false;
                                                         }
                                                     }
-                                                        
+
                                                 }
                                                 else
                                                 {

+ 546 - 0
TEAMModelOS/Controllers/OpenApi/Business/BizSSOController.cs

@@ -0,0 +1,546 @@
+using Microsoft.AspNetCore.Mvc;
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Threading.Tasks;
+using TEAMModelOS.Models;
+using TEAMModelOS.SDK.DI;
+using System.Text.Json;
+using TEAMModelOS.SDK.Models;
+using Microsoft.AspNetCore.Http;
+using TEAMModelOS.SDK.Extension;
+using Azure.Cosmos;
+using System.Text;
+using Microsoft.Extensions.Options;
+using Azure.Messaging.ServiceBus;
+using Microsoft.Extensions.Configuration;
+using HTEXLib.COMM.Helpers;
+using TEAMModelOS.SDK;
+using System.IdentityModel.Tokens.Jwt;
+using TEAMModelOS.Services;
+using TEAMModelOS.SDK.Models.Service;
+using System.IO;
+using System.Dynamic;
+using Microsoft.AspNetCore.Authorization;
+using Azure.Storage.Blobs.Models;
+using static TEAMModelOS.SDK.Models.Teacher;
+using System.Web;
+using static TEAMModelOS.Controllers.FixDataController;
+using static TEAMModelOS.SDK.SchoolService;
+using Microsoft.AspNetCore.Hosting;
+using Microsoft.Azure.Cosmos.Table;
+using System.Net.Http;
+using TEAMModelOS.SDK.Context.Attributes.Azure;
+using System.Security.Cryptography.Xml;
+using DocumentFormat.OpenXml.Office2010.Excel;
+using DocumentFormat.OpenXml.Wordprocessing;
+using Microsoft.OData.UriParser;
+using System.ComponentModel.DataAnnotations;
+using System.Runtime.Intrinsics.X86;
+using System.Security.Policy;
+using Top.Api;
+using Grpc.Core;
+using OfficeOpenXml.FormulaParsing.LexicalAnalysis;
+using System.Net.Http.Json;
+using DocumentFormat.OpenXml.EMMA; 
+using TEAMModelOS.Filter;
+
+namespace TEAMModelOS.Controllers
+{
+    [ApiController]
+    [Route("business")]
+    public class BizSSOController : ControllerBase
+    {
+        private readonly SnowflakeId _snowflakeId;
+        private readonly AzureCosmosFactory _azureCosmos;
+        private readonly DingDing _dingDing;
+        private readonly Option _option;
+        private readonly AzureStorageFactory _azureStorage;
+        private readonly AzureServiceBusFactory _serviceBus;
+        private readonly AzureRedisFactory _azureRedis;
+        private readonly CoreAPIHttpService _coreAPIHttpService;
+      
+        public readonly IHttpClientFactory _httpClientFactory;
+
+        public IConfiguration _configuration { get; set; }
+        public BizSSOController(IWebHostEnvironment environment, AzureCosmosFactory azureCosmos, SnowflakeId snowflakeId, DingDing dingDing, IOptionsSnapshot<Option> option, AzureStorageFactory azureStorage,
+          AzureRedisFactory azureRedis, AzureServiceBusFactory serviceBus, IConfiguration configuration, CoreAPIHttpService coreAPIHttpService, IHttpClientFactory httpClientFactory)
+        {
+            _azureCosmos = azureCosmos;
+            _snowflakeId = snowflakeId;
+            _dingDing = dingDing;
+            _option = option?.Value;
+            _azureStorage = azureStorage;
+            _serviceBus = serviceBus;
+            _configuration = configuration;
+            _azureRedis = azureRedis;
+            _coreAPIHttpService = coreAPIHttpService;
+            _httpClientFactory = httpClientFactory;
+        }
+       
+        [HttpPost("sso")]
+        [ApiToken(Auth = "2200", Name = "单点登录跳转", TName = "单点登录跳转", EName = "联盟单点登录跳转", RWN = "W", Limit = false)]
+        public async Task<IActionResult> Sso(BizSso sso)
+        {
+            var (tokenId, authSchool) = HttpContext.GetApiTokenInfo();
+            string HostName = HttpContext.GetHostName();
+            if (!string.IsNullOrWhiteSpace(_option.HostName))
+            {
+                HostName = _option.HostName;
+            }
+            var rurl = new StringBuilder($"https://{HostName}/tmdid-sso");
+            Teacher teacher = null;
+            int status = 4;//1项目未配置,2 账号未未关联,3账号已关联
+            string msg = "账号未关联";
+            TmdidImplicit implicit_token = null;
+            string sql = $"select value c from c  join b in c.binds where b.type='{tokenId}' and b.userid ='{sso.userid}'";
+            var result = await _azureCosmos.GetCosmosClient().GetContainer(Constant.TEAMModelOS, Constant.Teacher).GetList<Teacher>(sql, "Base");
+            List<Teacher> teachers = result.list;
+            if (teachers.Any())
+            {
+                teacher=teachers[0];
+                status = 3;//已关联
+                msg = "账号已关联";
+                bool change = false;
+                if (!string.IsNullOrWhiteSpace(authSchool)) {
+                    teacher.defaultSchool = authSchool;
+                    change = true;
+                }
+                if (!string.IsNullOrWhiteSpace(sso.name))
+                {
+                    change = true;
+                    teacher.name = sso.name;
+                }
+                if (!string.IsNullOrWhiteSpace(sso.picture))
+                {
+                    change = true;
+                    teacher.picture = sso.picture;
+                }
+                if (change) { await _azureCosmos.GetCosmosClient().GetContainer(Constant.TEAMModelOS, Constant.Teacher).UpsertItemAsync(teacher, new PartitionKey("Base")); }
+            }
+            else
+            {
+                if (!string.IsNullOrWhiteSpace(sso.mobile))
+                {
+
+                    //如果沒有,則初始化Teacher基本資料到Cosmos
+                    teacher = new Teacher
+                    {
+                        createTime = DateTimeOffset.UtcNow.ToUnixTimeMilliseconds(),
+                        pk = "Base",
+                        code = "Base",
+                        name = sso.name?.ToString(),
+                        picture = sso.picture?.ToString(),
+                        //创建账号并第一次登录IES5则默认赠送1G
+                        size = 1,
+                        defaultSchool = authSchool,
+                        schools = new List<TeacherSchool>(),
+                    };
+                    //未绑定,尝试用手机号进行关联
+                    var coreUser = await _coreAPIHttpService.GetUserInfo(new Dictionary<string, string> { { "key", sso.mobile } }, _option.Location, _configuration);
+                    if (coreUser != null)
+                    {
+                        var response =  await _azureCosmos.GetCosmosClient().GetContainer(Constant.TEAMModelOS, Constant.Teacher).ReadItemStreamAsync(coreUser.id, new PartitionKey("Base"));
+                        if (response.Status==200) {
+                            teacher=JsonDocument.Parse(response.Content).RootElement.ToObject<Teacher>();
+                            teacher.defaultSchool=authSchool;
+                        }
+                        teacher.id = coreUser.id;
+                        status = 3;//已关联
+                        msg = "账号已关联";
+                        if (string.IsNullOrWhiteSpace(teacher.name)) {
+                            teacher.name=coreUser.name;
+                        }
+                        if (string.IsNullOrWhiteSpace(teacher.picture))
+                        {
+                            teacher.picture=coreUser.picture;
+                        }
+                        teacher.binds.Add(new ThirdBind { type=tokenId,userid=sso.userid,username=sso.name,account=sso.mobile,data=new List<string> { sso.ToJsonString() } });
+                        await _azureCosmos.GetCosmosClient().GetContainer(Constant.TEAMModelOS, Constant.Teacher).UpsertItemAsync(teacher, new PartitionKey("Base"));
+                    }
+                    else
+                    {
+                        status = 4;
+                    }
+                }
+                else
+                {
+                    status = 2;
+                    msg = "教师信息没有手机号";
+                }
+            }
+
+            if (status == 3)
+            {
+                var clientID = _configuration.GetValue<string>("HaBookAuth:CoreService:clientID");
+                var location = _option.Location;
+                implicit_token = await _coreAPIHttpService.Implicit(
+                    new Dictionary<string, string>()
+                    {
+                                    { "grant_type", "implicit" },
+                                    { "client_id",clientID },
+                                    { "account",teacher.id },
+                                    { "nonce",Guid.NewGuid().ToString()}
+                    }, location, _configuration);
+                if (implicit_token != null)
+                {
+                    if (string.IsNullOrWhiteSpace(implicit_token.id_token))
+                    {
+                        await _dingDing.SendBotMsg($"OS,隐式登录获得信息为空:{_option.Location}-\n{sso.ToJsonString()} \n\n{implicit_token.ToJsonString()}", GroupNames.醍摩豆服務運維群組);
+                        status = 6;
+                        msg = "隐式登录异常";
+                    }
+                    else
+                    {
+                        status = 200;
+                        msg = "登录成功";
+                        if (!string.IsNullOrWhiteSpace(authSchool))
+                        {
+                            //检查自动加入学校
+                            Azure.Response responseSchool = await _azureCosmos.GetCosmosClient().GetContainer(Constant.TEAMModelOS, "School").ReadItemStreamAsync(authSchool, new PartitionKey("Base"));
+                            if (responseSchool.Status == 200)
+                            {
+                                School school = JsonDocument.Parse(responseSchool.Content).RootElement.ToObject<School>();
+                                JwtSecurityToken jwt = new JwtSecurityToken(implicit_token.id_token);
+                                var id = jwt.Payload.Sub;
+                                jwt.Payload.TryGetValue("name", out object name);
+                                jwt.Payload.TryGetValue("picture", out object picture);
+                                JoinSchool(id, name?.ToString(), picture?.ToString(), school);
+                            }
+                        }
+                    }
+                }
+                else
+                {
+                    status = 6;
+                    msg = "隐式登录异常";
+                }
+            }
+            if (status == 200)
+            {
+                var content = new { grant_type = "code", client_id = "516148eb-6a38-4657-ba98-a3699061937f", nonce = Guid.NewGuid().ToString(), implicit_token.id_token };
+                var response = await _httpClientFactory.CreateClient().PostAsJsonAsync("https://api2.teammodel.cn/oauth2/login", content);
+                string code = string.Empty;
+                if (response.IsSuccessStatusCode)
+                {
+                    string jsonStr = await response.Content.ReadAsStringAsync();
+                    var json = jsonStr.ToObject<JsonElement>();
+                    if (json.TryGetProperty("code", out JsonElement _code))
+                    {
+                        code = _code.ToString();
+                    }
+                }
+                string callback = string.Empty;
+                if (sso.callback.Contains("https://www.habook.com.cn"))
+                {
+                    callback = $"https://account.teammodel.cn/?code={code}&callback=https%3A%2F%2Fwww.habook.com.cn%2F";
+                }
+                else if (sso.callback.Contains("https://www.teammodel.cn"))
+                {
+                    callback = $"https://www.teammodel.cn/login?code={code}&callback=https%3A%2F%2Fwww.teammodel.cn%2Flogin";
+                }
+                //rurl.Append($"?status={status}&msg={HttpUtility.UrlEncode(msg, Encoding.UTF8)}&callback={HttpUtility.UrlEncode(callback)}&id_token={implicit_token?.id_token}&access_token={implicit_token?.access_token}&expires_in={HttpUtility.UrlEncode(implicit_token?.expires_in)}&token_type={HttpUtility.UrlEncode(implicit_token?.token_type)}").ToString();
+
+               // rurl.Append($"?status={status}&msg={HttpUtility.UrlEncode(msg, Encoding.UTF8)}&callback={HttpUtility.UrlEncode(callback)}").ToString();
+               // return Ok(new { code = status, message = msg, data = rurl.ToString(),tmdid= teacher.id });
+                return Ok(new { code = status, message = msg, data = callback, tmdid = teacher.id });
+            }
+            else if (status == 4)
+            {
+                msg = $"教师账号:{sso.userid},{sso.mobile}未关联";
+                sso.mobile = "";
+                sso.school=authSchool;
+                rurl.Append($"?status={status}&msg={HttpUtility.UrlEncode(msg, Encoding.UTF8)}&param={HttpUtility.UrlEncode(sso.ToJsonString(), Encoding.UTF8)}&type={tokenId}&bindurl=business/bind");
+                return Ok(new { code = 4, message = msg, data = rurl.ToString() });
+            }
+            else
+            {
+                rurl.Append($"?status={status}&msg={HttpUtility.UrlEncode(msg, Encoding.UTF8)}");
+                return Ok(new { code = 400, message = msg, data = rurl.ToString() });
+
+            }
+        }
+        [HttpPost("bind")]
+        [AllowAnonymous]
+        //[ApiToken(Auth = "2201", Name = "醍摩豆账号绑定", TName = "醍摩豆账号绑定", EName = "醍摩豆账号绑定", RWN = "W", Limit = false)]
+        public async Task<IActionResult> Bind(BizBind bind)
+        {
+            string HostName = HttpContext.GetHostName();
+            if (!string.IsNullOrWhiteSpace(_option.HostName))
+            {
+                HostName = _option.HostName;
+            }
+            if (!_option.Location.Contains("Dep") && !_option.Location.Contains("Test"))
+            {
+                HostName = "www.teammodel.cn";
+            }
+            var rurl = new StringBuilder($"https://{HostName}/tmdid-sso");
+            try
+            {
+                TmdidImplicit tmdidImplicit = null;
+                int status = 0;
+                string msg = "账号未关联";
+                Teacher teacher = null;
+                BizSso sso = HttpUtility.UrlDecode(bind.param, Encoding.UTF8).ToObject<BizSso>();
+                if (!string.IsNullOrWhiteSpace(bind.mobile))
+                {
+                    var coreUser = await _coreAPIHttpService.GetUserInfo(new Dictionary<string, string> { { "key", bind.mobile } }, _option.Location, _configuration);
+                    if (coreUser != null)
+                    {
+                        var clientID = _configuration.GetValue<string>("HaBookAuth:CoreService:clientID");
+                        tmdidImplicit = await _coreAPIHttpService.Implicit(new Dictionary<string, string> {   { "grant_type", "implicit" },
+                                        { "client_id",clientID },
+                                        { "account",coreUser.id },
+                                        { "nonce",Guid.NewGuid().ToString()} }, _option.Location, _configuration);
+                        if (tmdidImplicit != null && !string.IsNullOrWhiteSpace(tmdidImplicit.id_token))
+                        {
+                            bind.id_token = tmdidImplicit.id_token;
+                        }
+                        else
+                        {
+                            status = 7;
+                        }
+                    }
+                    else
+                    {
+                        status = 7;
+
+                    }
+                }
+                if (string.IsNullOrWhiteSpace(bind.id_token))
+                {
+                    status = 7;
+                }
+                else
+                {
+                    JwtSecurityToken jwt = new JwtSecurityToken(bind.id_token);
+                    var id = jwt.Payload.Sub;
+                    CoreUser coreUserById = await _coreAPIHttpService.GetUserInfo(new Dictionary<string, string> { { "key", $"{id}" } }, _option.Location, _configuration);
+                    if (coreUserById == null || string.IsNullOrWhiteSpace(coreUserById.mobile) || coreUserById.mobile.Length != 11)
+                    {
+                        status = 7;
+                    }
+                    jwt.Payload.TryGetValue("name", out object name);
+                    jwt.Payload.TryGetValue("picture", out object picture);
+
+                    string sql = $"select value c from c  join b in c.binds where b.type='{bind.type}' and b.userid ='{sso.userid}'";
+                    var result = await _azureCosmos.GetCosmosClient().GetContainer(Constant.TEAMModelOS, Constant.Teacher).GetList<Teacher>(sql, "Base");
+                    List<Teacher> teachers = result.list;
+                    if (teachers.Any())
+                    {
+                        teacher = teachers.First();
+                    }
+                    else
+                    {
+                        //如果沒有,則初始化Teacher基本資料到Cosmos
+                        teacher = new Teacher
+                        {
+                            createTime = DateTimeOffset.UtcNow.ToUnixTimeMilliseconds(),
+                            pk = "Base",
+                            code = "Base",
+                            name = sso.name?.ToString(),
+                            picture = sso.picture?.ToString(),
+                            //创建账号并第一次登录IES5则默认赠送1G
+                            size = 1,
+                            defaultSchool = sso.school,
+                            schools = new List<TeacherSchool>(),
+                        };
+                        var response = await _azureCosmos.GetCosmosClient().GetContainer(Constant.TEAMModelOS, Constant.Teacher).ReadItemStreamAsync(coreUserById.id, new PartitionKey("Base"));
+                        if (response.Status==200)
+                        {
+                            teacher=JsonDocument.Parse(response.Content).RootElement.ToObject<Teacher>();
+                            teacher.defaultSchool=sso.school;
+                        }
+                        teacher.id = coreUserById.id;
+                        status = 3;//已关联
+                        msg = "账号已关联";
+                        if (string.IsNullOrWhiteSpace(teacher.name))
+                        {
+                            teacher.name=coreUserById.name;
+                        }
+                        if (string.IsNullOrWhiteSpace(teacher.picture))
+                        {
+                            teacher.picture=coreUserById.picture;
+                        }
+                        teacher.binds.Add(new ThirdBind { type=bind.type, userid=sso.userid, username=sso.name, account=sso.mobile, data=new List<string> { sso.ToJsonString() } });
+                        await _azureCosmos.GetCosmosClient().GetContainer(Constant.TEAMModelOS, Constant.Teacher).UpsertItemAsync(teacher, new PartitionKey("Base"));
+                    }
+                    if (!string.IsNullOrWhiteSpace(sso.school))
+                    {
+                        Azure.Response responseSchool = await _azureCosmos.GetCosmosClient().GetContainer(Constant.TEAMModelOS, "School").ReadItemStreamAsync(sso.school, new PartitionKey("Base"));
+                        if (responseSchool.Status == 200)
+                        {
+                            School school = JsonDocument.Parse(responseSchool.Content).RootElement.ToObject<School>();
+                            JoinSchool(id, name?.ToString(), picture?.ToString(), school);
+                        }
+                    }
+                    status = 200;
+                }
+                if (status == 200)
+                {
+                    var content = new { grant_type = "code", client_id = "516148eb-6a38-4657-ba98-a3699061937f", nonce = Guid.NewGuid().ToString(), bind.id_token };
+                    var response = await _httpClientFactory.CreateClient().PostAsJsonAsync("https://api2.teammodel.cn/oauth2/login", content);
+                    string code = string.Empty;
+                    if (response.IsSuccessStatusCode)
+                    {
+                        string jsonStr = await response.Content.ReadAsStringAsync();
+                        var json = jsonStr.ToObject<JsonElement>();
+                        if (json.TryGetProperty("code", out JsonElement _code))
+                        {
+                            code = _code.ToString();
+                        }
+                    }
+                    string callback = string.Empty;
+                    if (sso.callback.Contains("https://www.habook.com.cn"))
+                    {
+                        callback = $"https://account.teammodel.cn/?code={code}&callback=https%3A%2F%2Fwww.habook.com.cn%2F";
+                    }
+                    else if (sso.callback.Contains("https://www.teammodel.cn"))
+                    {
+                        callback = $"https://www.teammodel.cn/login?code={code}&callback=https%3A%2F%2Fwww.teammodel.cn%2Flogin";
+                    }
+                    // rurl.Append($"?status={status}&msg={HttpUtility.UrlEncode("登录成功", Encoding.UTF8)}&callback={callback}&id_token={implicit_token?.id_token}&access_token={implicit_token?.access_token}&expires_in={HttpUtility.UrlEncode(implicit_token?.expires_in)}&token_type={HttpUtility.UrlEncode(implicit_token?.token_type)}").ToString();
+                    // return Ok(new { url = rurl.ToString() });
+                    return Ok(new { url = callback });
+
+                }
+                else if (status == 7)
+                {
+                    msg = $"教师账号:{sso.userid},{sso.mobile}失败";
+                    rurl.Append($"?status={status}&msg={HttpUtility.UrlEncode(msg, Encoding.UTF8)}&param={HttpUtility.UrlEncode(sso.ToJsonString(), Encoding.UTF8)}");
+                    return Ok(new { url = rurl.ToString() });
+                }
+                else
+                {
+                    rurl.Append($"?status={7}&msg={HttpUtility.UrlEncode("账号未关联成功", Encoding.UTF8)}");
+                    return Ok(new { url = rurl.ToString() });
+                }
+            }
+            catch (Exception ex)
+            {
+                await _dingDing.SendBotMsg($"账号绑定账号异常,{ex.Message},{ex.StackTrace},\n{bind.ToJsonString()}", GroupNames.成都开发測試群組);
+
+            }
+            rurl.Append($"?status={7}&msg={HttpUtility.UrlEncode("账号未关联成功", Encoding.UTF8)}");
+            return Ok(new { url = rurl.ToString() });
+        }
+        [HttpPost("notify-bind")]
+        [AllowAnonymous]
+        [ApiToken(Auth = "2202", Name = "醍摩豆账号绑定通知", TName = "醍摩豆账号绑定通知", EName = "醍摩豆账号绑定", RWN = "N", Limit = false)]
+        public async Task<IActionResult> NotifyBind(BizBind bind)
+        {
+            return Ok(new {  });
+        }
+        private async void JoinSchool(string tmdid, string name, string picture, School school)
+        {
+            Teacher teacher = null;
+            Azure.Response responseTeacher = await _azureCosmos.GetCosmosClient().GetContainer(Constant.TEAMModelOS, "Teacher").ReadItemStreamAsync(tmdid, new PartitionKey("Base"));
+            if (responseTeacher.Status == 200)
+            {
+                teacher = JsonDocument.Parse(responseTeacher.Content).RootElement.ToObject<Teacher>();
+                var sc = teacher.schools.Find(z => z.schoolId.Equals(school.id));
+                if (sc == null)
+                {
+                    teacher.schools.Add(new TeacherSchool
+                    {
+                        schoolId = school.id,
+                        name = school.name,
+                        picture = school.picture,
+                        status = "join",
+                        time = DateTimeOffset.UtcNow.ToUnixTimeMilliseconds(),
+                        areaId = school.areaId
+                    });
+                    teacher.defaultSchool = school.id;
+                }
+            }
+            else
+            {
+                teacher = new Teacher
+                {
+                    createTime = DateTimeOffset.UtcNow.ToUnixTimeMilliseconds(),
+                    id = tmdid,
+                    pk = "Teacher",
+                    code = "Base",
+                    name = name,
+                    picture = picture?.ToString(),
+                    //创建账号并第一次登录IES5则默认赠送1G
+                    size = 1,
+                    defaultSchool = school.id,
+                    schools = new List<TeacherSchool>() { new TeacherSchool
+                    {
+                        schoolId=school.id,
+                        name=school.name,picture=school.picture,status="join",time=DateTimeOffset.UtcNow.ToUnixTimeMilliseconds(),areaId=school.areaId
+                    } },
+                };
+            }
+            await _azureCosmos.GetCosmosClient().GetContainer(Constant.TEAMModelOS, Constant.Teacher).UpsertItemAsync(teacher, new PartitionKey(teacher.code));
+            Azure.Response responseSchoolTeacher = await _azureCosmos.GetCosmosClient().GetContainer(Constant.TEAMModelOS, Constant.School).ReadItemStreamAsync(tmdid, new PartitionKey($"Teacher-{school.id}"));
+            if (responseSchoolTeacher.Status != 200)
+            {
+                SchoolTeacher schoolTeacher = new SchoolTeacher
+                {
+                    id = teacher.id,
+                    code = $"Teacher-{school.id}",
+                    roles = new List<string> { "teacher" },
+                    permissions = new List<string>(),
+                    pk = "Teacher",
+                    name = teacher.name,
+                    picture = teacher.picture,
+                    status = "join",
+                    createTime = DateTimeOffset.UtcNow.ToUnixTimeMilliseconds(),
+                    ttl = -1
+                };
+                await _azureCosmos.GetCosmosClient().GetContainer(Constant.TEAMModelOS, "School").UpsertItemAsync(schoolTeacher, new PartitionKey(schoolTeacher.code));
+            }
+            else
+            {
+                SchoolTeacher schoolTeacher = JsonDocument.Parse(responseSchoolTeacher.Content).RootElement.ToObject<SchoolTeacher>();
+                if (schoolTeacher != null)
+                {
+                    if (!schoolTeacher.roles.IsEmpty())
+                    {
+                        if (!schoolTeacher.roles.Contains("teacher"))
+                        {
+                            schoolTeacher.roles.Add("teacher");
+                        }
+                    }
+                    else
+                    {
+                        schoolTeacher.roles = new List<string> { "teacher" };
+                    }
+                    schoolTeacher.status = "join";
+                    schoolTeacher.pk = "Teacher";
+                    schoolTeacher.name = teacher.name;
+                    schoolTeacher.picture = teacher.picture;
+                    schoolTeacher.createTime = DateTimeOffset.UtcNow.ToUnixTimeMilliseconds();
+                    schoolTeacher.ttl = -1;
+                    schoolTeacher.permissions = schoolTeacher.permissions.IsNotEmpty() ? schoolTeacher.permissions : new List<string>();
+                    await _azureCosmos.GetCosmosClient().GetContainer(Constant.TEAMModelOS, "School").UpsertItemAsync(schoolTeacher, new PartitionKey(schoolTeacher.code));
+                }
+            }
+        }
+    }
+    public class BizBind
+    {
+        [Required(ErrorMessage = "{0} 必须填写")]
+        public string param { get; set; }
+        public string id_token { get; set; }
+        public string mobile { get; set; }
+        public string type { get; set; }
+    }
+
+    public class BizSso
+    {
+        /// <summary>
+        /// 必传
+        /// </summary>
+        public string userid { get; set; }
+        public string mobile { get; set; }
+        public string name { get; set; }
+        public string picture { get; set; }
+        public string callback { get; set; }
+        public string school { get; set; }
+        //https://www.teammodel.cn/login?code=Code8c8dfddd-e717-4a2a-ac83-88f480303d80&callback=https%3A%2F%2Fwww.habook.com.cn%2F
+        //https://account.teammodel.cn/?code=Code19695116-fe51-4c3f-9172-7a6ab9f69523&callback=https%3A%2F%2Fwww.habook.com.cn%2F
+    }
+}

+ 1 - 1
TEAMModelOS/appsettings.Development.json

@@ -10,7 +10,7 @@
   "Option": {
     "Location": "China-Dep",
     "LocationNum": "1",
-    "HostName": "test.teammodel.cn",
+    "HostName": "localhost:5001",
     "AllowedHosts": [ "localhost", "*.teammodel.cn", "*.teammodel.net", "*.habookaclass.biz", "test" ],
     "Issuer": "www.teammodel.cn",
     "JwtSecretKey": "fXO6ko/qyXeYrkecPeKdgXnuLXf9vMEtnBC9OB3s+aA=",