Magicodes.IE已支持導出Word、Pdf和Html
- 2019 年 11 月 5 日
- 筆記
關於Magicodes.IE
導入導出通用庫,通過導入導出DTO模型來控制導入和導出,支持Excel、Word、Pdf和Html。
GitHub地址:https://github.com/xin-lai/Magicodes.IE
特點
- 導入支持數據下拉選擇,目前僅支持枚舉類型;
- 導入數據支持前後空格以及中間空格處理,允許指定列進行設置;
- 導入支持模板自動檢查,數據自動校驗,異常統一處理,並提供統一的錯誤封裝,包含異常、模板錯誤和行數據錯誤;
- 支持單個數據模板導出,常用於導出收據、憑據等業務
- 支持動態列導出(基於DataTable),感謝張善友(https://github.com/xin-lai/Magicodes.IE/pull/8)
相關官方Nuget包
聯繫我們
訂閱號
關注“麥扣聊技術”訂閱號可以獲得最新文章、教程、文檔:
QQ群
-
編程交流群<85318032>
-
產品交流群<897857351>
文檔官網&官方博客
其他開源庫
VNext
- 生成導入模板時必填項支持自定義樣式配置
- CSV支持
- 導入結果支持生成HTML輸出
更新歷史
2019.10.30
- 【Nuget】版本更新到1.4.0
- 【導出】Excel導出支持動態列導出(基於DataTable),感謝張善友(https://github.com/xin-lai/Magicodes.IE/pull/8)
2019.10.22
- 【Nuget】版本更新到1.3.7
- 【導入】修復忽略列的驗證問題
- 【導入】修正驗證錯誤信息,一行僅允許存在一條數據
- 【導入】修復忽略列在某些情況下可能引發的異常
- 【導入】添加存在忽略列的導入情形下的單元測試
2019.10.21
- 【Nuget】版本更新到1.3.4
- 【導入】支持設置忽略列,以便於在Dto定義數據列做處理或映射
2019.10.18
- 【優化】優化.NET標準庫2.1下集合轉DataTable的性能
- 【重構】多處IList修改為ICollection
- 【完善】補充部分單元測試
2019.10.12
- 【重構】重構HTML、PDF導出等邏輯,並修改IExporterByTemplate為:
- Task ExportListByTemplate(IList dataItems, string htmlTemplate = null) where T : class;
- Task ExportByTemplate(T data, string htmlTemplate = null) where T : class;
- 【示例】添加收據導出的單元測試示例
2019.9.28
- 【導出】修改默認的導出HTML、Word、Pdf模板
- 【導入】添加截斷行的單元測試,以測試中間空格和結尾空格
- 【導入】將【數據錯誤檢測】和【導入】單元測試的Dto分開,確保全部單元測試通過
- 【文檔】更新文檔
2019.9.26
- 【導出】支持導出Word、Pdf、HTML,支持自定義導出模板
- 【導出】添加相關導出的單元測試
- 【導入】支持重複驗證,需設置ImporterHeader特性的IsAllowRepeat為false
2019.9.19
- 【導入】支持截止列設置,如未設置則默認遇到空格截止
- 【導入】導入支持通過特性設置Sheet名稱
2019.9.18
- 【導入】重構導入模塊
- 【導入】統一導入錯誤消息
- Exception :導入異常信息
- RowErrors : 數據錯誤信息
- TemplateErrors :模板錯誤信息,支持錯誤分級
- HasError : 是否存在錯誤(僅當出現異常並且錯誤等級為Error時返回true)
- 【導入】基礎類型必填自動識別,比如int、double等不可為空類型自動識別,無需額外設置Required
- 【導入】修改Excel模板的Sheet名稱
- 【導入】支持導入表頭位置設置,默認為1
- 【導入】支持列亂序(導入模板的列序號不再需要固定)
- 【導入】支持列索引設置
- 【導入】支持將導入的Excel進行錯誤標註,支持多個錯誤
- 【導入】加強對基礎類型和可為空類型的支持
- 【EPPlus】由於EPPlus.Core已經不維護,將EPPlus的包從EPPlus.Core改為EPPlus,
2019.9.11
- 【導入】導入支持自動去除前後空格,默認啟用,可以針對列進行關閉,具體見AutoTrim設置
- 【導入】導入Dto的字段允許不設置ImporterHeader,支持通過DisplayAttribute特性獲取列名
- 【導入】導入的Excel移除對Sheet名稱的約束,默認獲取第一個Sheet
- 【導入】導入增加對中間空格的處理支持,需設置FixAllSpace
- 【導入】導入完善對日期類型的支持
- 【導入】完善導入的單元測試
導出 Demo
Demo1-1
普通導出 
public class ExportTestData { public string Name1 { get; set; } public string Name2 { get; set; } public string Name3 { get; set; } public string Name4 { get; set; } } var result = await Exporter.Export(filePath, new List<ExportTestData>() { new ExportTestData() { Name1 = "1", Name2 = "test", Name3 = "12", Name4 = "11", }, new ExportTestData() { Name1 = "1", Name2 = "test", Name3 = "12", Name4 = "11", } });
Demo1-2
特性導出 
[ExcelExporter(Name = "測試", TableStyle = "Light10")] public class ExportTestDataWithAttrs { [ExporterHeader(DisplayName = "加粗文本", IsBold = true)] public string Text { get; set; } [ExporterHeader(DisplayName = "普通文本")] public string Text2 { get; set; } [ExporterHeader(DisplayName = "忽略", IsIgnore = true)] public string Text3 { get; set; } [ExporterHeader(DisplayName = "數值", Format = "#,##0")] public double Number { get; set; } [ExporterHeader(DisplayName = "名稱", IsAutoFit = true)] public string Name { get; set; } } var result = await Exporter.Export(filePath, new List<ExportTestDataWithAttrs>() { new ExportTestDataWithAttrs() { Text = "啊實打實大蘇打撒", Name="aa", Number =5000, Text2 = "w薩達薩達薩達撒", Text3 = "sadsad打發打發士大夫的" }, new ExportTestDataWithAttrs() { Text = "啊實打實大蘇打撒", Name="啊實打實大蘇打撒", Number =6000, Text2 = "w薩達薩達薩達撒", Text3 = "sadsad打發打發士大夫的" }, new ExportTestDataWithAttrs() { Text = "啊實打實速度大蘇打撒", Name="薩達薩達", Number =6000, Text2 = "突然他也讓他人", Text3 = "sadsad打發打發士大夫的" }, });
Demo1-3
列頭處理或者多語言支持 
[ExcelExporter(Name = "測試", TableStyle = "Light10")] public class AttrsLocalizationTestData { [ExporterHeader(DisplayName = "加粗文本", IsBold = true)] public string Text { get; set; } [ExporterHeader(DisplayName = "普通文本")] public string Text2 { get; set; } [ExporterHeader(DisplayName = "忽略", IsIgnore = true)] public string Text3 { get; set; } [ExporterHeader(DisplayName = "數值", Format = "#,##0")] public double Number { get; set; } [ExporterHeader(DisplayName = "名稱", IsAutoFit = true)] public string Name { get; set; } } ExcelBuilder.Create().WithLocalStringFunc((key) => { if (key.Contains("文本")) { return "Text"; } return "未知語言"; }).Build(); var filePath = Path.Combine(Directory.GetCurrentDirectory(), "testAttrsLocalization.xlsx"); if (File.Exists(filePath)) File.Delete(filePath); var result = await Exporter.Export(filePath, new List<AttrsLocalizationTestData>() { new AttrsLocalizationTestData() { Text = "啊實打實大蘇打撒", Name="aa", Number =5000, Text2 = "w薩達薩達薩達撒", Text3 = "sadsad打發打發士大夫的" }, new AttrsLocalizationTestData() { Text = "啊實打實大蘇打撒", Name="啊實打實大蘇打撒", Number =6000, Text2 = "w薩達薩達薩達撒", Text3 = "sadsad打發打發士大夫的" }, new AttrsLocalizationTestData() { Text = "啊實打實速度大蘇打撒", Name="薩達薩達", Number =6000, Text2 = "突然他也讓他人", Text3 = "sadsad打發打發士大夫的" }, });
導入 Demo
導入特性(ImporterAttribute):
- HeaderRowIndex:表頭位置
導入列頭特性(ImporterHeader):
- Name:表頭顯示名稱(不可為空)。
- Description:表頭添加註釋。
- Author:注釋作者,默認值為“麥扣”。
- AutoTrim:自動過濾空格,默認啟用。
- FixAllSpace:處理掉所有的空格,包括中間空格。默認false。
- ColumnIndex:列索引,一般不建議設置。
導入結果(ImportResult):
- Data:IList<T> 導入的數據集合。
- RowErrors:IList 數據行錯誤。
- HasError:bool 是否存在導入錯誤。
- Exception:異常信息
- TemplateErrors:模板錯誤信息
Demo2-1 普通模板
生成模板
public class ImportProductDto { /// <summary> /// 產品名稱 /// </summary> [ImporterHeader(Name = "產品名稱")] public string Name { get; set; } /// <summary> /// 產品代碼 /// </summary> [ImporterHeader(Name = "產品代碼")] public string Code { get; set; } /// <summary> /// 產品條碼 /// </summary> [ImporterHeader(Name = "產品條碼")] public string BarCode { get; set; } }
導入模板
Demo2-2 多數據類型
生成模板
public class ImportProductDto { /// <summary> /// 產品名稱 /// </summary> [ImporterHeader(Name = "產品名稱")] public string Name { get; set; } /// <summary> /// 產品代碼 /// </summary> [ImporterHeader(Name = "產品代碼")] public string Code { get; set; } /// <summary> /// 產品條碼 /// </summary> [ImporterHeader(Name = "產品條碼")] public string BarCode { get; set; } /// <summary> /// 客戶Id /// </summary> [ImporterHeader(Name = "客戶代碼")] public long ClientId { get; set; } /// <summary> /// 產品型號 /// </summary> [ImporterHeader(Name = "產品型號")] public string Model { get; set; } /// <summary> /// 申報價值 /// </summary> [ImporterHeader(Name = "申報價值")] public double DeclareValue { get; set; } /// <summary> /// 貨幣單位 /// </summary> [ImporterHeader(Name = "貨幣單位")] public string CurrencyUnit { get; set; } /// <summary> /// 品牌名稱 /// </summary> [ImporterHeader(Name = "品牌名稱")] public string BrandName { get; set; } /// <summary> /// 尺寸 /// </summary> [ImporterHeader(Name = "尺寸(長x寬x高)")] public string Size { get; set; } /// <summary> /// 重量 /// </summary> [ImporterHeader(Name = "重量(KG)")] public double Weight { get; set; } /// <summary> /// 類型 /// </summary> [ImporterHeader(Name = "類型")] public ImporterProductType Type { get; set; } /// <summary> /// 是否行 /// </summary> [ImporterHeader(Name = "是否行")] public bool IsOk { get; set; } }
public enum ImporterProductType { [Display(Name = "第一")] One, [Display(Name = "第二")] Two }
導入模板
Demo2-3 數據驗證
生成模板
必填項表頭文本為紅色 
public class ImportProductDto { /// <summary> /// 產品名稱 /// </summary> [ImporterHeader(Name = "產品名稱",Description ="必填")] [Required(ErrorMessage = "產品名稱是必填的")] public string Name { get; set; } /// <summary> /// 產品代碼 /// </summary> [ImporterHeader(Name = "產品代碼", Description = "最大長度為8")] [MaxLength(8,ErrorMessage = "產品代碼最大長度為8")] public string Code { get; set; } /// <summary> /// 產品條碼 /// </summary> [ImporterHeader(Name = "產品條碼")] [MaxLength(10, ErrorMessage = "產品條碼最大長度為10")] [RegularExpression(@"^d*$", ErrorMessage = "產品條碼只能是數字")] public string BarCode { get; set; } /// <summary> /// 客戶Id /// </summary> [ImporterHeader(Name = "客戶代碼")] public long ClientId { get; set; } /// <summary> /// 產品型號 /// </summary> [ImporterHeader(Name = "產品型號")] public string Model { get; set; } /// <summary> /// 申報價值 /// </summary> [ImporterHeader(Name = "申報價值")] public double DeclareValue { get; set; } /// <summary> /// 貨幣單位 /// </summary> [ImporterHeader(Name = "貨幣單位")] public string CurrencyUnit { get; set; } /// <summary> /// 品牌名稱 /// </summary> [ImporterHeader(Name = "品牌名稱")] public string BrandName { get; set; } /// <summary> /// 尺寸 /// </summary> [ImporterHeader(Name = "尺寸(長x寬x高)")] public string Size { get; set; } /// <summary> /// 重量 /// </summary> [ImporterHeader(Name = "重量(KG)")] public double Weight { get; set; } /// <summary> /// 類型 /// </summary> [ImporterHeader(Name = "類型")] public ImporterProductType Type { get; set; } /// <summary> /// 是否行 /// </summary> [ImporterHeader(Name = "是否行")] public bool IsOk { get; set; } }
public enum ImporterProductType { [Display(Name = "第一")] One, [Display(Name = "第二")] Two }
導入模板
Docker中使用
- 如果是使用Excel導出,則需安裝libgdiplus庫
# 安裝libgdiplus庫,用於Excel導出 RUN apt-get update && apt-get install -y libgdiplus libc6-dev RUN ln -s /usr/lib/libgdiplus.so /usr/lib/gdiplus.dll
Dockerfile Demo
FROM microsoft/dotnet:2.2-aspnetcore-runtime AS base # 安裝libgdiplus庫,用於Excel導出 RUN apt-get update && apt-get install -y libgdiplus libc6-dev RUN ln -s /usr/lib/libgdiplus.so /usr/lib/gdiplus.dll WORKDIR /app EXPOSE 80 FROM microsoft/dotnet:2.2-sdk AS build WORKDIR /src COPY ["src/web/Admin.Host/Admin.Host.csproj", "src/web/Admin.Host/"] COPY ["src/web/Admin.Web.Core/Admin.Web.Core.csproj", "src/web/Admin.Web.Core/"] COPY ["src/application/Admin.Application/Admin.Application.csproj", "src/application/Admin.Application/"] COPY ["src/core/Magicodes.Admin.Core/Magicodes.Admin.Core.csproj", "src/core/Magicodes.Admin.Core/"] COPY ["src/data/Magicodes.Admin.EntityFrameworkCore/Magicodes.Admin.EntityFrameworkCore.csproj", "src/data/Magicodes.Admin.EntityFrameworkCore/"] COPY ["src/core/Magicodes.Admin.Core.Custom/Magicodes.Admin.Core.Custom.csproj", "src/core/Magicodes.Admin.Core.Custom/"] COPY ["src/application/Admin.Application.Custom/Admin.Application.Custom.csproj", "src/application/Admin.Application.Custom/"] RUN dotnet restore "src/web/Admin.Host/Admin.Host.csproj" COPY . . WORKDIR "/src/src/web/Admin.Host" RUN dotnet build "Admin.Host.csproj" -c Release -o /app FROM build AS publish RUN dotnet publish "Admin.Host.csproj" -c Release -o /app FROM base AS final WORKDIR /app COPY --from=publish /app . ENTRYPOINT ["dotnet", "Magicodes.Admin.Web.Host.dll"]
- 如果是使用Pdf導出,則需安裝相關字體,如:
# 安裝fontconfig庫,用於Pdf導出 RUN apt-get update && apt-get install -y fontconfig COPY /simsun.ttc /usr/share/fonts/simsun.ttc