using FreeSql; using FreeSql.DataAnnotations; using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Threading.Tasks; namespace FreeSql { /// /// 树状基类 /// /// /// [Table(DisableSyncStructure = true)] public abstract class BaseEntityTree : BaseEntity where TEntity : class { /// /// 父级id /// public TKey ParentId { get => _ParentId; set { if (Equals(value, default(TKey)) == false && Equals(value, Id)) throw new ArgumentException("ParentId 值不能与 Id 相同"); _ParentId = value; } } public TEntity Parent { get; set; } private TKey _ParentId; /// /// 下级列表 /// [Navigate("ParentId")] public List Childs { get; set; } /// /// 名称 /// public string Name { get; set; } /// /// 名称:技术部-前端 /// public string FullName { get; set; } public List GetAllChilds() => Select.WhereDynamic(this) .IncludeMany(a => (a as BaseEntityTree).Childs, t1 => t1.IncludeMany(a1 => (a1 as BaseEntityTree).Childs, t2 => t2.IncludeMany(a2 => (a2 as BaseEntityTree).Childs, t3 => t3.IncludeMany(a3 => (a3 as BaseEntityTree).Childs, t4 => t4.IncludeMany(a4 => (a4 as BaseEntityTree).Childs, t5 => t5.IncludeMany(a5 => (a5 as BaseEntityTree).Childs, t6 => t6.IncludeMany(a6 => (a6 as BaseEntityTree).Childs, t7 => t7.IncludeMany(a7 => (a7 as BaseEntityTree).Childs, t8 => t8.IncludeMany(a8 => (a8 as BaseEntityTree).Childs, t9 => t9.IncludeMany(a9 => (a9 as BaseEntityTree).Childs, t10 => t10.IncludeMany(a10 => (a10 as BaseEntityTree).Childs))))))))))).ToList() .SelectMany(a => (a as BaseEntityTree).Childs .SelectMany(a1 => (a1 as BaseEntityTree)?.Childs .SelectMany(a2 => (a2 as BaseEntityTree)?.Childs .SelectMany(a3 => (a3 as BaseEntityTree)?.Childs .SelectMany(a4 => (a4 as BaseEntityTree)?.Childs .SelectMany(a5 => (a5 as BaseEntityTree)?.Childs .SelectMany(a6 => (a6 as BaseEntityTree)?.Childs .SelectMany(a7 => (a7 as BaseEntityTree)?.Childs .SelectMany(a8 => (a8 as BaseEntityTree)?.Childs .SelectMany(a9 => (a9 as BaseEntityTree)?.Childs .SelectMany(a10 => (a10 as BaseEntityTree)?.Childs))))))))))).Where(a => a != null).ToList(); protected void RefershFullName() { var buf = new List(); buf.Add(this as TEntity); buf.AddRange(this.GetAllChilds()); var repo = Orm.GetRepository(); repo.UnitOfWork = UnitOfWork.Current.Value; buf = repo.Select.WhereDynamic(buf) .Include(a => ((((((((((a as BaseEntityTree).Parent as BaseEntityTree).Parent as BaseEntityTree).Parent as BaseEntityTree).Parent as BaseEntityTree).Parent as BaseEntityTree).Parent as BaseEntityTree).Parent as BaseEntityTree).Parent as BaseEntityTree).Parent as BaseEntityTree).Parent).ToList(true); foreach (var item in buf) { var up = item as BaseEntityTree; up.Name = up.Name; var cur = up.Parent as BaseEntityTree; while (cur != null) { up.Name = $"{cur.Name}-{up.Name}"; cur = cur.Parent as BaseEntityTree; } } repo.Update(buf); } T UpdateIsDelete(bool value, Func, List, T> func) { var childs = GetAllChilds(); childs.Add(this as TEntity); var repo = Orm.GetRepository(); repo.UnitOfWork = UnitOfWork.Current.Value; repo.Attach(childs); foreach (var item in childs) (item as BaseEntity).IsDeleted = false; return func(repo, childs); } public override bool Delete() => UpdateIsDelete(true, (repo, chis) => repo.Update(chis)) > 0; async public override Task DeleteAsync() => await UpdateIsDelete(true, (repo, chis) => repo.UpdateAsync(chis)) > 0; public override bool Restore() => UpdateIsDelete(false, (repo, chis) => repo.Update(chis)) > 0; async public override Task RestoreAsync() => await UpdateIsDelete(false, (repo, chis) => repo.UpdateAsync(chis)) > 0; public override TEntity Insert() { var ret = base.Insert(); RefershFullName(); return ret; } async public override Task InsertAsync() { var ret = await base.InsertAsync(); RefershFullName(); return ret; } public override bool Update() { var old = Find(this.Id) as BaseEntityTree; var ret = base.Update(); if (old.Name != this.Name || Equals(old.ParentId, old.ParentId) == false) RefershFullName(); return ret; } async public override Task UpdateAsync() { var old = Find(this.Id) as BaseEntityTree; var ret = await base.UpdateAsync(); if (old.Name != this.Name || Equals(old.ParentId, old.ParentId) == false) RefershFullName(); return ret; } public override TEntity Save() { var old = Find(this.Id) as BaseEntityTree; var ret = base.Save(); if (old.Name != this.Name || Equals(old.ParentId, old.ParentId) == false) RefershFullName(); return ret; } async public override Task SaveAsync() { var old = Find(this.Id) as BaseEntityTree; var ret = await base.SaveAsync(); if (old.Name != this.Name || Equals(old.ParentId, old.ParentId) == false) RefershFullName(); return ret; } } }