You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

1435 lines
62 KiB

using Microsoft.EntityFrameworkCore;
using Newtonsoft.Json;
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Linq.Expressions;
using System.Reflection;
using VOL.Core.CacheManager;
using VOL.Core.Configuration;
using VOL.Core.Const;
using VOL.Core.Enums;
using VOL.Core.Extensions;
using VOL.Core.Extensions.AutofacManager;
using VOL.Core.Filters;
using VOL.Core.ManageUser;
using VOL.Core.Services;
using VOL.Core.Tenancy;
using VOL.Core.Utilities;
using VOL.Core.WorkFlow;
using VOL.Entity;
using VOL.Entity.DomainModels;
using VOL.Entity.SystemModels;
namespace VOL.Core.BaseProvider
{
public abstract class ServiceBase<T, TRepository> : ServiceFunFilter<T>
where T : BaseEntity
where TRepository : IRepository<T>
{
public ICacheService CacheContext
{
get
{
return AutofacContainerModule.GetService<ICacheService>();
}
}
public Microsoft.AspNetCore.Http.HttpContext Context
{
get
{
return HttpContext.Current;
}
}
private WebResponseContent Response { get; set; }
protected IRepository<T> repository;
private PropertyInfo[] _propertyInfo { get; set; } = null;
private PropertyInfo[] TProperties
{
get
{
if (_propertyInfo != null)
{
return _propertyInfo;
}
_propertyInfo = typeof(T).GetProperties();
return _propertyInfo;
}
}
public ServiceBase()
{
}
public ServiceBase(TRepository repository)
{
Response = new WebResponseContent(true);
this.repository = repository;
}
protected virtual void Init(IRepository<T> repository)
{
IsMultiTenancy = true; // 开启租户隔离
}
protected virtual Type GetRealDetailType()
{
return typeof(T).GetCustomAttribute<EntityAttribute>()?.DetailTable?[0];
}
/// <summary>
/// 2020.08.15添加自定义原生查询sql或多租户(查询、导出)
/// </summary>
/// <returns></returns>
private IQueryable<T> GetSearchQueryable()
{
//2021.08.22移除数据隔离(租房管理)超级管理员的判断
//没有自定sql与多租户执行默认查询
if (QuerySql == null && !IsMultiTenancy)
// if ((QuerySql == null && !IsMultiTenancy) || UserContext.Current.IsSuperAdmin)
{
return repository.DbContext.Set<T>();
}
//自定sql,没有使用多租户直接执行自定义sql
if (QuerySql != null && !IsMultiTenancy)
// if ((QuerySql != null && !IsMultiTenancy) || UserContext.Current.IsSuperAdmin)
{
return repository.DbContext.Set<T>().FromSqlRaw(QuerySql);
}
string multiTenancyString = TenancyManager<T>.GetSearchQueryable(typeof(T).GetEntityTableName());
return repository.DbContext.Set<T>().FromSqlRaw(multiTenancyString);
}
/// <summary>
/// 2020.08.15添加获取多租户数据过滤sql删除、编辑
/// </summary>
/// <returns></returns>
private string GetMultiTenancySql(string ids, string tableKey)
{
return TenancyManager<T>.GetMultiTenancySql(typeof(T).GetEntityTableName(), ids, tableKey);
}
/// <summary>
/// 2020.08.15添加多租户数据过滤(编辑)
/// </summary>
private void CheckUpdateMultiTenancy(string ids, string tableKey)
{
string sql = GetMultiTenancySql(ids, tableKey);
//请接着过滤条件
//例如sql只能(编辑)自己创建的数据:判断数据是不是当前用户创建的
//sql = $" {sql} and createid!={UserContext.Current.UserId}";
object obj = repository.DapperContext.ExecuteScalar(sql, null);
if (obj == null || obj.GetInt() == 0)
{
Response.Error("不能编辑此数据");
}
}
/// <summary>
/// 2020.08.15添加多租户数据过滤(删除)
/// </summary>
private void CheckDelMultiTenancy(string ids, string tableKey)
{
string sql = GetMultiTenancySql(ids, tableKey);
//请接着过滤条件
//例如sql只能(删除)自己创建的数据:找出不是自己创建的数据
//sql = $" {sql} and createid!={UserContext.Current.UserId}";
object obj = repository.DapperContext.ExecuteScalar(sql, null);
int idsCount = ids.Split(",").Distinct().Count();
if (obj == null || obj.GetInt() != idsCount)
{
Response.Error("不能删除此数据");
}
}
private const string _asc = "asc";
/// <summary>
/// 生成排序字段
/// </summary>
/// <param name="pageData"></param>
/// <param name="propertyInfo"></param>
private Dictionary<string, QueryOrderBy> GetPageDataSort(PageDataOptions pageData, PropertyInfo[] propertyInfo)
{
if (base.OrderByExpression != null)
{
return base.OrderByExpression.GetExpressionToDic();
}
if (!string.IsNullOrEmpty(pageData.Sort))
{
if (pageData.Sort.Contains(","))
{
var sortArr = pageData.Sort.Split(",").Where(x => propertyInfo.Any(c => c.Name == x)).Select(s => s).Distinct().ToList();
Dictionary<string, QueryOrderBy> sortDic = new Dictionary<string, QueryOrderBy>();
foreach (var name in sortArr)
{
sortDic[name] = pageData.Order?.ToLower() == _asc ? QueryOrderBy.Asc : QueryOrderBy.Desc;
}
return sortDic;
}
else if (propertyInfo.Any(x => x.Name == pageData.Sort))
{
return new Dictionary<string, QueryOrderBy>() { {
pageData.Sort,
pageData.Order?.ToLower() == _asc? QueryOrderBy.Asc: QueryOrderBy.Desc
} };
}
}
//如果没有排序字段,则使用主键作为排序字段
PropertyInfo property = propertyInfo.GetKeyProperty();
//如果主键不是自增类型则使用appsettings.json中CreateMember->DateField配置的创建时间作为排序
if (property.PropertyType == typeof(int) || property.PropertyType == typeof(long))
{
if (!propertyInfo.Any(x => x.Name.ToLower() == pageData.Sort))
{
pageData.Sort = propertyInfo.GetKeyName();
}
}
else
{
if (!string.IsNullOrEmpty(AppSetting.CreateMember.DateField)
&& propertyInfo.Any(x => x.Name == AppSetting.CreateMember.DateField))
{
pageData.Sort = AppSetting.CreateMember.DateField;
}
else
{
pageData.Sort = propertyInfo.GetKeyName();
}
}
return new Dictionary<string, QueryOrderBy>() { {
pageData.Sort, pageData.Order?.ToLower() == _asc? QueryOrderBy.Asc: QueryOrderBy.Desc
} };
}
/// <summary>
/// 前端查询条件转换为EF查询Queryable(2023.04.02)
/// </summary>
/// <param name="options">前端查询参数</param>
/// <param name="useTenancy">是否使用数据隔离</param>
/// <returns></returns>
public IQueryable<T> GetPageDataQueryFilter(PageDataOptions options, bool useTenancy = true)
{
ValidatePageOptions(options, out IQueryable<T> queryable, useTenancy);
return queryable;
}
/// <summary>
/// 验证排序与查询字段合法性
/// </summary>
/// <param name="options"></param>
/// <param name="queryable"></param>
/// <returns></returns>
protected PageDataOptions ValidatePageOptions(PageDataOptions options, out IQueryable<T> queryable, bool useTenancy = true)
{
options = options ?? new PageDataOptions();
List<SearchParameters> searchParametersList = new List<SearchParameters>();
if (options.Filter != null && options.Filter.Count > 0)
{
searchParametersList.AddRange(options.Filter);
}
else if (!string.IsNullOrEmpty(options.Wheres))
{
try
{
searchParametersList = options.Wheres.DeserializeObject<List<SearchParameters>>();
options.Filter = searchParametersList;
}
catch { }
}
QueryRelativeList?.Invoke(searchParametersList);
if (useTenancy)
{
queryable = GetSearchQueryable();
}
else
{
queryable = repository.DbContext.Set<T>();
}
// Connection
// queryable = repository.DbContext.Set<T>();
//2020.08.15添加自定义原生查询sql或多租户
//判断列的数据类型数字,日期的需要判断值的格式是否正确
for (int i = 0; i < searchParametersList.Count; i++)
{
SearchParameters x = searchParametersList[i];
x.DisplayType = x.DisplayType.GetDBCondition();
if (string.IsNullOrEmpty(x.Value))
{
continue;
}
PropertyInfo property = TProperties.Where(c => c.Name.ToUpper() == x.Name.ToUpper()).FirstOrDefault();
//2020.06.25增加字段null处理
if (property == null) continue;
// property
//移除查询的值与数据库类型不匹配的数据
object[] values = property.ValidationValueForDbType(x.Value.Split(',')).Where(q => q.Item1).Select(s => s.Item3).ToArray();
if (values == null || values.Length == 0)
{
continue;
}
if (x.DisplayType == HtmlElementType.Contains)
x.Value = string.Join(",", values);
LinqExpressionType expressionType = x.DisplayType.GetLinqCondition();
queryable = LinqExpressionType.In == expressionType
? queryable.Where(x.Name.CreateExpression<T>(values, expressionType))
: queryable.Where(x.Name.CreateExpression<T>(x.Value, expressionType));
}
options.TableName = base.TableName ?? typeof(T).Name;
return options;
}
/// <summary>
/// 加载页面数据
/// </summary>
/// <param name="loadSingleParameters"></param>
/// <returns></returns>
public virtual PageGridData<T> GetPageData(PageDataOptions options)
{
options = ValidatePageOptions(options, out IQueryable<T> queryable);
//获取排序字段
Dictionary<string, QueryOrderBy> orderbyDic = GetPageDataSort(options, TProperties);
PageGridData<T> pageGridData = new PageGridData<T>();
if (QueryRelativeExpression != null)
{
queryable = QueryRelativeExpression.Invoke(queryable);
}
if (options.Export)
{
queryable = queryable.GetIQueryableOrderBy(orderbyDic);
if (Limit > 0)
{
queryable = queryable.Take(Limit);
}
pageGridData.rows = queryable.ToList();
}
else
{
pageGridData.rows = repository.IQueryablePage(queryable,
options.Page,
options.Rows,
out int rowCount,
orderbyDic).ToList();
pageGridData.total = rowCount;
//查询界面统计求等字段
if (SummaryExpress != null)
{
pageGridData.summary = SummaryExpress.Invoke(queryable);
//Func<T, T> groupExpress = x =>x;
//pageGridData.summary = queryable.GroupBy(groupExpress).Select(SummaryExpress).FirstOrDefault();
}
}
GetPageDataOnExecuted?.Invoke(pageGridData);
return pageGridData;
}
public virtual object GetDetailPage(PageDataOptions pageData)
{
Type detailType = typeof(T).GetCustomAttribute<EntityAttribute>()?.DetailTable?[0];
if (detailType == null)
{
return null;
}
object obj = typeof(ServiceBase<T, TRepository>)
.GetMethod("GetDetailPage", BindingFlags.Instance | BindingFlags.NonPublic)
.MakeGenericMethod(new Type[] { detailType }).Invoke(this, new object[] { pageData });
return obj;
}
protected override object GetDetailSummary<Detail>(IQueryable<Detail> queryeable)
{
return null;
}
private PageGridData<Detail> GetDetailPage<Detail>(PageDataOptions options) where Detail : class
{
//校验查询值,排序字段,分页大小规则待完
PageGridData<Detail> gridData = new PageGridData<Detail>();
if (options.Value == null) return gridData;
//主表主键字段
string keyName = typeof(T).GetKeyName();
//生成查询条件
Expression<Func<Detail, bool>> whereExpression = keyName.CreateExpression<Detail>(options.Value, LinqExpressionType.Equal);
var queryeable = repository.DbContext.Set<Detail>().Where(whereExpression);
gridData.total = queryeable.Count();
options.Sort = options.Sort ?? typeof(Detail).GetKeyName();
Dictionary<string, QueryOrderBy> orderBy = GetPageDataSort(options, typeof(Detail).GetProperties());
gridData.rows = queryeable
.GetIQueryableOrderBy(orderBy)
.Skip((options.Page - 1) * options.Rows)
.Take(options.Rows)
.ToList();
gridData.summary = GetDetailSummary<Detail>(queryeable);
return gridData;
}
/// <summary>
/// 上传文件
/// </summary>
/// <param name="files"></param>
/// <returns></returns>
public virtual WebResponseContent Upload(List<Microsoft.AspNetCore.Http.IFormFile> files)
{
if (files == null || files.Count == 0) return Response.Error("请上传文件");
string filePath;
if (!string.IsNullOrEmpty(UploadFolder))
{
filePath = UploadFolder;
if (!filePath.EndsWith("/") || !filePath.EndsWith("\\"))
{
filePath += "/";
}
}
else
{
filePath = $"Upload/Tables/{typeof(T).GetEntityTableName()}/{DateTime.Now.ToString("yyyMMddHHmmsss") + new Random().Next(1000, 9999)}/";
}
string fullPath = filePath.MapPath(true);
int i = 0;
try
{
if (!Directory.Exists(fullPath)) Directory.CreateDirectory(fullPath);
for (i = 0; i < files.Count; i++)
{
string fileName = files[i].FileName;
using (var stream = new FileStream(fullPath + fileName, FileMode.Create))
{
files[i].CopyTo(stream);
}
}
}
catch (Exception ex)
{
Logger.Error($"上传文件失败:{typeof(T).GetEntityTableCnName()},路径:{filePath},失败文件:{files[i]},{ex.Message + ex.StackTrace}");
return Response.Error("文件上传失败");
}
return Response.OK("文件上传成功", filePath);
}
private List<string> GetIgnoreTemplate()
{
//忽略创建人、修改人、审核等字段
List<string> ignoreTemplate = UserIgnoreFields.ToList();
ignoreTemplate.AddRange(auditFields.ToList());
return ignoreTemplate;
}
public virtual WebResponseContent DownLoadTemplate()
{
string tableName = typeof(T).GetEntityTableCnName();
string dicPath = $"Download/{DateTime.Now.ToString("yyyMMdd")}/Template/".MapPath();
if (!Directory.Exists(dicPath)) Directory.CreateDirectory(dicPath);
string fileName = tableName + DateTime.Now.ToString("yyyyMMddHHssmm") + ".xlsx";
//DownLoadTemplateColumns 2020.05.07增加扩展指定导出模板的列
EPPlusHelper.ExportTemplate<T>(DownLoadTemplateColumns, GetIgnoreTemplate(), dicPath, fileName);
return Response.OK(null, dicPath + fileName);
}
/// <summary>
/// 导入表数据Excel文件夹
/// </summary>
/// <param name="files"></param>
/// <returns></returns>
public virtual WebResponseContent Import(List<Microsoft.AspNetCore.Http.IFormFile> files)
{
if (files == null || files.Count == 0)
return new WebResponseContent { Status = true, Message = "请选择上传的文件" };
Microsoft.AspNetCore.Http.IFormFile formFile = files[0];
string dicPath = $"Upload/{DateTime.Now.ToString("yyyMMdd")}/{typeof(T).Name}/".MapPath();
if (!Directory.Exists(dicPath)) Directory.CreateDirectory(dicPath);
dicPath = $"{dicPath}{Guid.NewGuid().ToString()}_{formFile.FileName}";
using (var stream = new FileStream(dicPath, FileMode.Create))
{
formFile.CopyTo(stream);
}
try
{
//2022.06.20增加原生excel读取方法(导入时可以自定义读取excel内容)
Response = EPPlusHelper.ReadToDataTable<T>(dicPath, DownLoadTemplateColumns, GetIgnoreTemplate(), readValue: ImportOnReadCellValue, ignoreSelectValidationColumns: ImportIgnoreSelectValidationColumns);
}
catch (Exception ex)
{
Response.Error("未能处理导入的文件,请检查导入的文件是否正确");
Logger.Error($"表{typeof(T).GetEntityTableCnName()}导入失败{ex.Message + ex.InnerException?.Message}");
}
if (CheckResponseResult()) return Response;
List<T> list = Response.Data as List<T>;
if (ImportOnExecuting != null)
{
Response = ImportOnExecuting.Invoke(list);
if (CheckResponseResult()) return Response;
}
//2022.01.08增加明细表导入判断
if (HttpContext.Current.Request.Query.ContainsKey("table"))
{
ImportOnExecuted?.Invoke(list);
return Response.OK("文件上传成功", list.Serialize());
}
repository.AddRange(list, true);
if (ImportOnExecuted != null)
{
Response = ImportOnExecuted.Invoke(list);
if (CheckResponseResult()) return Response;
}
return Response.OK("文件上传成功");
}
/// <summary>
/// 导出
/// </summary>
/// <param name="pageData"></param>
/// <returns></returns>
public virtual WebResponseContent Export(PageDataOptions pageData)
{
pageData.Export = true;
List<T> list = GetPageData(pageData).rows;
string tableName = typeof(T).GetEntityTableCnName();
string fileName = tableName + DateTime.Now.ToString("yyyyMMddHHssmm") + ".xlsx";
string folder = DateTime.Now.ToString("yyyyMMdd");
string savePath = $"Download/ExcelExport/{folder}/".MapPath();
List<string> ignoreColumn = new List<string>();
if (ExportOnExecuting != null)
{
Response = ExportOnExecuting(list, ignoreColumn);
if (CheckResponseResult()) return Response;
}
//ExportColumns 2020.05.07增加扩展指定导出模板的列
EPPlusHelper.Export(list, ExportColumns?.GetExpressionToArray(), ignoreColumn, savePath, fileName);
//return Response.OK(null, (savePath + "/" + fileName).EncryptDES(AppSetting.Secret.ExportFile));
//2022.01.08优化导出功能
return Response.OK(null, (savePath + "/" + fileName));
}
/// <summary>
/// 新建
/// </summary>
/// <param name="saveDataModel"></param>
/// <returns></returns>
public virtual WebResponseContent Add(SaveModel saveDataModel)
{
if (AddOnExecute != null)
{
Response = AddOnExecute(saveDataModel);
if (CheckResponseResult()) return Response;
}
if (saveDataModel == null
|| saveDataModel.MainData == null
|| saveDataModel.MainData.Count == 0)
return Response.Set(ResponseType.ParametersLack, false);
saveDataModel.DetailData = saveDataModel.DetailData?.Where(x => x.Count > 0).ToList();
Type type = typeof(T);
// 修改为与Update一致先设置默认值再进行实体的校验
UserInfo userInfo = UserContext.Current.UserInfo;
saveDataModel.SetDefaultVal(AppSetting.CreateMember, userInfo);
string validReslut = type.ValidateDicInEntity(saveDataModel.MainData, true, UserIgnoreFields);
if (!string.IsNullOrEmpty(validReslut)) return Response.Error(validReslut);
if (saveDataModel.MainData.Count == 0)
return Response.Error("保存的数据为空请检查model是否配置正确!");
PropertyInfo keyPro = type.GetKeyProperty();
if (keyPro.PropertyType == typeof(Guid) || keyPro.PropertyType == typeof(string))
{
saveDataModel.MainData.Add(keyPro.Name, Guid.NewGuid());
}
else
{
saveDataModel.MainData.Remove(keyPro.Name);
}
//没有明细直接保存返回
if (saveDataModel.DetailData == null || saveDataModel.DetailData.Count == 0)
{
T mainEntity = saveDataModel.MainData.DicToEntity<T>();
SetAuditDefaultValue(mainEntity);
if (base.AddOnExecuting != null)
{
Response = base.AddOnExecuting(mainEntity, null);
if (CheckResponseResult()) return Response;
}
Response = repository.DbContextBeginTransaction(() =>
{
repository.Add(mainEntity, true);
saveDataModel.MainData[keyPro.Name] = keyPro.GetValue(mainEntity);
Response.OK(ResponseType.SaveSuccess);
if (base.AddOnExecuted != null)
{
Response = base.AddOnExecuted(mainEntity, null);
}
return Response;
});
if (Response.Status) Response.Data = new { data = saveDataModel.MainData };
AddProcese(mainEntity);
return Response;
}
Type detailType = GetRealDetailType();
return typeof(ServiceBase<T, TRepository>)
.GetMethod("Add", BindingFlags.Instance | BindingFlags.NonPublic)
.MakeGenericMethod(new Type[] { detailType })
.Invoke(this, new object[] { saveDataModel })
as WebResponseContent;
}
public virtual WebResponseContent AddEntity(T entity, bool validationEntity = true)
{
return Add<T>(entity, null, validationEntity);
}
/// <summary>
/// 保存主、明细数据
/// </summary>
/// <typeparam name="TDetail"></typeparam>
/// <param name="entity"></param>
/// <param name="list"></param>
/// <param name="validationEntity">是否进行实体验证</param>
/// <returns></returns>
public WebResponseContent Add<TDetail>(T entity, List<TDetail> list = null, bool validationEntity = true) where TDetail : class
{
//设置用户默认值
entity.SetCreateDefaultVal();
SetAuditDefaultValue(entity);
if (validationEntity)
{
Response = entity.ValidationEntity();
if (CheckResponseResult()) return Response;
if (list != null && list.Count > 0)
{
Response = list.ValidationEntity();
if (CheckResponseResult()) return Response;
}
}
if (this.AddOnExecuting != null)
{
Response = AddOnExecuting(entity, list);
if (CheckResponseResult()) return Response;
}
Response = repository.DbContextBeginTransaction(() =>
{
repository.Add(entity);
repository.DbContext.SaveChanges();
//保存明细
if (list != null && list.Count > 0)
{
//获取保存后的主键值
PropertyInfo mainKey = typeof(T).GetKeyProperty();
PropertyInfo detailMainKey = typeof(TDetail).GetProperties()
.Where(q => q.Name.ToLower() == mainKey.Name.ToLower()).FirstOrDefault();
object keyValue = mainKey.GetValue(entity);
list.ForEach(x =>
{
//设置用户默认值
x.SetCreateDefaultVal();
detailMainKey.SetValue(x, keyValue);
repository.DbContext.Entry<TDetail>(x).State = EntityState.Added;
});
repository.DbContext.SaveChanges();
}
Response.OK(ResponseType.SaveSuccess);
if (AddOnExecuted != null)
Response = AddOnExecuted(entity, list);
return Response;
});
if (Response.Status && string.IsNullOrEmpty(Response.Message))
{
Response.OK(ResponseType.SaveSuccess);
}
AddProcese(entity);
return Response;
}
/// <summary>
/// 设置审批字段默认值
/// </summary>
/// <param name="entity"></param>
private void SetAuditDefaultValue(T entity)
{
if (!WorkFlowManager.Exists<T>())
{
return;
}
var propertity = TProperties.Where(x => x.Name.ToLower() == "auditstatus").FirstOrDefault();
if (propertity != null && propertity.GetValue(entity) == null)
{
propertity.SetValue(entity, 0);
}
}
/// <summary>
/// 写入流程
/// </summary>
/// <typeparam name="T"></typeparam>
/// <param name="entity"></param>
/// <param name="changeTableStatus">是否修改原表的审批状态</param>
protected void RewriteFlow(T entity, bool changeTableStatus = true)
{
WorkFlowManager.AddProcese(entity, true, changeTableStatus);
}
private void AddProcese(T entity)
{
if (!CheckResponseResult() && WorkFlowManager.Exists<T>())
{
if (AddWorkFlowExecuting != null && !AddWorkFlowExecuting.Invoke(entity))
{
return;
}
//写入流程
WorkFlowManager.AddProcese<T>(entity, addWorkFlowExecuted: AddWorkFlowExecuted);
// WorkFlowManager.Audit<T>(entity, AuditStatus.待审核, null, null, null, null, init: true, initInvoke: AddWorkFlowExecuted);
}
}
public void AddDetailToDBSet<TDetail>() where TDetail : class
{
List<PropertyInfo> listChilds = TProperties.Where(x => x.PropertyType.Name == "List`1").ToList();
// repository.DbContext.Set<TDetail>().AddRange();
}
private WebResponseContent Add<TDetail>(SaveModel saveDataModel) where TDetail : class
{
T mainEntity = saveDataModel.MainData.DicToEntity<T>();
//验证明细
string reslut = typeof(TDetail).ValidateDicInEntity(saveDataModel.DetailData, true, false, new string[] { TProperties.GetKeyName() });
if (reslut != string.Empty)
return Response.Error(reslut);
List<TDetail> list = saveDataModel.DetailData.DicToList<TDetail>();
Response = Add<TDetail>(mainEntity, list, false);
//保存失败
if (CheckResponseResult())
{
Logger.Error(LoggerType.Add, saveDataModel.Serialize() + Response.Message);
return Response;
}
PropertyInfo propertyKey = typeof(T).GetKeyProperty();
saveDataModel.MainData[propertyKey.Name] = propertyKey.GetValue(mainEntity);
Response.Data = new { data = saveDataModel.MainData, list };
return Response.Set(ResponseType.SaveSuccess);
}
#region 编辑
/// <summary>
/// 获取编辑明细主键
/// </summary>
/// <typeparam name="DetailT"></typeparam>
/// <typeparam name="Tkey"></typeparam>
/// <param name="detailKeyName"></param>
/// <param name="mainKeyName"></param>
/// <param name="mainKeyValue"></param>
/// <returns></returns>
public List<Tkey> GetUpdateDetailSelectKeys<DetailT, Tkey>(string detailKeyName, string mainKeyName, string mainKeyValue) where DetailT : class
{
IQueryable<DetailT> queryable = repository.DbContext.Set<DetailT>();
Expression<Func<DetailT, Tkey>> selectExpression = detailKeyName.GetExpression<DetailT, Tkey>();
Expression<Func<DetailT, bool>> whereExpression = mainKeyName.CreateExpression<DetailT>(mainKeyValue, LinqExpressionType.Equal);
List<Tkey> detailKeys = queryable.Where(whereExpression).Select(selectExpression).ToList();
return detailKeys;
}
/// <summary>
/// 将数据转换成对象后最终保存
/// </summary>
/// <typeparam name="DetailT"></typeparam>
/// <param name="saveModel"></param>
/// <param name="mainKeyProperty"></param>
/// <param name="detailKeyInfo"></param>
/// <param name="keyDefaultVal"></param>
/// <returns></returns>
public WebResponseContent UpdateToEntity<DetailT>(SaveModel saveModel, PropertyInfo mainKeyProperty, PropertyInfo detailKeyInfo, object keyDefaultVal) where DetailT : class
{
T mainEnity = saveModel.MainData.DicToEntity<T>();
List<DetailT> detailList = saveModel.DetailData.DicToList<DetailT>();
//2021.08.21优化明细表删除
//删除的主键
//查出所有明细表数据的ID
//System.Collections.IList detailKeys = this.GetType().GetMethod("GetUpdateDetailSelectKeys")
// .MakeGenericMethod(new Type[] { typeof(DetailT), detailKeyInfo.PropertyType })
// .Invoke(this, new object[] {
// detailKeyInfo.Name, mainKeyProperty.Name,
// saveModel.MainData[mainKeyProperty.Name].ToString()
// }) as System.Collections.IList;
//新增对象
List<DetailT> addList = new List<DetailT>();
// List<object> containsKeys = new List<object>();
//编辑对象
List<DetailT> editList = new List<DetailT>();
//删除的主键
List<object> delKeys = new List<object>();
mainKeyProperty = typeof(DetailT).GetProperties().Where(x => x.Name == mainKeyProperty.Name).FirstOrDefault();
//获取新增与修改的对象
foreach (DetailT item in detailList)
{
object value = detailKeyInfo.GetValue(item);
if (keyDefaultVal.Equals(value))//主键为默认值的,新增数据
{
//设置新增的主表的值
mainKeyProperty.SetValue(item,
saveModel.MainData[mainKeyProperty.Name]
.ChangeType(mainKeyProperty.PropertyType));
if (detailKeyInfo.PropertyType == typeof(Guid))
{
detailKeyInfo.SetValue(item, Guid.NewGuid());
}
addList.Add(item);
}
else //if (detailKeys.Contains(value))
{
//containsKeys.Add(value);
editList.Add(item);
}
}
//获取需要删除的对象的主键
if (saveModel.DelKeys != null && saveModel.DelKeys.Count > 0)
{
//2021.08.21优化明细表删除
delKeys = saveModel.DelKeys.Select(q => q.ChangeType(detailKeyInfo.PropertyType)).Where(x => x != null).ToList();
//.Where(x => detailKeys.Contains(x.ChangeType(detailKeyInfo.PropertyType)))
//.Select(q => q.ChangeType(detailKeyInfo.PropertyType)).ToList();
}
if (UpdateOnExecuting != null)
{
Response = UpdateOnExecuting(mainEnity, addList, editList, delKeys);
if (CheckResponseResult())
return Response;
}
mainEnity.SetModifyDefaultVal();
//主表修改
//不修改!CreateFields.Contains创建人信息
repository.Update(mainEnity, typeof(T).GetEditField()
.Where(c => saveModel.MainData.Keys.Contains(c) && !CreateFields.Contains(c))
.ToArray());
//foreach (var item in saveModel.DetailData)
//{
// item.SetModifyDefaultVal();
//}
//明细修改
editList.ForEach(x =>
{
//获取编辑的字段
var updateField = saveModel.DetailData
.Where(c => c[detailKeyInfo.Name].ChangeType(detailKeyInfo.PropertyType)
.Equal(detailKeyInfo.GetValue(x)))
.FirstOrDefault()
.Keys.Where(k => k != detailKeyInfo.Name)
.Where(r => !CreateFields.Contains(r))
.ToList();
updateField.AddRange(ModifyFields);
//設置默認值
x.SetModifyDefaultVal();
//添加修改字段
repository.Update<DetailT>(x, updateField.ToArray());
});
//明细新增
addList.ForEach(x =>
{
x.SetCreateDefaultVal();
repository.DbContext.Entry<DetailT>(x).State = EntityState.Added;
});
//明细删除
delKeys.ForEach(x =>
{
DetailT delT = Activator.CreateInstance<DetailT>();
detailKeyInfo.SetValue(delT, x);
repository.DbContext.Entry<DetailT>(delT).State = EntityState.Deleted;
});
if (UpdateOnExecuted == null)
{
repository.DbContext.SaveChanges();
Response.OK(ResponseType.SaveSuccess);
}
else
{
Response = repository.DbContextBeginTransaction(() =>
{
repository.DbContext.SaveChanges();
Response = UpdateOnExecuted(mainEnity, addList, editList, delKeys);
return Response;
});
}
if (Response.Status)
{
addList.AddRange(editList);
Response.Data = new { data = mainEnity, list = addList };
if (string.IsNullOrEmpty(Response.Message))
Response.OK(ResponseType.SaveSuccess);
}
return Response;
}
/// <summary>
/// 获取配置的创建人ID创建时间创建人,修改人ID修改时间、修改人与数据相同的字段
/// </summary>
private static string[] _userIgnoreFields { get; set; }
private static string[] UserIgnoreFields
{
get
{
if (_userIgnoreFields != null) return _userIgnoreFields;
List<string> fields = new List<string>();
fields.AddRange(CreateFields);
fields.AddRange(ModifyFields);
_userIgnoreFields = fields.ToArray();
return _userIgnoreFields;
}
}
private static string[] _createFields { get; set; }
private static string[] CreateFields
{
get
{
if (_createFields != null) return _createFields;
_createFields = AppSetting.CreateMember.GetType().GetProperties()
.Select(x => x.GetValue(AppSetting.CreateMember)?.ToString())
.Where(w => !string.IsNullOrEmpty(w)).ToArray();
return _createFields;
}
}
private static string[] _modifyFields { get; set; }
private static string[] ModifyFields
{
get
{
if (_modifyFields != null) return _modifyFields;
_modifyFields = AppSetting.ModifyMember.GetType().GetProperties()
.Select(x => x.GetValue(AppSetting.ModifyMember)?.ToString())
.Where(w => !string.IsNullOrEmpty(w)).ToArray();
return _modifyFields;
}
}
/// <summary>
/// 编辑
/// 1、明细表必须把主表的主键字段也设置为可编辑
/// 2、修改、增加只会操作设置为编辑列的数据
/// </summary>
/// <param name="saveModel"></param>
/// <returns></returns>
public virtual WebResponseContent Update(SaveModel saveModel)
{
if (UpdateOnExecute != null)
{
Response = UpdateOnExecute(saveModel);
if (CheckResponseResult()) return Response;
}
if (saveModel == null)
return Response.Error(ResponseType.ParametersLack);
//if (WorkFlowManager.Exists<T>())
//{
// var auditProperty = TProperties.Where(x => x.Name.ToLower() == "auditstatus").FirstOrDefault();
// string value = saveModel.MainData[auditProperty.Name]?.ToString();
// if (WorkFlowManager.GetAuditStatus<T>(value) != 1)
// {
// return Response.Error("数据已经在审核中,不能修改");
// }
//}
Type type = typeof(T);
//设置修改时间,修改人的默认值
UserInfo userInfo = UserContext.Current.UserInfo;
saveModel.SetDefaultVal(AppSetting.ModifyMember, userInfo);
//判断提交的数据与实体格式是否一致
string result = type.ValidateDicInEntity(saveModel.MainData, true, false, UserIgnoreFields);
if (result != string.Empty)
return Response.Error(result);
PropertyInfo mainKeyProperty = type.GetKeyProperty();
//验证明细
Type detailType = null;
if (saveModel.DetailData != null || (saveModel.DelKeys != null && saveModel.DelKeys.Count > 0))
{
detailType = GetRealDetailType();
if (detailType != null)
{
saveModel.DetailData = saveModel.DetailData == null
? new List<Dictionary<string, object>>()
: saveModel.DetailData.Where(x => x.Count > 0).ToList();
result = detailType.ValidateDicInEntity(saveModel.DetailData, true, false, new string[] { mainKeyProperty.Name });
if (result != string.Empty) return Response.Error(result);
}
//主从关系指定外键,即从表的外键可以不是主键的主表,还需要改下代码生成器设置属性外键,功能预留后面再开发(2020.04.25)
//string foreignKey = type.GetTypeCustomValue<System.ComponentModel.DataAnnotations.Schema.ForeignKeyAttribute>(x => new { x.Name });
//if (!string.IsNullOrEmpty(foreignKey))
//{
// var _mainKeyProperty = detailType.GetProperties().Where(x => x.Name.ToLower() == foreignKey.ToLower()).FirstOrDefault();
// if (_mainKeyProperty != null)
// {
// mainKeyProperty = _mainKeyProperty;
// }
//}
}
//获取主建类型的默认值用于判断后面数据是否正确,int long默认值为0,guid :0000-000....
object keyDefaultVal =
mainKeyProperty.PropertyType == typeof(string)
? ""
: mainKeyProperty.PropertyType.Assembly.CreateInstance(mainKeyProperty.PropertyType.FullName);//.ToString();
//判断是否包含主键
if (mainKeyProperty == null
|| !saveModel.MainData.ContainsKey(mainKeyProperty.Name)
|| saveModel.MainData[mainKeyProperty.Name] == null
)
{
return Response.Error(ResponseType.NoKey);
}
object mainKeyVal = saveModel.MainData[mainKeyProperty.Name];
//判断主键类型是否正确
(bool, string, object) validation = mainKeyProperty.ValidationValueForDbType(mainKeyVal).FirstOrDefault();
if (!validation.Item1)
return Response.Error(ResponseType.KeyError);
object valueType = mainKeyVal.ToString().ChangeType(mainKeyProperty.PropertyType);
//判断主键值是不是当前类型的默认值
if (valueType == null ||
(!valueType.GetType().Equals(mainKeyProperty.PropertyType)
|| valueType.ToString() == keyDefaultVal.ToString()
))
return Response.Error(ResponseType.KeyError);
if (saveModel.MainData.Count <= 1) return Response.Error("系统没有配置好编辑的数据请检查model!");
// 2020.08.15添加多租户数据过滤(编辑)
if (IsMultiTenancy && !UserContext.Current.IsSuperAdmin)
{
CheckUpdateMultiTenancy(mainKeyProperty.PropertyType == typeof(Guid) ? "'" + mainKeyVal.ToString() + "'" : mainKeyVal.ToString(), mainKeyProperty.Name);
if (CheckResponseResult())
{
return Response;
}
}
Expression<Func<T, bool>> expression = mainKeyProperty.Name.CreateExpression<T>(mainKeyVal.ToString(), LinqExpressionType.Equal);
if (!repository.Exists(expression)) return Response.Error("保存的数据不存在!");
//没有明细的直接保存主表数据
if (detailType == null)
{
saveModel.SetDefaultVal(AppSetting.ModifyMember, userInfo);
T mainEntity = saveModel.MainData.DicToEntity<T>();
if (UpdateOnExecuting != null)
{
Response = UpdateOnExecuting(mainEntity, null, null, null);
if (CheckResponseResult()) return Response;
}
//不修改!CreateFields.Contains创建人信息
repository.Update(mainEntity, type.GetEditField().Where(c => saveModel.MainData.Keys.Contains(c) && !CreateFields.Contains(c)).ToArray());
if (base.UpdateOnExecuted == null)
{
repository.SaveChanges();
Response.OK(ResponseType.SaveSuccess);
}
else
{
Response = repository.DbContextBeginTransaction(() =>
{
repository.SaveChanges();
Response = UpdateOnExecuted(mainEntity, null, null, null);
return Response;
});
}
if (Response.Status) Response.Data = new { data = mainEntity };
if (Response.Status && string.IsNullOrEmpty(Response.Message))
Response.OK(ResponseType.SaveSuccess);
return Response;
}
saveModel.DetailData = saveModel.DetailData.Where(x => x.Count > 0).ToList();
//明细操作
PropertyInfo detailKeyInfo = detailType.GetKeyProperty();
//主键类型
// string detailKeyType = mainKeyProperty.GetTypeCustomValue<ColumnAttribute>(c => new { c.TypeName });
//判断明细是否包含了主表的主键
string deatilDefaultVal = detailKeyInfo.PropertyType.Assembly.CreateInstance(detailKeyInfo.PropertyType.FullName).ToString();
foreach (Dictionary<string, object> dic in saveModel.DetailData)
{
//不包含主键的默认添加主键默认值,用于后面判断是否为新增数据
if (!dic.ContainsKey(detailKeyInfo.Name))
{
dic.Add(detailKeyInfo.Name, keyDefaultVal);
if (dic.ContainsKey(mainKeyProperty.Name))
{
dic[mainKeyProperty.Name] = keyDefaultVal;
}
else
{
dic.Add(mainKeyProperty.Name, keyDefaultVal);
}
continue;
}
if (dic[detailKeyInfo.Name] == null)
return Response.Error(ResponseType.NoKey);
//主键值是否正确
string detailKeyVal = dic[detailKeyInfo.Name].ToString();
if (!detailKeyInfo.ValidationValueForDbType(detailKeyVal).FirstOrDefault().Item1
|| deatilDefaultVal == detailKeyVal)
return Response.Error(ResponseType.KeyError);
//判断主表的值是否正确
if (detailKeyVal != keyDefaultVal.ToString() && (!dic.ContainsKey(mainKeyProperty.Name) || dic[mainKeyProperty.Name] == null || dic[mainKeyProperty.Name].ToString() == keyDefaultVal.ToString()))
{
return Response.Error(mainKeyProperty.Name + "是必填项!");
}
}
if (saveModel.DetailData.Exists(c => c.Count <= 2))
return Response.Error("系统没有配置好明细编辑的数据请检查model!");
return this.GetType().GetMethod("UpdateToEntity")
.MakeGenericMethod(new Type[] { detailType })
.Invoke(this, new object[] { saveModel, mainKeyProperty, detailKeyInfo, keyDefaultVal })
as WebResponseContent;
}
#endregion
/// <summary>
///
/// </summary>
/// <param name="keys"></param>
/// <param name="delList">是否删除明细数据(默认会删除明细)</param>
/// <returns></returns>
public virtual WebResponseContent Del(object[] keys, bool delList = true)
{
Type entityType = typeof(T);
var keyProperty = entityType.GetKeyProperty();
if (keyProperty == null || keys == null || keys.Length == 0) return Response.Error(ResponseType.NoKeyDel);
IEnumerable<(bool, string, object)> validation = keyProperty.ValidationValueForDbType(keys);
if (validation.Any(x => !x.Item1))
{
return Response.Error(validation.Where(x => !x.Item1).Select(s => s.Item2 + "</br>").Serialize());
}
string tKey = keyProperty.Name;
if (string.IsNullOrEmpty(tKey))
return Response.Error("没有主键不能删除");
if (DelOnExecuting != null)
{
Response = DelOnExecuting(keys);
if (CheckResponseResult()) return Response;
}
if (keyProperty.PropertyType == typeof(string))
{
Response = repository.DbContextBeginTransaction(() =>
{
repository.DeleteWithKeys(keys);
if (DelOnExecuted != null)
{
Response = DelOnExecuted(keys);
}
return Response;
});
if (Response.Status && string.IsNullOrEmpty(Response.Message)) Response.OK(ResponseType.DelSuccess);
return Response;
}
FieldType fieldType = entityType.GetFieldType();
string joinKeys = (fieldType == FieldType.Int || fieldType == FieldType.BigInt)
? string.Join(",", keys)
: $"'{string.Join("','", keys)}'";
// 2020.08.15添加判断多租户数据(删除)
//if (IsMultiTenancy && !UserContext.Current.IsSuperAdmin)
//{
// CheckDelMultiTenancy(joinKeys, tKey);
// if (CheckResponseResult())
// {
// return Response;
// }
//}
string sql = $"DELETE FROM {entityType.GetEntityTableName()} where {tKey} in ({joinKeys});";
// 2020.08.06增加pgsql删除功能
if (DBType.Name == DbCurrentType.PgSql.ToString())
{
sql = $"DELETE FROM \"public\".\"{entityType.GetEntityTableName()}\" where \"{tKey}\" in ({joinKeys});";
}
if (delList)
{
Type detailType = GetRealDetailType();
if (detailType != null)
{
if (DBType.Name == DbCurrentType.PgSql.ToString())
{
sql += $"DELETE FROM \"public\".\"{detailType.GetEntityTableName()}\" where \"{tKey}\" in ({joinKeys});";
}
else
{
sql += $"DELETE FROM {detailType.GetEntityTableName()} where {tKey} in ({joinKeys});";
}
}
}
//repository.DapperContext.ExcuteNonQuery(sql, CommandType.Text, null, true);
//可能在删除后还要做一些其它数据库新增或删除操作,这样就可能需要与删除保持在同一个事务中处理
//采用此方法 repository.DbContextBeginTransaction(()=>{//do delete......and other});
//做的其他操作在DelOnExecuted中加入委托实现
Response = repository.DbContextBeginTransaction(() =>
{
repository.ExecuteSqlCommand(sql);
if (DelOnExecuted != null)
{
Response = DelOnExecuted(keys);
}
return Response;
});
if (Response.Status && string.IsNullOrEmpty(Response.Message)) Response.OK(ResponseType.DelSuccess);
return Response;
}
private static string[] auditFields = new string[] { "auditid", "auditstatus", "auditor", "auditdate", "auditreason" };
/// <summary>
/// 审核默认对应数据库字段为AuditId审核人ID ,AuditStatus审核状态,Auditor审核人,Auditdate审核时间,Auditreason审核原因
/// </summary>
/// <param name="keys"></param>
/// <param name="auditStatus"></param>
/// <param name="auditReason"></param>
/// <returns></returns>
public virtual WebResponseContent Audit(object[] keys, int? auditStatus, string auditReason)
{
if (keys == null || keys.Length == 0)
return Response.Error("未获取到参数!");
Expression<Func<T, bool>> whereExpression = typeof(T).GetKeyName().CreateExpression<T>(keys[0], LinqExpressionType.Equal);
T entity = repository.FindAsIQueryable(whereExpression).FirstOrDefault();
if (entity == null)
{
return Response.Error($"未查到数据,或者数据已被删除,id:{keys[0]}");
}
//进入流程审批
if (WorkFlowManager.Exists<T>(entity))
{
var auditProperty = TProperties.Where(x => x.Name.ToLower() == "auditstatus").FirstOrDefault();
if (auditProperty == null)
{
return Response.Error("表缺少审核状态字段AuditStatus");
}
AuditStatus status = (AuditStatus)Enum.Parse(typeof(AuditStatus), auditStatus.ToString());
int val = auditProperty.GetValue(entity).GetInt();
if (!(val == (int)AuditStatus. || val == (int)AuditStatus.))
{
return Response.Error("只能审批[待审核或审核中]的数据");
}
Response = repository.DbContextBeginTransaction(() =>
{
return WorkFlowManager.Audit<T>(entity, status, auditReason, auditProperty, AuditWorkFlowExecuting, AuditWorkFlowExecuted);
});
if (Response.Status)
{
return Response.OK(ResponseType.AuditSuccess);
}
return Response.Error(Response.Message ?? "审批失败");
}
//获取主键
PropertyInfo property = TProperties.GetKeyProperty();
if (property == null)
return Response.Error("没有配置好主键!");
UserInfo userInfo = UserContext.Current.UserInfo;
//表如果有审核相关字段,设置默认审核
PropertyInfo[] updateFileds = TProperties.Where(x => auditFields.Contains(x.Name.ToLower())).ToArray();
List<T> auditList = new List<T>();
foreach (var value in keys)
{
object convertVal = value.ToString().ChangeType(property.PropertyType);
if (convertVal == null) continue;
entity = Activator.CreateInstance<T>();
property.SetValue(entity, convertVal);
foreach (var item in updateFileds)
{
switch (item.Name.ToLower())
{
case "auditid":
item.SetValue(entity, userInfo.User_Id);
break;
case "auditstatus":
item.SetValue(entity, auditStatus);
break;
case "auditor":
item.SetValue(entity, userInfo.UserTrueName);
break;
case "auditdate":
item.SetValue(entity, DateTime.Now);
break;
case "auditreason":
item.SetValue(entity, auditReason);
break;
}
}
auditList.Add(entity);
}
if (base.AuditOnExecuting != null)
{
Response = AuditOnExecuting(auditList);
if (CheckResponseResult()) return Response;
}
Response = repository.DbContextBeginTransaction(() =>
{
repository.UpdateRange(auditList, updateFileds.Select(x => x.Name).ToArray(), true);
if (base.AuditOnExecuted != null)
{
Response = AuditOnExecuted(auditList);
if (CheckResponseResult()) return Response;
}
return Response.OK();
});
if (Response.Status)
{
return Response.OK(ResponseType.AuditSuccess);
}
return Response.Error(Response.Message);
}
public virtual (string, T, bool) ApiValidate(string bizContent, Expression<Func<T, object>> expression = null)
{
return ApiValidateInput<T>(bizContent, expression);
}
/// <summary>
/// 对指定类与api的参数进行验证
/// </summary>
/// <typeparam name="TInput"></typeparam>
/// <param name="bizContent"></param>
/// <param name="input"></param>
/// <param name="expression">对指属性验证</param>
/// <returns>(string,TInput, bool) string:返回验证消息,TInputbizContent序列化后的对象,bool:验证是否通过</returns>
public virtual (string, TInput, bool) ApiValidateInput<TInput>(string bizContent, Expression<Func<TInput, object>> expression)
{
return ApiValidateInput(bizContent, expression, null);
}
/// <summary>
///
/// </summary>
/// <typeparam name="TInput"></typeparam>
/// <param name="bizContent"></param>
/// <param name="expression">对指属性验证格式如x=>new { x.UserName,x.Value }</param>
/// <param name="validateExpression">对指定的字段只做合法性判断比如长度是是否超长</param>
/// <returns>(string,TInput, bool) string:返回验证消息,TInputbizContent序列化后的对象,bool:验证是否通过</returns>
public virtual (string, TInput, bool) ApiValidateInput<TInput>(string bizContent, Expression<Func<TInput, object>> expression, Expression<Func<TInput, object>> validateExpression)
{
try
{
TInput input = JsonConvert.DeserializeObject<TInput>(bizContent);
if (!(input is System.Collections.IList))
{
Response = input.ValidationEntity(expression, validateExpression);
return (Response.Message, input, Response.Status);
}
System.Collections.IList list = input as System.Collections.IList;
for (int i = 0; i < list.Count; i++)
{
Response = list[i].ValidationEntity(expression?.GetExpressionProperty(),
validateExpression?.GetExpressionProperty());
if (CheckResponseResult())
return (Response.Message, default(TInput), false);
}
return ("", input, true);
}
catch (Exception ex)
{
Response.Status = false;
Response.Message = ApiMessage.ParameterError;
Logger.Error(LoggerType.HandleError, bizContent, null, ex.Message);
}
return (Response.Message, default(TInput), Response.Status);
}
/// <summary>
/// 将数据源映射到新的数据中,目前只支持List<TSource>映射到List<TResult>或TSource映射到TResult
/// 目前只支持Dictionary或实体类型
/// </summary>
/// <typeparam name="TSource"></typeparam>
/// <typeparam name="TResult"></typeparam>
/// <param name="source"></param>
/// <param name="resultExpression">只映射返回对象的指定字段</param>
/// <param name="sourceExpression">只映射数据源对象的指定字段</param>
/// 过滤条件表达式调用方式List表达式x => new { x[0].MenuName, x[0].Menu_Id}表示指定映射MenuName,Menu_Id字段
/// List<Sys_Menu> list = new List<Sys_Menu>();
/// list.MapToObject<List<Sys_Menu>, List<Sys_Menu>>(x => new { x[0].MenuName, x[0].Menu_Id}, null);
///
///过滤条件表达式调用方式实体表达式x => new { x.MenuName, x.Menu_Id}表示指定映射MenuName,Menu_Id字段
/// Sys_Menu sysMenu = new Sys_Menu();
/// sysMenu.MapToObject<Sys_Menu, Sys_Menu>(x => new { x.MenuName, x.Menu_Id}, null);
/// <returns></returns>
public virtual TResult MapToEntity<TSource, TResult>(TSource source, Expression<Func<TResult, object>> resultExpression,
Expression<Func<TSource, object>> sourceExpression = null) where TResult : class
{
return source.MapToObject<TSource, TResult>(resultExpression, sourceExpression);
}
/// <summary>
/// 将一个实体的赋到另一个实体上,应用场景:
/// 两个实体a a1= new a();b b1= new b(); a1.P=b1.P; a1.Name=b1.Name;
/// </summary>
/// <typeparam name="TSource"></typeparam>
/// <typeparam name="TResult"></typeparam>
/// <param name="source"></param>
/// <param name="result"></param>
/// <param name="expression">指定对需要的字段赋值,格式x=>new {x.Name,x.P},返回的结果只会对Name与P赋值</param>
public virtual void MapValueToEntity<TSource, TResult>(TSource source, TResult result, Expression<Func<TResult, object>> expression = null) where TResult : class
{
source.MapValueToEntity<TSource, TResult>(result, expression);
}
/// <summary>
/// 2021.07.04增加code="-1"强制返回,具体使用见:后台开发文档->后台基础代码扩展实现
/// </summary>
/// <returns></returns>
private bool CheckResponseResult()
{
return !Response.Status || Response.Code == "-1";
}
}
}