123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320 |
- using Microsoft.Azure.Cosmos;
- using System;
- using System.Collections.Generic;
- using System.Linq;
- using System.Text.RegularExpressions;
- using System.Threading.Tasks;
- using TEAMModelOS.SDK.DI;
- using TEAMModelOS.SDK.Extension;
- using TEAMModelOS.SDK.Models;
- using TEAMModelOS.SDK.Models.Cosmos.Common;
- namespace TEAMModelOS.SDK.Services
- {
- public static class SyllabusService
- {
- /// <summary>
- /// 根据id查询列表串联id pid的新的关系列表
- /// </summary>
- /// <param name="nodes"></param>
- /// <param name="pid"></param>
- /// <param name="newNodes"></param>
- /// <returns></returns>
- public async static Task<(List<List<IdCode>> idCodes, List<SyllabusTreeNode> tree)> ImportSyllabus(List<List<string>> nodes,string volumeId,string scope ,string code,string creatorId ,string creatorName,string grant_type, AzureCosmosFactory azureCosmos, bool ignoreCharacter = true) {
- HashSet<Syllabus> syllabuses= new HashSet<Syllabus>();
- string tbname = scope.Equals("school", StringComparison.OrdinalIgnoreCase) ? Constant.School : Constant.Teacher;
- await foreach (var item in azureCosmos.GetCosmosClient().GetContainer(Constant.TEAMModelOS, tbname).GetItemQueryIteratorSql<Syllabus>(queryText: $"select value(c) from c where c.volumeId='{volumeId}'",
- requestOptions: new QueryRequestOptions() { PartitionKey = new PartitionKey($"Syllabus-{code}") })) {
- syllabuses.Add(item);
- }
- Volume volume = await azureCosmos.GetCosmosClient().GetContainer(Constant.TEAMModelOS, tbname).ReadItemAsync<Volume>($"{volumeId}", new PartitionKey($"Volume-{code}"));
- HashSet<Syllabus> chapters = new HashSet<Syllabus>();
- long now= DateTimeOffset.UtcNow.ToUnixTimeMilliseconds();
- List<List<IdCode> > resNodes = new List<List<IdCode>>();
- foreach (var points in nodes) {
- // points 作为 层级路径 ["汽车考照", "汽车法规","驾驶道德、交通安全常识及行车安全检查与维护"]
- int level = 0;
- // 根节点 作为章节进行当前 路径操作的主要对象
- Syllabus chapter = null;
- //用于记录 ["汽车考照", "汽车法规","驾驶道德、交通安全常识及行车安全检查与维护"] 标题的id 路径
- List<(string title, string id)> nodesVal = new List<(string title, string id)>();
- //上一次操作的 id 用于方便检索下一层级时作为pid
- string lastId =null;
- foreach (var point in points) {
- string express = "[ \\[ \\] \\^ \\-|()【】/' {}_*×――(^)$%~!@#$…&%¥—+=<>《》!!???::•`·、。,;,.;\"‘’“”-]";
- //是否开启特殊符号的正则过滤
- string pt = ignoreCharacter? Regex.Replace(point, express, ""):point;
- if (level == 0)
- {
- var sylbs = syllabuses.SelectMany(z => z.children).Where(c => c.pid.Equals(volumeId) && pt.Equals(ignoreCharacter? Regex.Replace(c.title, express, ""): c.title));
- if (sylbs.Any())
- {
- //找到相关的章节
- chapter = syllabuses.Where(z=>z.id.Equals(sylbs.First().id)).FirstOrDefault();
- if (chapter == null )
- {
- foreach (var item in syllabuses)
- {
- var it = item.children.Find(z => z.id.Equals(sylbs.First().id));
- if (it != null)
- {
- item.id = sylbs.First().id;
- chapter = item;
- chapters.Add(chapter);
- lastId = item.id;
- nodesVal.Add((point, item.id));
- break;
- }
- }
- }
- else {
- chapters.Add(chapter);
- lastId = chapter.id;
- nodesVal.Add((point, sylbs.First().id));
- }
- }
- else {
- //未找到相关的章节
- string id = id = Guid.NewGuid().ToString();
- lastId= id;
- chapter = new Syllabus {
- id = id,
- volumeId = volumeId,
- code = $"Syllabus-{code}",
- pk = "Syllabus",
- ttl = -1,
- scope= scope,
- children= new List<Tnode> { new Tnode {id = id ,pid=volumeId, creatorId = creatorId,
- creatorName = creatorName,title=pt,updateTime= now} }
- };
- chapters.Add(chapter);
- syllabuses.Add(chapter);
- nodesVal.Add((point, id));
- }
- //下钻一层
- level += 1;
- }
- else {
- if (!string.IsNullOrWhiteSpace(lastId))
- {
- var child = chapter.children.Find(child => child.pid.Equals(lastId) && pt.Equals(ignoreCharacter ? Regex.Replace(child.title, express, "") : child.title));
- if (child == null)
- {
- string id = id = Guid.NewGuid().ToString();
- child = new Tnode {
- id = id,
- pid = lastId,
- creatorId = creatorId,
- creatorName = creatorName,
- title = pt,
- updateTime = now
- };
- chapter.children.Add(child);
- lastId = child.id;
- nodesVal.Add((point, child.id));
- }
- else {
- lastId= child.id;
- nodesVal.Add((point, child.id));
- }
- level += 1;
- }
- }
- }
- if (chapter != null) {
- resNodes.Add(nodesVal.Select(z => new IdCode { id = z.id, code = z.title }).ToList());
- }
- }
- bool volumeChange=false;
- List<SyllabusTreeNode> treeNodes = new List<SyllabusTreeNode>();
- foreach (var chapter in chapters)
- {
- if (!volume.syllabusIds.Contains(chapter.id)) {
- volume.syllabusIds.Add(chapter.id);
- volumeChange = true;
- }
- if (!string.IsNullOrWhiteSpace(grant_type) && grant_type.Equals("upsert")) {
- await azureCosmos.GetCosmosClient().GetContainer(Constant.TEAMModelOS, tbname).UpsertItemAsync(chapter);
- }
- List<SyllabusTree> trees = SyllabusService.ListToTree(chapter.children);
- SyllabusTreeNode tree = new SyllabusTreeNode() { id = chapter.id, scope = chapter.scope, trees = trees, volumeId = chapter.volumeId, auth = chapter.auth, codeval = code };
- treeNodes.Add(tree);
- }
- if (volumeChange && !string.IsNullOrWhiteSpace(grant_type) && grant_type.Equals("upsert"))
- {
- await azureCosmos.GetCosmosClient().GetContainer(Constant.TEAMModelOS, tbname).ReplaceItemAsync(volume, volume.id, new PartitionKey(volume.code));
- }
- List<SyllabusTreeNode> redt = new List<SyllabusTreeNode>();
- //对课纲树形结构排序
- if (volume.syllabusIds.IsNotEmpty())
- {
- volume.syllabusIds.ForEach(x =>
- {
- for (int index = 0; index < treeNodes.Count; index++)
- {
- if (treeNodes[index].id == x)
- {
- redt.Add(treeNodes[index]);
- treeNodes.RemoveAt(index);
- }
- }
- });
- redt.AddRange(treeNodes);
- return (resNodes, redt);
- }
- else {
- return (resNodes, treeNodes);
- }
- }
- /// <summary>
- /// 根据id查询列表串联id pid的新的关系列表
- /// </summary>
- /// <param name="nodes"></param>
- /// <param name="pid"></param>
- /// <param name="newNodes"></param>
- /// <returns></returns>
- public static HashSet<Tnode> GetNewNode(List<Tnode> nodes, string pid, HashSet<Tnode> newNodes) {
- bool flag = false;
- string spid = "";
- foreach (var node in nodes) {
- if (node.pid == pid) {
- newNodes.Add(node);
- spid = node.id;
- GetNewNode(nodes, spid, newNodes);
- flag = true;
- }
- }
- return newNodes;
- //if (flag)
- //{
- // return GetNewNode(nodes, spid, newNodes);
- //}
- //else {
- // return newNodes;
- //}
- }
- public static List<Tnode> TreeToList(List<SyllabusTree> trees, List<Tnode> nodes,long now)
- {
- int index = 0;
- foreach (SyllabusTree tr in trees)
- {
- tr.order = index;
- index++;
- }
- trees = trees.OrderBy(x => x.order).ToList();
- List<Tnode> list = new List<Tnode>();
- //var list = trees.ToJsonString().ToObject<List<Tnode>>();
- trees.ForEach(x=> {
- List<string> cids = new List<string>();
- if (x.children.IsNotEmpty()) {
- x.children.ForEach(y => cids.Add(y.id));
- }
- var node = new Tnode
- {
- title = x.title,
- id = x.id,
- pid = x.pid,
- order = x.order,
- rnodes = x.rnodes,
- cids= cids,
- creatorId=x.creatorId,
- creatorName=x.creatorName,
- updateTime= now
- };
- list.Add(node);
- });
- nodes.AddRange(list);
- foreach (SyllabusTree tree in trees)
- {
- if (null != tree.children && tree.children.Count > 0)
- {
- TreeToList(tree.children, nodes,now);
- }
- }
- return nodes;
- }
- public static List<SyllabusTree> ListToTree(List<Tnode> noes)
- {
- List<SyllabusTree> list = noes.ToJsonString().ToObject<List<SyllabusTree>>();
- //var lookup = list.ToDictionary(n => n.RowKey, n => n);
- var res = from r in list group r by r.id into g select g;
- Dictionary<string, SyllabusTree> blockDict = new Dictionary<string, SyllabusTree>();
- foreach (var s in res)
- {
- blockDict.TryAdd(s.First().id, s.First());
- }
- return GetChild(list, blockDict);
- }
- private static List<SyllabusTree> GetChild(List<SyllabusTree> list, Dictionary<string, SyllabusTree> dict)
- {
- // list = list.OrderBy(m => m.Order).ToList();
- List<SyllabusTree> trees = new List<SyllabusTree>();
- trees = trees.OrderBy(x => x.order).ToList();
- foreach (SyllabusTree node in list)
- {
- bool flag = dict.TryGetValue(node.pid, out SyllabusTree syllabus);
- if (flag && syllabus != null)
- {
- syllabus.children.Add(node);
- }
- else
- {
- trees.Add(node);
- }
- }
- return trees;
- }
- #region 开放平台使用
- public static List<OSyllabusTree> OListToTree(List<OTnode> noes)
- {
- List<OSyllabusTree> list = noes.ToJsonString().ToObject<List<OSyllabusTree>>();
- //var lookup = list.ToDictionary(n => n.RowKey, n => n);
- var res = from r in list group r by r.id into g select g;
- Dictionary<string, OSyllabusTree> blockDict = new Dictionary<string, OSyllabusTree>();
- foreach (var s in res)
- {
- blockDict.TryAdd(s.First().id, s.First());
- }
- return GetChildO(list, blockDict);
- }
- private static List<OSyllabusTree> GetChildO(List<OSyllabusTree> list, Dictionary<string, OSyllabusTree> dict)
- {
- // list = list.OrderBy(m => m.Order).ToList();
- List<OSyllabusTree> trees = new List<OSyllabusTree>();
- trees = trees.OrderBy(x => x.order).ToList();
- foreach (OSyllabusTree node in list)
- {
- bool flag = dict.TryGetValue(node.pid, out OSyllabusTree syllabus);
- if (flag && syllabus != null)
- {
- syllabus.children.Add(node);
- }
- else
- {
- trees.Add(node);
- }
- }
- return trees;
- }
- #endregion
- }
- }
|