我使用ClosedXM具有Excel导入功能,并且使用activator . createinstance (typeof(T))遇到错误。又:
系统。不能动态创建类型的实例"FSH.WebApi.Domain.Catalog.Brand"。原因:没有定义无参数构造函数
请帮忙!!
// Controller
[HttpPost("import")]
public async Task<ActionResult<int>> ImportAsync(ImportBrandsRequest request)
{
IList<Brand> result = new List<Brand>();
result = await _excelReader.ImportAsync<Brand>(request.ExcelFile, FileType.Excel);
return Ok(result.Count);
}
// Interface
public interface IExcelReader : ITransientService
{
Task<IList<T>> ImportAsync<T>(
FileUploadRequest request,
FileType supportedFileType,
string sheetName = "Sheet1");
}
// Service:
public class ExcelReader : IExcelReader
{
public async Task<IList<T>> ImportAsync<T>(FileUploadRequest request, FileType supportedFileType, string sheetName = "Sheet1")
{
var streamData = new MemoryStream(Convert.FromBase64String(base64Data));
List<T> list = new List<T>();
Type typeOfObject = typeof(T);
using (IXLWorkbook workbook = new XLWorkbook(streamData))
{
var worksheet = workbook.Worksheets.First(w => w.Name == sheetName);
PropertyDescriptorCollection properties = TypeDescriptor.GetProperties(typeof(T));
// header column texts
var columns = worksheet.FirstRow().Cells().Select((v, i) => new { v.Value, Index = i + 1 });
// indexing in closedxml starts with 1 not from 0
// Skip first row which is used for column header texts
foreach (IXLRow row in worksheet.RowsUsed().Skip(1))
{
T item = (T)Activator.CreateInstance(typeof(T));
// T item = (T)Activator.CreateInstance(typeof(T));
foreach (PropertyDescriptor prop in properties)
{
int colIndex = columns.Single(
c => c.Value.ToString() == prop.Name).Index;
if (colIndex == 0) continue;
object? val = row.Cell(colIndex).Value;
var type = prop.PropertyType;
prop.SetValue(item, Convert.ChangeType(val, type));
}
if (item != null) list.Add(item);
}
}
return await Task.FromResult(list);
}
可以推测,Brand
没有没有参数的构造函数。因此,要么为Brand
添加无参数构造函数,要么将参数参数传递给Activator.CreateInstance
。