From c9aa3353fb36d7be8759d9d254e5a3ef49d2f722 Mon Sep 17 00:00:00 2001 From: d4ilys <963922242@qq.com> Date: Thu, 17 Aug 2023 11:51:36 +0800 Subject: [PATCH] =?UTF-8?q?=E4=BF=AE=E5=A4=8DDynamicEntity=E7=89=B9?= =?UTF-8?q?=E6=80=A7=E6=9E=84=E9=80=A0=E5=87=BD=E6=95=B0=E5=AE=9E=E4=BE=8B?= =?UTF-8?q?=E5=8C=96=E9=97=AE=E9=A2=98?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../DynamicEntity/DynamicEntityTest.cs | 43 +++++++++++++++++++ FreeSql/Extensions/DynamicEntityExtensions.cs | 27 ++++++++---- 2 files changed, 62 insertions(+), 8 deletions(-) diff --git a/FreeSql.Tests/FreeSql.Tests/DynamicEntity/DynamicEntityTest.cs b/FreeSql.Tests/FreeSql.Tests/DynamicEntity/DynamicEntityTest.cs index ec135fcb8..113e50799 100644 --- a/FreeSql.Tests/FreeSql.Tests/DynamicEntity/DynamicEntityTest.cs +++ b/FreeSql.Tests/FreeSql.Tests/DynamicEntity/DynamicEntityTest.cs @@ -194,8 +194,51 @@ public void DefaultValueTest() fsql.Insert().AsType(table.Type).AppendData(instance).ExecuteAffrows(); var objects = fsql.Select().AsType(table.Type).ToList(); } + + [Fact] + public void Issue1591Test() + { + var backupTableName = "test"; + var newTableName = "new_test"; + var key = "index_key"; + var columns = new List() + { + "Name", + "Tid" + }; + var attributes = new List(); + attributes.Add(new TableAttribute() { Name = newTableName }); + + var indexName = key.ToUpper().Replace(backupTableName.ToUpper(), newTableName.ToUpper()); + var indexFields = string.Join(",", columns.Select(c => c)); + var indexAttribute = new IndexAttribute(indexName, indexFields + , false); + attributes.Add(indexAttribute); + + var table = fsql.CodeFirst.DynamicEntity("AttributeUsers", attributes.ToArray()) + .Property("Id", typeof(int), + new ColumnAttribute() { IsPrimary = true, IsIdentity = true, Position = 1 }) + .Property("Name", typeof(string), + new ColumnAttribute() { StringLength = 20, Position = 2 }) + .Property("Tid", typeof(string), + new ColumnAttribute() { StringLength = 20, Position = 4 }) + .Property("Address", typeof(string), + new ColumnAttribute() { StringLength = 150, Position = 3 }) + .Build(); + var dict = new Dictionary + { + ["Name"] = "张三", + ["Address"] = "北京市" + }; + var instance = table.CreateInstance(dict); + //根据Type生成表 + fsql.CodeFirst.SyncStructure(table.Type); + var insertId = fsql.Insert().AsType(table.Type).AppendData(instance).ExecuteIdentity(); + var select = fsql.Select().AsType(table.Type).ToList(); + } } + public class BaseModel { [Column(Position = 99)] public DateTime UpdateTime { get; set; } diff --git a/FreeSql/Extensions/DynamicEntityExtensions.cs b/FreeSql/Extensions/DynamicEntityExtensions.cs index 458737204..00bfbe7a8 100644 --- a/FreeSql/Extensions/DynamicEntityExtensions.cs +++ b/FreeSql/Extensions/DynamicEntityExtensions.cs @@ -49,6 +49,7 @@ public static object CreateInstance(this TableInfo table, Dictionary p.CanWrite == true).ToArray(); - foreach (var propertyInfo in propertyInfos) propertyValues.Add(propertyInfo.GetValue(tableAttribute)); - - //可能存在有参构造 - if (classCtorInfo == null) + //是否存在有参构造函数 + var existConstructorArguments = classCtorInfos.Any(c => c.GetParameters().Length > 0); + if (existConstructorArguments) { - var constructorTypes = propertyInfos.Select(p => p.PropertyType); - classCtorInfo = tableAttribute.GetType().GetConstructor(constructorTypes.ToArray()); - var customAttributeBuilder = new CustomAttributeBuilder(classCtorInfo, propertyValues.ToArray()); + var defaultParamsCtor = classCtorInfos.Where(c => c.GetParameters().Length > 0) + .OrderBy(c => c.GetParameters().Length).First(); + //获取参数默认值 + var defaultParams = new List(); + foreach (var parameterInfo in defaultParamsCtor.GetParameters()) + { + defaultParams.Add(parameterInfo.ParameterType.CreateInstanceGetDefaultValue()); + } + + //思路:先通过构造函数的默认值实例化对象,然后通过属性的方式赋值 + var customAttributeBuilder = new CustomAttributeBuilder(defaultParamsCtor, defaultParams.ToArray(), + propertyInfos, + propertyValues.ToArray()); typeBuilder.SetCustomAttribute(customAttributeBuilder); } else { + //不存在构造函数赋值直接属性赋值 var customAttributeBuilder = new CustomAttributeBuilder(classCtorInfo, new object[0], propertyInfos, propertyValues.ToArray()); typeBuilder.SetCustomAttribute(customAttributeBuilder);