Parcourir la source

HiTA接口。

CrazyIter_Bin il y a 3 ans
Parent
commit
1fd917de3a

+ 4 - 0
TEAMModelOS.SDK/Models/Service/Common/TeacherService.cs

@@ -29,6 +29,10 @@ namespace TEAMModelOS.Services
 {
     public static class TeacherService
     {
+
+
+        
+
         public static async Task<TeacherInfo> GetTeacherInfo (AzureCosmosFactory _azureCosmos,Teacher teacher,string name,string picture,string id , AzureStorageFactory _azureStorage, Option _option)
         {
             List<object> schools = new List<object>();

+ 3 - 3
TEAMModelOS/Controllers/Client/HiTAControlller.cs

@@ -55,7 +55,7 @@ namespace TEAMModelOS.Controllers.Client
             public string id{ get; set; }
             [Required(ErrorMessage = "{0} 必须填写")]
             public string name { get; set; }
-            [Required(ErrorMessage = "{0} 必须填写")]
+            //[Required(ErrorMessage = "{0} 必须填写")]
             public string pic { get; set; }
             [Required(ErrorMessage = "{0} 必须填写")]
             public string school { get; set; }
@@ -69,7 +69,7 @@ namespace TEAMModelOS.Controllers.Client
         /// <returns></returns>
         [ProducesDefaultResponseType]
         [HttpGet("join-school")]
-        [Authorize(Roles = "HiTA")]
+        //[Authorize(Roles = "HiTA")]
         public async Task<IActionResult> ScanCodeJoinSchool([FromQuery] HiTAJoinSchool join) {
             string school=join.school;
             string id = join.id;
@@ -167,7 +167,7 @@ namespace TEAMModelOS.Controllers.Client
                 schoolTeacher.picture = schoolInfo.picture;
                 await _azureCosmos.GetCosmosClient().GetContainer(Constant.TEAMModelOS, "School").ReplaceItemAsync<SchoolTeacher>(schoolTeacher, schoolTeacher.id, new PartitionKey($"Teacher-{ schoolInfo.id }"));
             }
-            return Ok(new {  schoolTeacher.name, schoolTeacher.picture, school=$"{school}"});
+            return Ok(new { schoolTeacher.roles, schoolTeacher.status,   school =$"{school}",   schoolInfo.name,   schoolInfo.picture });
         }
 
         //[Authorize(Roles = "HiTA")]

+ 0 - 1
TEAMModelOS/Controllers/Student/StudentController.cs

@@ -60,7 +60,6 @@ namespace TEAMModelOS.Controllers
         /// <returns></returns>
         [HttpPost("student-manage")]
         [Authorize(Roles = "IES")]
-
         [AuthToken(Roles = "admin,student,teacher")]
         public async Task<IActionResult> StudentManage(JsonElement request)
         {

+ 360 - 0
TEAMModelOS/Controllers/Teacher/TeacherInitController.cs

@@ -0,0 +1,360 @@
+using Azure.Cosmos;
+using Azure.Storage.Blobs.Models;
+using Azure.Storage.Sas;
+using Microsoft.AspNetCore.Http;
+using Microsoft.AspNetCore.Mvc;
+using Microsoft.Extensions.Options;
+using System;
+using System.Collections.Generic;
+using System.Dynamic;
+using System.IdentityModel.Tokens.Jwt;
+using System.IO;
+using System.Linq;
+using System.Text.Json;
+using System.Threading.Tasks;
+using TEAMModelOS.Models;
+using TEAMModelOS.SDK.Models;
+using TEAMModelOS.SDK.DI;
+using TEAMModelOS.SDK.Extension;
+using TEAMModelOS.Filter;
+using TEAMModelOS.SDK.Models.Cosmos;
+using HTEXLib.COMM.Helpers;
+using TEAMModelOS.SDK.Models.Service;
+using Microsoft.Extensions.Configuration;
+using System.Net.Http;
+using TEAMModelOS.SDK;
+using static TEAMModelOS.SDK.Models.Teacher;
+using TEAMModelOS.Services;
+using Microsoft.AspNetCore.Authorization;
+
+namespace TEAMModelOS.Controllers
+{
+    [ProducesResponseType(StatusCodes.Status200OK)]
+    [ProducesResponseType(StatusCodes.Status400BadRequest)]
+
+    [Route("teacher-init")]
+    [ApiController]
+    public class TeacherInitController : ControllerBase
+    {
+        private readonly AzureCosmosFactory _azureCosmos;
+        private readonly AzureStorageFactory _azureStorage;
+        private readonly DingDing _dingDing;
+        private readonly Option _option;
+        private readonly IConfiguration _configuration;
+        private readonly NotificationService _notificationService;
+        private readonly CoreAPIHttpService _coreAPIHttpService;
+        public TeacherInitController(CoreAPIHttpService coreAPIHttpService, AzureCosmosFactory azureCosmos, AzureStorageFactory azureStorage, DingDing dingDing, IOptionsSnapshot<Option> option, IConfiguration configuration, NotificationService notificationService)
+        {
+            _azureCosmos = azureCosmos;
+            _azureStorage = azureStorage;
+            _dingDing = dingDing;
+            _option = option?.Value;
+            _configuration = configuration;
+            _notificationService = notificationService;
+            _coreAPIHttpService = coreAPIHttpService;
+        }
+        //TODO 此API需處理對應前端返回的相關數據
+        [ProducesDefaultResponseType]
+        [Authorize(Roles = "IES")]
+        [HttpPost("get-teacher-info")]
+        public async Task<IActionResult> GetTeacherInfo(JsonElement request)
+        {
+            try
+            {
+                if (!request.TryGetProperty("id_token", out JsonElement id_token)) return BadRequest();
+                var jwt = new JwtSecurityToken(id_token.GetString());
+                //TODO 此驗證IdToken先簡單檢查,後面需向Core ID新API,驗證Token
+                var id = jwt.Payload.Sub;
+                jwt.Payload.TryGetValue("name", out object name);
+                jwt.Payload.TryGetValue("picture", out object picture);
+                Teacher teacher = null;
+                TeacherInfo teacherInfo = await TeacherInfo(_azureCosmos, teacher, $"{name}", $"{picture}", id, _azureStorage, _option);
+                return Ok(new
+                {
+                    location = _option.Location,
+                    teacherInfo.auth_token,
+                    teacherInfo.blob_uri,
+                    teacherInfo.blob_sas,
+                    teacherInfo.schools,
+                    teacherInfo.defaultschool,
+                    teacherInfo.courses,
+                    teacherInfo.total,
+                    teacherInfo.osblob_uri,
+                    teacherInfo.osblob_sas,
+                    teacherInfo.tsize,
+                    status = 200,
+                    teacherInfo.areas
+                });
+            }
+            catch (CosmosException ex)
+            {
+                await _dingDing.SendBotMsg($"IES5,{_option.Location},Teacher/GetTeacherInfo()\n{ex.Message}{ex.StackTrace}", GroupNames.醍摩豆服務運維群組);
+                return BadRequest();
+            }
+            catch (Exception ex)
+            {
+                await _dingDing.SendBotMsg($"IES5,{_option.Location},Teacher/GetTeacherInfo()\n{ex.Message}{ex.StackTrace}", GroupNames.醍摩豆服務運維群組);
+                return BadRequest();
+            }
+        }
+
+        public static async Task<TeacherInfo> TeacherInfo(AzureCosmosFactory _azureCosmos, Teacher teacher, string name, string picture, string id, AzureStorageFactory _azureStorage, Option _option)
+        {
+            List<object> schools = new List<object>();
+            List<AreaDto> areas = new List<AreaDto>();
+            List<Area> areasd = new List<Area>();
+            string defaultschool = null;
+            //TODO 取得Teacher 個人相關數據(課程清單、虛擬教室清單、歷史紀錄清單等),學校數據另外API處理,多校切換時不同
+            var client = _azureCosmos.GetCosmosClient();
+            int total = 0;
+            int tsize = 0;
+            try
+            {
+                if (teacher == null)
+                {
+                    teacher = await client.GetContainer(Constant.TEAMModelOS, "Teacher").ReadItemAsync<Teacher>(id, new PartitionKey("Base"));
+                    teacher.name = $"{name}";
+                    teacher.picture = $"{picture}";
+                }
+                else
+                {
+                    name = teacher.name;
+                    picture = teacher.picture;
+                    id = teacher.id;
+                }
+                ///教师的个人空间
+                tsize = teacher.size;
+                ///教师的总空间 包含 个人空间和学校赠送的空间累加
+                total = teacher.size;
+                //areas = teacher.areas;
+                if (teacher.areas.IsNotEmpty())
+                {
+                    //teacher.areas.Select(x => x.areaId);
+                    //await foreach (var item    client.GetContainer(Constant.TEAMModelOS, "Normal").GetItemQueryIterator<Area>($"{areat.areaId}", new PartitionKey("Base-Area"))) { 
+
+                    //}
+                    //https://test.teammodel.cn/hita/join-school?ts=1644291704907&school=cdxcwgy
+                    foreach (var areat in teacher.areas)
+                    {
+                        try
+                        {
+                            Area area = await client.GetContainer(Constant.TEAMModelOS, "Normal").ReadItemAsync<Area>($"{areat.areaId}", new PartitionKey("Base-Area"));
+                            areasd.Add(area);
+                            AreaSetting setting = null;
+                            try
+                            {
+                                setting = await client.GetContainer(Constant.TEAMModelOS, "Normal").ReadItemAsync<AreaSetting>($"{areat.areaId}", new PartitionKey("AreaSetting"));
+                            }
+                            catch (CosmosException ex)
+                            {
+                                setting = null;
+                            }
+                            int access = 0;
+                            if (setting != null && !string.IsNullOrWhiteSpace(setting.accessConfig))
+                            {
+                                access = 1;
+                            }
+                            if (setting != null)
+                            {
+                                setting.accessConfig = null;
+                            }
+                            areas.Add(new AreaDto { areaId = area.id, name = area.name, standard = area.standard, standardName = area.standardName, setting = setting, access = access });
+                        }
+                        catch (CosmosException)
+                        {
+                            //数据库捞不到数据
+                            continue;
+                        }
+                    }
+                }
+                //检查是否有加入学校,如果加入学校,则当个人空间size是0G的时候,则免费获得一个G空间,但无论加入多少个学校,只能获取一次 1G的免费空间。没有加入学校则默认0G空间,除非自己购买空间
+                if (teacher.schools.IsNotEmpty())
+                {
+                    foreach (var sc in teacher.schools)
+                    {
+                        string statusNow = sc.status != null ? sc.status : "";
+                        if (statusNow.Equals("join") || statusNow.Equals("invite") || statusNow.Equals("request"))
+                        {
+                            dynamic schoolExtobj = new ExpandoObject();
+                            // var schoolJson = await client.GetContainer(Constant.TEAMModelOS, "School").ReadItemStreamAsync($"{sc.schoolId}", new PartitionKey("Base"));
+                            //var school = await JsonDocument.ParseAsync(schoolJson.ContentStream);
+                            schoolExtobj.schoolId = sc.schoolId;
+                            schoolExtobj.name = sc.name;
+                            schoolExtobj.status = sc.status;
+                            schoolExtobj.time = sc.time;
+                            schoolExtobj.picture = sc.picture;
+                            schoolExtobj.areaId = $"{sc.areaId}";
+                            Area area = null;
+                            int access = 0;
+                            if (!string.IsNullOrEmpty($"{sc.areaId}"))
+                            {
+
+                                try
+                                {
+
+                                    area = await client.GetContainer(Constant.TEAMModelOS, "Normal").ReadItemAsync<Area>($"{sc.areaId}", new PartitionKey("Base-Area"));
+                                    AreaSetting setting = null;
+                                    try
+                                    {
+                                        setting = await client.GetContainer(Constant.TEAMModelOS, "Normal").ReadItemAsync<AreaSetting>($"{area.id}", new PartitionKey("AreaSetting"));
+                                    }
+                                    catch (CosmosException ex)
+                                    {
+                                        setting = null;
+                                    }
+
+                                    if (setting != null && !string.IsNullOrWhiteSpace(setting.accessConfig))
+                                    {
+                                        access = 1;
+                                    }
+                                    areasd.Add(area);
+
+                                }
+                                catch (CosmosException)
+                                {
+                                    area = null;
+                                }
+                            }
+                            if (area != null)
+                            {
+                                schoolExtobj.area = new { area.name, area.id, area.institution, area.provName, area.code, area.cityCode, area.cityName, area.standard, area.provCode, area.pk, access };
+
+                            }
+                            else
+                            {
+                                schoolExtobj.area = area;
+                            }
+                            var sctch = await client.GetContainer(Constant.TEAMModelOS, "School").ReadItemStreamAsync(id, new PartitionKey($"Teacher-{sc.schoolId}"));
+                            if (sctch.Status == 200)
+                            {
+                                var jsonDoc = await JsonDocument.ParseAsync(sctch.ContentStream);
+                                SchoolTeacher schoolTeacher = jsonDoc.RootElement.ToObject<SchoolTeacher>();
+                                schoolTeacher.name = $"{name}";
+                                schoolTeacher.picture = $"{picture}";
+                                await client.GetContainer(Constant.TEAMModelOS, "School").ReplaceItemAsync(schoolTeacher, id, new PartitionKey($"Teacher-{sc.schoolId}"));
+                                if (jsonDoc.RootElement.TryGetProperty("size", out JsonElement _size) && _size.ValueKind.Equals(JsonValueKind.Number))
+                                {
+                                    total += _size.GetInt32();
+                                    schoolExtobj.size = _size.GetInt32();
+                                }
+                                else { schoolExtobj.size = 0; }
+                            }
+                            else
+                            {
+                                schoolExtobj.size = 0;
+                            }
+                            if (statusNow.Equals("join"))
+                            {
+                                //初始化
+                                await TmdUserService.JoinSchool(client, teacher.id, teacher.picture, teacher.name, sc.schoolId, sc.name);
+                            }
+                            schools.Add(schoolExtobj);
+                        }
+                    }
+                    //如果包含任何申请,邀请,加入学校的记录 且个人空间未分配2G  则默认分配个人空间至2G.
+                    if (teacher.size < 2 && teacher.schools.Count > 0)
+                    {
+                        teacher.size = 2;
+                    }
+                    //如果未包含任何申请,邀请,加入学校的记录 且 个人空间没有分配1G 则默认赠送一个G 
+                    if (teacher.schools.Count == 0 && teacher.size < 1)
+                    {
+                        teacher.size = 1;
+                    }
+                }
+                if (string.IsNullOrEmpty(teacher.defaultSchool) && teacher.schools.IsNotEmpty())
+                {
+                    var tech = teacher.schools.FindAll(x => x.status.Equals("join"));
+                    if (tech.IsNotEmpty())
+                    {
+                        teacher.defaultSchool = teacher.schools[0].schoolId;
+                    }
+                }
+                await client.GetContainer(Constant.TEAMModelOS, "Teacher").ReplaceItemAsync<Teacher>(teacher, id, new PartitionKey("Base"));
+                //預設學校ID
+                defaultschool = teacher.defaultSchool;
+            }
+            catch (CosmosException ex)
+            {
+                if (ex.Status == 404)
+                {
+                    //如果沒有,則初始化Teacher基本資料到Cosmos
+                    teacher = new Teacher
+                    {
+                        id = id,
+                        pk = "Base",
+                        code = "Base",
+                        name = name?.ToString(),
+                        picture = picture?.ToString(),
+                        //创建账号并第一次登录IES5则默认赠送1G
+                        size = 1,
+                        defaultSchool = null,
+                        schools = new List<Teacher.TeacherSchool>(),
+                    };
+                    var container = _azureStorage.GetBlobContainerClient(id);
+                    await container.CreateIfNotExistsAsync(PublicAccessType.None); //嘗試創建Teacher私有容器,如存在則不做任何事,保障容器一定存在
+                    teacher = await _azureCosmos.GetCosmosClient().GetContainer(Constant.TEAMModelOS, "Teacher").CreateItemAsync<Teacher>(teacher, new PartitionKey("Base"));
+                    total = teacher.size;
+                    tsize = teacher.size;
+                }
+            }
+            catch (Exception ex) {
+                throw new Exception($"{ex.Message}{ex.StackTrace}");
+            }
+            //私人課程
+            List<object> courses = new List<object>();
+            await foreach (var item in client.GetContainer(Constant.TEAMModelOS, "Teacher").GetItemQueryStreamIterator(queryText: $"select value(c) from c ", requestOptions: new QueryRequestOptions() { PartitionKey = new PartitionKey($"Course-{id}") }))
+            {
+                using var json = await JsonDocument.ParseAsync(item.ContentStream);
+                if (json.RootElement.TryGetProperty("_count", out JsonElement count) && count.GetUInt16() > 0)
+                {
+                    foreach (var obj in json.RootElement.GetProperty("Documents").EnumerateArray())
+                    {
+                        courses.Add(obj.ToObject<object>());
+                    }
+                }
+            }
+
+
+            List<string> roles = new List<string>() { "teacher" };
+            Area areaa = null;
+            if (areas.Count > 0)
+            {
+                roles.Add("area");
+                if (!string.IsNullOrEmpty($"{areas[0]}"))
+                {
+
+                    try
+                    {
+                        areaa = await client.GetContainer(Constant.TEAMModelOS, "Normal").ReadItemAsync<Area>($"{areas[0].areaId}", new PartitionKey("Base-Area"));
+                    }
+                    catch (CosmosException)
+                    {
+                        areaa = null;
+                    }
+                }
+            }
+            //換取AuthToken,提供給前端
+            var auth_token = JwtAuthExtension.CreateAuthToken(_option.HostName, id, name?.ToString(), picture?.ToString(), _option.JwtSecretKey, Website: "IES", scope: Constant.ScopeTeacher, standard: areaa != null ? areaa.standard : "", roles: roles.ToArray());
+            //取得Teacher Blob 容器位置及SAS 
+            await _azureStorage.GetBlobContainerClient(id).CreateIfNotExistsAsync(PublicAccessType.None); //嘗試創建Teacher私有容器,如存在則不做任何事,保障容器一定存在
+            var (blob_uri, blob_sas) = _azureStorage.GetBlobContainerSAS(id, BlobContainerSasPermissions.Write | BlobContainerSasPermissions.Read | BlobContainerSasPermissions.List | BlobContainerSasPermissions.Delete);
+            var (osblob_uri, osblob_sas) = roles.Contains("area") ? _azureStorage.GetBlobContainerSAS("teammodelos", BlobContainerSasPermissions.Write | BlobContainerSasPermissions.Read | BlobContainerSasPermissions.List | BlobContainerSasPermissions.Delete) : _azureStorage.GetBlobContainerSAS("teammodelos", BlobContainerSasPermissions.Read | BlobContainerSasPermissions.List);
+            return new TeacherInfo
+            {
+                auth_token = auth_token,
+                blob_uri = blob_uri,
+                blob_sas = blob_sas,
+                schools = schools,
+                defaultschool = defaultschool,
+                courses = courses,
+                total = total,
+                osblob_sas = osblob_sas,
+                osblob_uri = osblob_uri,
+                tsize = tsize,
+                areas = areas,
+                teacher = teacher
+            };
+        }
+    }
+}