Synchronization code

This commit is contained in:
sunkaixuan
2022-12-02 03:53:27 +08:00
parent f9e7f7d9c4
commit fb87a0d178
8 changed files with 263 additions and 1 deletions

View File

@@ -10,6 +10,9 @@ using System.Reflection;
using System.Dynamic;
using System.Threading.Tasks;
using System.Collections.ObjectModel;
using NetTaste;
using Newtonsoft.Json.Linq;
using System.Xml.Linq;
namespace SqlSugar
{
@@ -1159,8 +1162,12 @@ namespace SqlSugar
RestoreMapping();
_Mapper(result);
_InitNavigat(result);
_SubQuery(result);
return result;
}
protected async Task<List<TResult>> _ToListAsync<TResult>()
{
List<TResult> result = null;
@@ -1177,6 +1184,7 @@ namespace SqlSugar
RestoreMapping();
_Mapper(result);
await _InitNavigatAsync(result);
await _SubQueryAsync(result);
return result;
}
private void ToSqlBefore()
@@ -1391,5 +1399,96 @@ namespace SqlSugar
return new KeyValuePair<string, List<SugarParameter>>(sql, QueryBuilder.Parameters);
}
#endregion
#region Subquery
private void _SubQuery<TResult>(List<TResult> result)
{
var isSubToList = this.QueryBuilder.SubToListParameters != null && this.QueryBuilder.SubToListParameters.Any();
if (!isSubToList)
{
return;
}
var isAuto = this.Context.CurrentConnectionConfig.IsAutoCloseConnection;
if(!this.Context.Ado.IsAnyTran())
this.Context.CurrentConnectionConfig.IsAutoCloseConnection = false;
Console.WriteLine("Subquery long link start");
var entityInfo = this.Context.EntityMaintenance.GetEntityInfo(this.QueryBuilder.EntityType);
foreach (var paramter in this.QueryBuilder.SubToListParameters)
{
for (int i = 0; i < result.Count; i++)
{
var ps = this.QueryBuilder.Parameters.ToList();
var item = result[i];
var sqlPart = paramter.Value.ObjToString();
int j = 0;
foreach (var column in entityInfo.Columns)
{
j++;
if (column.DbColumnName == null) continue;
var isumber = UtilMethods.IsNumber(column.PropertyInfo.PropertyType.Name);
var name = this.SqlBuilder.GetTranslationColumnName(this.QueryBuilder.TableShortName) + "." + this.SqlBuilder.GetTranslationColumnName(column.DbColumnName);
var guid = Guid.NewGuid() + "-" + Guid.NewGuid();
var oldLength = sqlPart.Length;
sqlPart = sqlPart.Replace(name, guid);
var newLength = sqlPart.Length;
if (oldLength != newLength)
{
PropertyInfo property = item.GetType().GetProperties().FirstOrDefault(it => it.Name.Equals(column.PropertyName));
Check.ExceptionEasy(property == null, $"The subquery condition uses {column.PropertyName}, so the Select DTO must have a {column.PropertyName} column", $"子查询条件用到了{column.PropertyName},所以 Select DTO 中必须要有 {column.PropertyName} 列");
var parameterName = this.SqlBuilder.SqlParameterKeyWord + "sublistp" +column.PropertyName+ j;
var parameter = new SugarParameter(parameterName, property.GetValue(item));
ps.Add(parameter);
sqlPart = sqlPart.Replace(guid, parameterName);
}
}
//sqlPart = sqlPart.Replace("@SugarlistRowIndex", 0);
var methodParamters = new object[] { sqlPart, ps };
var itemProperty = item.GetType().GetProperty(paramter.Key);
var callType = itemProperty.PropertyType.GetGenericArguments()[0];
var subList = ExpressionBuilderHelper.CallFunc(callType, methodParamters, this, "SubQueryList");
if (item.GetType().IsAnonymousType())
{
var jobj = JObject.FromObject(item);
var prop = jobj.Property(paramter.Key);
prop.Value = JArray.FromObject(subList);
result[i] = jobj.ToObject<TResult>();
}
else
{
itemProperty.SetValue(item, subList);
}
++i;
}
}
Console.WriteLine("Subquery long link end");
if (!this.Context.Ado.IsAnyTran())
{
this.Context.CurrentConnectionConfig.IsAutoCloseConnection = isAuto;
if (isAuto)
{
this.Context.Close();
}
}
}
private async Task _SubQueryAsync<TResult>(List<TResult> result)
{
var isSubToList = this.QueryBuilder.SubToListParameters != null && this.QueryBuilder.SubToListParameters.Any();
if (!isSubToList)
{
return;
}
await Task.Run(() =>{_SubQuery(result);});
}
public List<Type> SubQueryList<Type>(string sql,object parameters)
{
return this.Context.Ado.SqlQuery<Type>(sql,parameters);
}
#endregion
}
}

View File

@@ -33,6 +33,7 @@ namespace SqlSugar
#endregion
#region Splicing basic
public Dictionary<string, object> SubToListParameters { get; set; }
public bool IsCrossQueryWithAttr { get; set; }
public Dictionary<string,string> CrossQueryItems { get; set; }
public bool IsSelectSingleFiledJson { get; set; }

View File

