本文共 9119 字,大约阅读时间需要 30 分钟。
本教程主要说明如果使用Magicodes.IE.Excel完成学生数据的Excel导入。
在本篇教程中,我们仅演示使用Excel来完成学生数据的导入。我们需要在已准备好的工程中安装以下包,参考命令如下所示:
Install-Package Magicodes.IE.Excel
主要代码如下所示:
学生数据Dto
////// 导入学生数据Dto /// IsLabelingError:是否标注数据错误 /// [ExcelImporter(IsLabelingError = true)] public class ImportStudentDto { ////// 序号 /// [ImporterHeader(Name = "序号")] public long SerialNumber { get; set; } ////// 学籍号 /// [ImporterHeader(Name = "学籍号")] [MaxLength(30, ErrorMessage = "学籍号字数超出最大限制,请修改!")] public string StudentCode { get; set; } ////// 姓名 /// [ImporterHeader(Name = "姓名")] [Required(ErrorMessage = "学生姓名不能为空")] [MaxLength(50, ErrorMessage = "名称字数超出最大限制,请修改!")] public string Name { get; set; } ////// 身份证号码 /// [ImporterHeader(Name = "身份证号", IsAllowRepeat = false)] [Required(ErrorMessage = "身份证号不能为空")] [MaxLength(18, ErrorMessage = "身份证字数超出最大限制,请修改!")] public string IdCard { get; set; } ////// 性别 /// [ImporterHeader(Name = "性别")] [Required(ErrorMessage = "性别不能为空")] [ValueMapping("男", 0)] [ValueMapping("女", 1)] public Genders Gender { get; set; } ////// 家庭地址 /// [ImporterHeader(Name = "家庭住址")] [Required(ErrorMessage = "家庭地址不能为空")] [MaxLength(200, ErrorMessage = "家庭地址字数超出最大限制,请修改!")] public string Address { get; set; } ////// 家长姓名 /// [ImporterHeader(Name = "家长姓名")] [Required(ErrorMessage = "家长姓名不能为空")] [MaxLength(50, ErrorMessage = "家长姓名数超出最大限制,请修改!")] public string Guardian { get; set; } ////// 家长联系电话 /// [ImporterHeader(Name = "家长联系电话")] [MaxLength(20, ErrorMessage = "家长联系电话字数超出最大限制,请修改!")] public string GuardianPhone { get; set; } ////// 学号 /// [ImporterHeader(Name = "学号")] [MaxLength(30, ErrorMessage = "学号字数超出最大限制,请修改!")] public string StudentNub { get; set; } ////// 宿舍号 /// [ImporterHeader(Name = "宿舍号")] [MaxLength(20, ErrorMessage = "宿舍号字数超出最大限制,请修改!")] public string DormitoryNo { get; set; } ////// QQ /// [ImporterHeader(Name = "QQ号")] [MaxLength(30, ErrorMessage = "QQ号字数超出最大限制,请修改!")] public string QQ { get; set; } ////// 民族 /// [ImporterHeader(Name = "民族")] [MaxLength(2, ErrorMessage = "民族字数超出最大限制,请修改!")] public string Nation { get; set; } ////// 户口性质 /// [ImporterHeader(Name = "户口性质")] [MaxLength(10, ErrorMessage = "户口性质字数超出最大限制,请修改!")] public string HouseholdType { get; set; } ////// 联系电话 /// [ImporterHeader(Name = "学生联系电话")] [MaxLength(20, ErrorMessage = "手机号码字数超出最大限制,请修改!")] public string Phone { get; set; } ////// 状态 /// 测试可为空的枚举类型 /// [ImporterHeader(Name = "状态")] public StudentStatus? Status { get; set; } ////// 备注 /// [ImporterHeader(Name = "备注")] [MaxLength(200, ErrorMessage = "备注字数超出最大限制,请修改!")] public string Remark { get; set; } ////// 是否住校(宿舍) /// [ImporterHeader(IsIgnore = true)] public bool? IsBoarding { get; set; } ////// 所属班级id /// [ImporterHeader(IsIgnore = true)] public Guid ClassId { get; set; } ////// 学校Id /// [ImporterHeader(IsIgnore = true)] public Guid? SchoolId { get; set; } ////// 校区Id /// [ImporterHeader(IsIgnore = true)] public Guid? CampusId { get; set; } ////// 专业Id /// [ImporterHeader(IsIgnore = true)] public Guid? MajorsId { get; set; } ////// 年级Id /// [ImporterHeader(IsIgnore = true)] public Guid? GradeId { get; set; } }
如上述代码所示,我们定义了以上学生数据Dto,主要注意事项如下:
性别枚举
定义如下所示:
////// 性别/// public enum Genders{ ////// 男 /// Man = 0, ////// 女 /// Female = 1}
注意上文中的第7点。
////// 学生状态 正常、流失、休学、勤工俭学、顶岗实习、毕业、参军/// public enum StudentStatus{ ////// 正常 /// [Display(Name = "正常")] Normal = 0, ////// 流失 /// [Description("流水")] PupilsAway = 1, ////// 休学 /// [Display(Name = "休学")] Suspension = 2, ////// 勤工俭学 /// [Display(Name = "勤工俭学")] WorkStudy = 3, ////// 顶岗实习 /// [Display(Name = "顶岗实习")] PostPractice = 4, ////// 毕业 /// [Display(Name = "毕业")] Graduation = 5, ////// 参军 /// [Display(Name = "参军")] JoinTheArmy = 6}
注意上文中的第7点。
导入之前是不是得准备一份模板?对于我们,手写模板?这是不存在的。Magicodes.IE.Excel封装了根据DTO自动生成Excel导入模板的方法,我们可以直接调用。这里我们来看下导入的相关方法:
////// 导入/// public interface IImporter{ ////// 生成Excel导入模板 /// ////// Task GenerateTemplate (string fileName) where T : class, new(); /// /// 生成Excel导入模板 /// ////// 二进制字节 TaskGenerateTemplateBytes () where T : class, new(); /// /// 导入模型验证数据 /// ////// /// Task > Import (string filePath) where T : class, new();}
通过以上方法中的GenerateTemplate,我们可以得到需要的导入模板。具体使用可以参考以下单元测试:
public IImporter Importer = new ExcelImporter(); [Fact(DisplayName = "生成学生数据导入模板(测试枚举生成模板)")] public async Task GenerateStudentImportTemplate_Test() { var filePath = Path.Combine(Directory.GetCurrentDirectory(), nameof(GenerateStudentImportTemplate_Test) + ".xlsx"); if (File.Exists(filePath)) File.Delete(filePath); var result = await Importer.GenerateTemplate(filePath); result.ShouldNotBeNull(); File.Exists(filePath).ShouldBeTrue(); //TODO:读取Excel检查表头和格式 }
以上DTO获取模板并填充数据后如下图所示:
注意:枚举会自动生成下拉选择,必填项列头会标红。
根据模板填充数据后,我们就可以进行数据导入了。通常情况下,我们有以下步骤:
验证导入数据
通过Magicodes.IE.Excel导入数据会自动进行验证,并且输出验证结果,以便于前台显示。具体我们可以通过其导入的结果类来了解:
////// 导入结果/// public class ImportResultwhere T : class{ /// /// public ImportResult() { RowErrors = new List(); } /// /// 导入数据 /// public virtual ICollectionData { get; set; } /// /// 验证错误 /// public virtual IListRowErrors { get; set; } /// /// 模板错误 /// public virtual IListTemplateErrors { get; set; } /// /// 导入异常信息 /// public virtual Exception Exception { get; set; } ////// 是否存在导入错误 /// public virtual bool HasError => Exception != null || (TemplateErrors?.Count(p => p.ErrorLevel == ErrorLevels.Error) ?? 0) > 0 || (RowErrors?.Count ?? 0) > 0;}
其中,
Data为数据结果
RowErrors为验证错误,比如必填、重复验证、文本长度等等。会给出行号、字段以及字段错误集合
TemplateErrors为模板错误,比如必填列缺失等错误信息。支持错误等级(警告、错误)
Exception为导入异常信息
HasError为是否存在错误(不包含警告)
通过ImportResult,我们就可以很方便的拿到导入验证错误而无须额外编写代码。通常在导入时我们需要判断HasError属性并给前台返回具体的错误结果。
数据导入参考代码如下所示:
[Fact(DisplayName = "学生基础数据导入")] public async Task StudentInfoImporter_Test() { var filePath = Path.Combine(Directory.GetCurrentDirectory(), "TestFiles", "Import", "学生基础数据导入.xlsx"); var import = await Importer.Import(filePath); import.ShouldNotBeNull(); if (import.Exception != null) _testOutputHelper.WriteLine(import.Exception.ToString()); if (import.RowErrors.Count > 0) _testOutputHelper.WriteLine(JsonConvert.SerializeObject(import.RowErrors)); import.HasError.ShouldBeFalse(); import.Data.ShouldNotBeNull(); import.Data.Count.ShouldBe(16); }
客户说虽然你提示了,但是我还是不知道哪里错了!!怎么办?!!
我们贴心的为你准备了导入数据的Excel文件的标注:
如何开启这个【史诗剧情】呢?仅需:
[ExcelImporter(IsLabelingError = true)]
开启后,我们将自动保存“{目标文件名称}_.xlsx”的标注文件到目标位置。
没有错误了?也就是HasError为false,那么我们就可以直接拿到Data为所欲为了!
整个学生数据的导入教程就此结束了。相关库会一直更新,在功能体验上有可能会和本文教程有细微的出入,请以相关具体代码、版本日志、单元测试示例为准。
转载地址:http://xzgkz.baihongyu.com/