HiITEdenX 2 năm trước cách đây
mục cha
commit
9c5e702cb9

+ 1 - 1
TEAMModelOS.FunctionV4/ServiceBus/ActiveTaskTopic.cs

@@ -2219,7 +2219,7 @@ namespace TEAMModelOS.FunctionV4.ServiceBus
         {
             try
             {
-                await _dingDing.SendBotMsg($"IES5,{_option.Location},Imei AF call\n{msg.ToJsonString()}", GroupNames.成都开发測試群組);
+                //await _dingDing.SendBotMsg($"IES5,{Environment.GetEnvironmentVariable("Option:Location")},Imei AF call\n{msg.ToJsonString()}", GroupNames.成都开发測試群組);
                 using var json = JsonDocument.Parse(msg);
                 if (json.RootElement.TryGetProperty("channel", out JsonElement channel) &&
                     json.RootElement.TryGetProperty("userid", out JsonElement userid) &&

+ 60 - 1
TEAMModelOS.SDK/DI/CoreAPI/CoreAPIHttpService.cs

@@ -68,6 +68,65 @@ namespace TEAMModelOS.SDK
             //_dingDing = dingDing;
 
         }
+
+        public class CoreAPIToken { 
+            public string id_token { get; set; }
+            public string access_token { get; set; }
+            public string expires_in { get; set; }
+            public string token_type { get; set; }
+        }
+
+        public async Task<(HttpStatusCode code , CoreAPIToken token )> GetCoreAPIoAuth2Token(Dictionary<string,object> data, string location, IConfiguration _configuration, DI.DingDing _dingDing) {
+            try
+            {
+                var url = _configuration.GetValue<string>("HaBookAuth:CoreAPI");
+                //url = "https://api2-rc.teammodel.cn";
+                url = $"{url}/service/sandsms/pin";
+                var clientID = _configuration.GetValue<string>("HaBookAuth:CoreService:clientID");
+                var clientSecret = _configuration.GetValue<string>("HaBookAuth:CoreService:clientSecret");
+                if (location.Contains("China"))
+                {
+                    location = "China";
+                }
+                else if (location.Contains("Global"))
+                {
+                    location = "Global";
+                }
+                var token = await CoreTokenExtensions.CreateAccessToken(clientID, clientSecret, location);
+                if (_httpClient.DefaultRequestHeaders.Contains("Authorization"))
+                {
+                    _httpClient.DefaultRequestHeaders.Remove("Authorization");
+                }
+                _httpClient.DefaultRequestHeaders.Add("Authorization", $"Bearer {token.AccessToken}");
+                HttpResponseMessage responseMessage = await _httpClient.PostAsJsonAsync(url, data);
+                if (responseMessage.Content != null)
+                {
+                    string content = await responseMessage.Content.ReadAsStringAsync();
+                    if (!string.IsNullOrWhiteSpace(content))
+                    {
+                        CoreAPIToken coreAPI = content.ToObject<CoreAPIToken>();
+                        return (responseMessage.StatusCode, coreAPI);
+                    }
+                    else
+                    {
+                        return (responseMessage.StatusCode, null);
+                    }
+                }
+                else
+                {
+                    return (responseMessage.StatusCode, null);
+                }
+
+
+            }
+            catch (Exception ex)
+            {
+                await _dingDing.SendBotMsg($"{location}验证码发送异常:\n{ex.Message}\n{ex.StackTrace}", DI.GroupNames.醍摩豆服務運維群組);
+                return (HttpStatusCode.InternalServerError, null);
+            }
+
+        }
+
         /*
         hubName	string	Optional	指定要傳送到哪個訊息中樞,若沒給則不傳送端外通知,只會發送端內通知。(目前只有"hita"及"hita5"能使用)
         sender	string	Optional	發送訊息的來源端
@@ -204,7 +263,7 @@ namespace TEAMModelOS.SDK
                                 {
                                     urlAction = "https://test.teammodel.cn/core/process-notify";
                                 }
-                                byte[] byts = Encoding.Unicode.GetBytes(replaceData.ToJsonString());
+                                byte[] byts = Encoding.Default.GetBytes(replaceData.ToJsonString());
                                 var  rdata=Convert.ToBase64String(byts);
                                 urlAction = $"{urlAction}?notifyCode={notifyCode}&data={rdata}";
                                 if (msgs.Count == 3)

+ 158 - 8
TEAMModelOS/Controllers/System/CoreController.cs

@@ -4,6 +4,7 @@ using Microsoft.AspNetCore.Http;
 using Microsoft.AspNetCore.Mvc;
 using Microsoft.Extensions.Configuration;
 using Microsoft.Extensions.Options;
+using Microsoft.OData.UriParser;
 using StackExchange.Redis;
 using System;
 using System.Collections.Generic;
@@ -15,6 +16,7 @@ using System.Net;
 using System.Net.Http;
 using System.Reflection;
 using System.Runtime.InteropServices;
+using System.Security.Policy;
 using System.Text;
 using System.Text.Json;
 using System.Text.RegularExpressions;
@@ -27,6 +29,8 @@ using TEAMModelOS.SDK.Extension;
 using TEAMModelOS.SDK.Models;
 using TEAMModelOS.SDK.Models.Service;
 using TEAMModelOS.SDK.PngQuant;
+using Top.Api;
+using static TEAMModelOS.SDK.CoreAPIHttpService;
 
 namespace TEAMModelOS.Controllers
 {
@@ -34,6 +38,7 @@ namespace TEAMModelOS.Controllers
     [ApiController]
     public class CoreController : ControllerBase
     {
+        private readonly AzureCosmosFactory _azureCosmos;
         private readonly AzureRedisFactory _azureRedis;
         private readonly AzureStorageFactory _azureStorage;
         private readonly DingDing _dingDing;
@@ -43,8 +48,9 @@ namespace TEAMModelOS.Controllers
         private readonly CoreAPIHttpService _coreAPIHttpService;
         private readonly IConfiguration _configuration;
         private readonly SnowflakeId _snowflakeId;
-        public CoreController(SnowflakeId snowflakeId,CoreAPIHttpService coreAPIHttpService,IConfiguration configuration,IPSearcher searcher, AzureRedisFactory azureRedis, AzureStorageFactory azureStorage, DingDing dingDing, IOptionsSnapshot<Option> option, HttpClient httpClient)
+        public CoreController(AzureCosmosFactory azureCosmos, SnowflakeId snowflakeId,CoreAPIHttpService coreAPIHttpService,IConfiguration configuration,IPSearcher searcher, AzureRedisFactory azureRedis, AzureStorageFactory azureStorage, DingDing dingDing, IOptionsSnapshot<Option> option, HttpClient httpClient)
         {
+            _azureCosmos = azureCosmos;
             _searcher = searcher;
             _azureStorage = azureStorage;
             _dingDing = dingDing;
@@ -64,14 +70,158 @@ namespace TEAMModelOS.Controllers
         }
         [HttpGet("process-notify")]
         public async Task<IActionResult> ProcessNotify([FromQuery] NotifyData notifyData) {
-            await  _dingDing.SendBotMsg($"{notifyData.ToJsonString()}", GroupNames.成都开发測試群組);
-            switch (true) {
-                case bool when $"{notifyData.notifyCode}".Equals("request_school"):
-                    break;
-                case bool when $"{notifyData.notifyCode}".Equals("invite_school"):
-                    break;
+            string msg = "";
+            /// code =-1 参数异常,0 凭据失效 1不是管理员,2操作成功,3服务端异常
+            int code = -1;
+            try {
+                //await _dingDing.SendBotMsg($"{notifyData.ToJsonString()}", GroupNames.成都开发測試群組);
+                string opttmdid = "";
+                if (!string.IsNullOrWhiteSpace(notifyData.ticket))
+                {
+                    var clientID = _configuration.GetValue<string>("HaBookAuth:CoreService:clientID");
+                    (HttpStatusCode statusCode, CoreAPIToken token) = await _coreAPIHttpService.GetCoreAPIoAuth2Token(
+                         new Dictionary<string, object> { { "client_id", clientID }, { "grant_type", "authorization_code" }, { "code", notifyData.ticket } }, _option.Location, _configuration, _dingDing);
+                    if (statusCode.Equals(HttpStatusCode.OK))
+                    {
+                        var jwt = new JwtSecurityToken(token.id_token);
+                        opttmdid = jwt.Payload.Sub;
+                    }
+                    else {
+                        code = 0;
+                        msg = "凭据失效";
+                    }
+                }
+                else {
+                    code = -1;
+                    msg = "凭据参数异常";
+                }
+                var dataByte = Convert.FromBase64String(notifyData.data);
+                string data = Encoding.Default.GetString(dataByte);
+                Dictionary<string, object> dict = data.ToObject<Dictionary<string, object>>();
+                dict.TryGetValue("schoolId", out object _schoolId);
+                dict.TryGetValue("tmdid", out object _tmdid);
+                if (!string.IsNullOrWhiteSpace($"{_schoolId}") && !string.IsNullOrWhiteSpace($"{_tmdid}") && string.IsNullOrWhiteSpace(opttmdid))
+                {
+                    switch (true)
+                    {
+                        case bool when $"{notifyData.notifyCode}".Equals("request_school"):
+                            {
+                                Azure.Response adminResponse = await _azureCosmos.GetCosmosClient().GetContainer(Constant.TEAMModelOS, Constant.School)
+                                .ReadItemStreamAsync(opttmdid, new Azure.Cosmos.PartitionKey($"Teacher-{_schoolId}"));
+                                //是否是管理员
+                                if (adminResponse.Status == 200)
+                                {
+                                    var adminTeacher = JsonDocument.Parse(adminResponse.Content).RootElement.Deserialize<SchoolTeacher>();
+                                    if (adminTeacher.roles.Contains("admin"))
+                                    {
+                                        Azure.Response teacherResponse = await _azureCosmos.GetCosmosClient().GetContainer(Constant.TEAMModelOS, Constant.Teacher)
+                                        .ReadItemStreamAsync($"{_tmdid}", new Azure.Cosmos.PartitionKey("Base"));
+                                        Azure.Response schoolTeacherResponse = await _azureCosmos.GetCosmosClient().GetContainer(Constant.TEAMModelOS, Constant.School)
+                                               .ReadItemStreamAsync($"{_tmdid}", new Azure.Cosmos.PartitionKey($"Teacher-{_schoolId}"));
+                                        if (teacherResponse.Status == 200 && schoolTeacherResponse.Status == 200)
+                                        {
+                                            var teacher = JsonDocument.Parse(teacherResponse.Content).RootElement.Deserialize<Teacher>();
+                                            var schoolTeacher = JsonDocument.Parse(teacherResponse.Content).RootElement.Deserialize<SchoolTeacher>();
+                                            //同意
+                                            if (notifyData.notifyEvent == 1)
+                                            {
+                                                teacher.schools.ForEach(school =>
+                                                {
+                                                    if (school.schoolId.Equals($"{_schoolId}"))
+                                                    {
+                                                        school.status = "join";
+                                                    }
+                                                });
+                                                schoolTeacher.status = "join";
+                                                await _azureCosmos.GetCosmosClient().GetContainer(Constant.TEAMModelOS, Constant.School).ReplaceItemAsync(schoolTeacher, schoolTeacher.id, new Azure.Cosmos.PartitionKey(schoolTeacher.code));
+                                            }
+                                            //拒绝
+                                            if (notifyData.notifyEvent == 2)
+                                            {
+                                                //只有在未正式加入成功才能拒绝成功,防止HiTA消息未清除,再次操作。
+                                                teacher.schools.RemoveAll(z => z.schoolId.Equals($"{_schoolId}") && (z.status.Equals("request") || z.status.Equals("invite")));
+                                            }
+                                            await _azureCosmos.GetCosmosClient().GetContainer(Constant.TEAMModelOS, Constant.Teacher).ReplaceItemAsync(teacher, teacher.id, new Azure.Cosmos.PartitionKey(teacher.code));
+                                            code = 2;
+                                            msg = "操作成功";
+                                        }
+                                        else
+                                        {
+                                            code = -1;
+                                            msg = "教师不存在";
+                                        }
+
+                                    }
+                                    else
+                                    {
+                                        code = 1;
+                                        msg = "不是管理员";
+                                    }
+                                }
+                                else
+                                {
+                                    code = -1;
+                                    msg = "管理员不存在";
+                                }
+                            }
+                            break;
+                        case bool when $"{notifyData.notifyCode}".Equals("invite_school"):
+                            {
+                                Azure.Response teacherResponse = await _azureCosmos.GetCosmosClient().GetContainer(Constant.TEAMModelOS, Constant.Teacher)
+                                   .ReadItemStreamAsync($"{opttmdid}", new Azure.Cosmos.PartitionKey("Base"));
+                                Azure.Response schoolTeacherResponse = await _azureCosmos.GetCosmosClient().GetContainer(Constant.TEAMModelOS, Constant.School)
+                                       .ReadItemStreamAsync($"{opttmdid}", new Azure.Cosmos.PartitionKey($"Teacher-{_schoolId}"));
+                                if (teacherResponse.Status == 200 && schoolTeacherResponse.Status == 200)
+                                {
+                                    var teacher = JsonDocument.Parse(teacherResponse.Content).RootElement.Deserialize<Teacher>();
+                                    var schoolTeacher = JsonDocument.Parse(teacherResponse.Content).RootElement.Deserialize<SchoolTeacher>();
+                                    //同意
+                                    if (notifyData.notifyEvent == 1)
+                                    {
+                                        teacher.schools.ForEach(school =>
+                                        {
+                                            if (school.schoolId.Equals($"{_schoolId}"))
+                                            {
+                                                school.status = "join";
+                                            }
+                                        });
+                                        schoolTeacher.status = "join";
+                                        await _azureCosmos.GetCosmosClient().GetContainer(Constant.TEAMModelOS, Constant.School).ReplaceItemAsync(schoolTeacher, schoolTeacher.id, new Azure.Cosmos.PartitionKey(schoolTeacher.code));
+                                    }
+                                    //拒绝
+                                    if (notifyData.notifyEvent == 2)
+                                    {
+                                        //只有在未正式加入成功才能拒绝成功,防止HiTA消息未清除,再次操作。
+                                        teacher.schools.RemoveAll(z => z.schoolId.Equals($"{_schoolId}") && (z.status.Equals("request") || z.status.Equals("invite")));
+                                        await _azureCosmos.GetCosmosClient().GetContainer(Constant.TEAMModelOS, Constant.School).DeleteItemStreamAsync($"{opttmdid}", new Azure.Cosmos.PartitionKey($"Teacher-{_schoolId}"));
+                                    }
+                                    await _azureCosmos.GetCosmosClient().GetContainer(Constant.TEAMModelOS, Constant.Teacher).ReplaceItemAsync(teacher, teacher.id, new Azure.Cosmos.PartitionKey(teacher.code));
+                                    code = 2;
+                                    msg = "操作成功";
+                                }
+                                else
+                                {
+                                    code = -1;
+                                    msg = "教师不存在";
+                                }
+                            }
+                            break;
+                    }
+                }
+                else
+                {
+                    code = -1;
+                    msg = "参数异常";
+                }
+            } catch (Exception ex) {
+                await _dingDing.SendBotMsg($"{ex.Message}\n{ex.StackTrace}", GroupNames.醍摩豆服務運維群組);
+                code = 3;
+                msg = "服务端异常";
             }
-            return Ok();
+            string HostName = HttpContext.GetHostName();
+            var rurl = $"https://{HostName}/feedback?code={code}&msg={msg}";
+            return Redirect(rurl);
+            //return Ok(new { code,msg});
         }
         [HttpPost("sendsms/pin")]
         public async Task<IActionResult> SendSmsPinCode(JsonElement request)