@@ -135,6 +135,14 @@ namespace SqlSugar
var value = GetNewExpressionValue(item);
parameter.Context.Result.Append($" {value} AS {asName} ");
}
else if (IsSubToList(item))
{
var value = GetNewExpressionValue(item);
if (this.Context.SugarContext.QueryBuilder.SubToListParameters == null)
this.Context.SugarContext.QueryBuilder.SubToListParameters = new Dictionary<string, object>();
this.Context.SugarContext.QueryBuilder.SubToListParameters.Add(asName, value);
//throw new Exception("子查询ToList开发中..");
}
else
{
asName = GetAsNameResolveAnObject(parameter, item, asName, isSameType);

View File

@@ -12,6 +12,21 @@ namespace SqlSugar
public partial class BaseResolve
{
private static bool IsSubToList(Expression item)
{
return ExpressionTool.GetMethodName(item) == "ToList" && IsSubquery(item);
}
private static bool IsSubquery(Expression item)
{
var method = (item as MethodCallExpression);
if (method == null)
return false;
if (method.Object == null)
return false;
return method.Object.Type.Name.StartsWith("Subquery");
}
private bool IsExtSqlFuncObj(Expression item)
{
return this.Context.SqlFuncServices != null && item is MethodCallExpression && this.Context.SqlFuncServices.Any(it => it.UniqueMethodName == ExpressionTool.GetMethodName(item));

View File

@@ -0,0 +1,107 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Linq.Expressions;
using System.Text;
using System.Threading.Tasks;
namespace SqlSugar
{
public class SubToList:ISubOperation
{
public bool HasWhere
{
get; set;
}
public string Name
{
get
{
return "ToList";
}
}
public Expression Expression
{
get; set;
}
public int Sort
{
get
{
return 200;
}
}
public ExpressionContext Context
{
get; set;
}
public string GetValue(Expression expression = null)
{;
var exp = expression as MethodCallExpression;
InitType(exp);
if (exp.Arguments.Count == 0)
return "*";
var argExp = exp.Arguments[0];
var parametres = (argExp as LambdaExpression).Parameters;
if ((argExp as LambdaExpression).Body is UnaryExpression)
{
argExp = ((argExp as LambdaExpression).Body as UnaryExpression).Operand;
}
var argLambda = argExp as LambdaExpression;
var copyContext = this.Context.GetCopyContextWithMapping();
copyContext.Resolve(argLambda, ResolveExpressType.SelectMultiple);
var select= copyContext.Result.GetString();
this.Context.Parameters.AddRange(copyContext.Parameters);
this.Context.Index = copyContext.Index;
this.Context.ParameterIndex = copyContext.ParameterIndex;
SetShortName(exp, null);
return select;
}
private void InitType(MethodCallExpression exp)
{
if (exp.Arguments.Count > 0)
{
foreach (var arg in (exp.Arguments[0] as LambdaExpression).Parameters)
{
if (this.Context.InitMappingInfo != null)
{
this.Context.InitMappingInfo(arg.Type);
this.Context.RefreshMapping();
}
}
}
}
public void SetShortName(MethodCallExpression exp, string result)
{
if (exp.Arguments[0] is LambdaExpression)
{
var parameters = (exp.Arguments[0] as LambdaExpression).Parameters;
if (parameters != null && parameters.Count > 0)
{
this.Context.CurrentShortName = this.Context.GetTranslationColumnName(parameters[0].ObjToString());
}
}
}
public void SetShortNameNext(MethodCallExpression exp, string result)
{
if (exp.Arguments.Count > 1 && exp.Arguments[1] is LambdaExpression)
{
var parameters = (exp.Arguments[1] as LambdaExpression).Parameters;
if (parameters != null && parameters.Count > 0)
{
this.Context.CurrentShortName = this.Context.GetTranslationColumnName(parameters[0].ObjToString());
}
}
}
}
}

View File

@@ -37,7 +37,8 @@ namespace SqlSugar
new SubWithNolock(){ Context=Context },
new SubEnableTableFilter(){ Context=Context },
new SubSelectStringJoin{ Context=Context },
new SubDistinctCount{ Context=Context }
new SubDistinctCount{ Context=Context },
new SubToList{ Context=Context}
};
}

View File

@@ -170,5 +170,15 @@ namespace SqlSugar
{
return this;
}
public List<T> ToList()
{
return new List<T>();
}
public List<TResult> ToList<TResult>(Func<T, TResult> selector) where TResult:class,new()
{
return null;
}
}
}

View File

@@ -12,6 +12,27 @@ namespace SqlSugar
{
public class ExpressionBuilderHelper
{
public static object CallFunc(Type type, object[] param, object methodData, string methodName)
{
MethodInfo mi = methodData.GetType().GetMethod(methodName).MakeGenericMethod(new Type[] { type });
var ret = mi.Invoke(methodData, param);
return ret;
}
public static T CallFunc<T>(object param, object methodData, string methodName)
{
Type type = param.GetType();
MethodInfo mi = methodData.GetType().GetMethod(methodName).MakeGenericMethod(new Type[] { type });
var ret = mi.Invoke(methodData, new object[] { param });
return (T)ret;
}
public static T CallStaticFunc<T>(object param, Type methodType, string methodName)
{
Type type = param.GetType();
MethodInfo mi = methodType.GetMethod(methodName).MakeGenericMethod(new Type[] { type });
var ret = mi.Invoke(null, new object[] { param });
return (T)ret;
}
/// <summary>
/// Create Expression
/// </summary>