using Microsoft.Azure.Cosmos; using System; using System.Collections.Generic; using System.Globalization; using System.Linq; using System.Text; using System.Text.Json; using System.Text.Json.Nodes; using System.Threading.Tasks; using TEAMModelOS.SDK.DI; using TEAMModelOS.SDK.Extension; using TEAMModelOS.SDK.Models.Cosmos.Student; namespace TEAMModelOS.SDK.Models { public static class OverallEducationService { public static async Task GetAppraiseRecord(AzureCosmosFactory _azureCosmosFactory, string schoolId,string _studyYear, string semesterId,List students,HashSet classIds) { StringBuilder sqlQ = new StringBuilder($"SELECT c.targetId,c.classId,c.id,c.academicYearId, b as appraise FROM c join b in c.nodes where c.code = 'AppraiseRecord-{schoolId}' and ARRAY_Contains(b.appraiseNode.path,'提问能力') "); if (!string.IsNullOrWhiteSpace(_studyYear)&& !string.IsNullOrWhiteSpace(semesterId)) { sqlQ.Append($" and c.academicYearId ='{_studyYear}-{semesterId}'"); } if (classIds.Count > 0) { sqlQ.Append($" and c.classId in ({string.Join(",",classIds.Select(x=>$"'{x}'"))})"); } if (students.Count > 0) { sqlQ.Append($" and c.targetId in ({string.Join(",", students.Select(x => $"'{x.id}'"))})"); } List appraiseRecords = new List(); var result= await _azureCosmosFactory.GetCosmosClient().GetContainer(Constant.TEAMModelOS, Constant.Student).GetList(sqlQ.ToString(), $"AppraiseRecord-{schoolId}"); if (result.list.IsNotEmpty()) { appraiseRecords.AddRange(result.list); } // 获取当前文化的日历 CultureInfo culture = CultureInfo.CurrentCulture; Calendar calendar = culture.Calendar; Dictionary> dict = new Dictionary>(); foreach (var appraiseRecord in appraiseRecords) { var date= DateTimeOffset.FromUnixTimeMilliseconds(appraiseRecord.appraise.createTime); int year = date.Year; // 计算当前时间是一年中的第几周 int weekOfYear = calendar.GetWeekOfYear(date.DateTime, culture.DateTimeFormat.CalendarWeekRule, culture.DateTimeFormat.FirstDayOfWeek); string key = $"{appraiseRecord.targetId}::{year}-{weekOfYear}"; if (dict.ContainsKey(key)) { dict[key].Add(appraiseRecord); } else { dict[key] = new List() { appraiseRecord }; } } foreach (var item in dict) { //正向评价-负向评价,评价次数 int count = item.Value.Where(x => x.appraise.appraiseNode.isPraise).Count() - item.Value.Where(x =>! x.appraise.appraiseNode.isPraise).Count(); double score = 100 / (1 + Math.Exp(-0.3 * count));//0.3是斜率,用于处理评分值曲线变化 string[] sp = item.Key.Split(); } //最新一周的数据 ,检查当前最新一周的数据是否大于历史均值,如果小于,则在平均次数上累加当前一周的数据,如果大于则累计在均值中。以防止当前周将均值拉下去。 return null; } public static Dictionary GetQueryCond(JsonElement request) { Dictionary dict = new Dictionary(); if (request.TryGetProperty("periodId", out JsonElement periodId) && !string.IsNullOrWhiteSpace($"{periodId}")) { dict.Add("periodId", periodId); } if (request.TryGetProperty("classIds", out JsonElement classIds)) { dict.Add("classId", classIds); } return dict; } public async static Task<(List classes, List students, List grade_classes, List grade_students, List overallEducations)> GetGradeData(CosmosClient client, HashSet years,string _periodId,string _school,HashSet classIds,string _studyYear,string _semesterId, AzureRedisFactory _azureRedis) { List classes = new List(); List students = new List(); List grade_classes = new List(); List grade_students = new List(); //StringBuilder sql = new StringBuilder($"select value c from c where c.year in ({string.Join(",", years)}) and c.periodId='{_periodId}' "); //if (classIds.Any() && classIds.Count>0) //{ // sql.Append($" and c.id in ({string.Join(",", classIds.Select(z => $"'{z}'"))})"); //} //当前条件的班级 // var result = await client.GetContainer(Constant.TEAMModelOS, Constant.School).GetList(sql.ToString(), $"Class-{_school}"); //classes = result.list; //StringBuilder studentCountSQL = new StringBuilder($"select c.id,c.name ,c.picture, c.classId,c.periodId ,c.year from c " + // $"where ( c.graduate = 0 or IS_DEFINED(c.graduate) = false) and c.classId in ({string.Join(",", classes.Select(z => $"'{z.id}'"))}) "); //当前条件的学生 // var data = await client.GetContainer(Constant.TEAMModelOS, Constant.Student).GetList(studentCountSQL.ToString(), $"Base-{_school}"); //获取年级的所有的班级 StringBuilder gradeSql = new StringBuilder($"select value c from c where c.year in ({string.Join(",", years)}) and c.periodId='{_periodId}' "); var result_grade_classes = await client.GetContainer(Constant.TEAMModelOS, Constant.School).GetList(gradeSql.ToString(), $"Class-{_school}"); grade_classes = result_grade_classes.list; //------获取当前条件的班级 classes= grade_classes.FindAll(z => classIds!=null && classIds.Any() && classIds.Count>0 ? classIds.Contains(z.id):true && z.periodId.Equals(_periodId) && years.Contains(z.year)); string classin = string.Empty; if (classes.IsNotEmpty()) { classin=$" {string.Join(",", grade_classes.Select(z => $"'{z.id}'"))} "; } else { classin="'--00000--'"; } StringBuilder grade_studentCountSQL = new StringBuilder($"select c.id,c.name ,c.picture, c.classId,c.periodId ,c.year from c " + $" where c.classId in ( {classin} ) and c.periodId='{_periodId}' and ( c.graduate = 0 or IS_DEFINED(c.graduate) = false) "); //获取年级所有学生 var gradeData = await client.GetContainer(Constant.TEAMModelOS, Constant.Student).GetList(grade_studentCountSQL.ToString(), $"Base-{_school}"); grade_students = gradeData.list; //------获取当前条件的学生 students = grade_students.FindAll(z => classes.Select(x => x.id).Contains(z.classId) && z.periodId.Equals(_periodId)); //获取缓存的五育数据 //1.先从redis获取部分。 List overallEducations = new List(); foreach (var grade_class in grade_classes) { string key = $"OverallEducation:{_school}:{_periodId}:{_studyYear}:{_semesterId}:{grade_class.id}"; var records = await _azureRedis.GetRedisClient(8).HashGetAllAsync(key); foreach (var rcd in records) { var value = rcd.Value.ToString().ToObject(); if (value != null && !string.IsNullOrWhiteSpace(value.studentId)) { overallEducations.Add(value); } } } //2.整个年级的学生基础信息,对比redis获取的差,看是否是有部门未缓存在Redis,缓存没有数据的学生。 var no_overall_stduents = grade_students.ExceptBy(overallEducations.Select(z => z.studentId), v => v.id); if (no_overall_stduents.Any() && no_overall_stduents.Count() > 0) { string oesql = $"select value c from c where c.semesterId='{_semesterId}' and c.year={_studyYear} and c.periodId='{_periodId}' and c.studentId in ({string.Join(",", no_overall_stduents.Select(z => $"'{z.id}'"))}) "; var oeresults = await client.GetContainer(Constant.TEAMModelOS, Constant.Student).GetList(oesql, $"OverallEducation-{_school}"); if (oeresults.list.IsNotEmpty()) { overallEducations.AddRange(oeresults.list); //将获取到的最新数据缓存在redis中。下次则不需要再次获取 foreach (var item in oeresults.list) { string key = $"OverallEducation:{item.schoolCode}:{item.periodId}:{item.year}:{item.semesterId}:{item.classId}"; await _azureRedis.GetRedisClient(8).HashSetAsync(key, item.studentId, item.ToJsonString()); await _azureRedis.GetRedisClient(8).KeyExpireAsync(key, new TimeSpan(180 * 24, 0, 0)); } } } return (classes, students, grade_classes, grade_students, overallEducations); } } }