List导出到Excel文件
例如用户列表导出
using System.Collections.Generic;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Mvc;
using Admin.Web.Controllers;
using Business.OrganizationManage;
using Entity.OrganizationManage;
using Model.Param.OrganizationManage;
using Util;
using Util.Model;namespace Admin.Web.Areas.OrganizationManage.Controllers
{[Area("OrganizationManage")]public class UserController : BaseController{private UserBLL userBLL = new UserBLL();[HttpPost]public async Task<IActionResult> ExportUserJson(UserListParam param){TData<string> obj = new TData<string>();TData<List<UserEntity>> userObj = await userBLL.GetList(param);if (userObj.Tag == 1){string file = new ExcelHelper<UserEntity>().ExportToExcel("用户列表.xls","用户列表",userObj.Data,new string[] { "UserName", "RealName", "Gender", "Mobile", "Email" });obj.Data = file;obj.Tag = 1;}return Json(obj);}}
}
用户实体类
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.ComponentModel.DataAnnotations.Schema;
using System.Linq;
using System.Numerics;
using System.Text;
using System.Threading.Tasks;
using Newtonsoft.Json;namespace Entity.OrganizationManage
{[Table("SysUser")]public class UserEntity : BaseExtensionEntity{[Description("用户名")]public string UserName { get; set; }public string Password { get; set; }[JsonIgnore]public string Salt { get; set; }[Description("真实姓名")]public string RealName { get; set; }[Description("性别")]public int? Gender { get; set; }public string Birthday { get; set; }public string Portrait { get; set; }public string Email { get; set; }[Description("手机号")]public string Mobile { get; set; }public string QQ { get; set; }public string Wechat { get; set; }public int? LoginCount { get; set; }public int? UserStatus { get; set; }/// <summary>/// 角色Id/// </summary>[NotMapped]public string RoleIds { get; set; }}
}
ExportToExcel方法如下:
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.IO;
using System.Linq;
using System.Reflection;
using NPOI.HSSF.UserModel;
using NPOI.XSSF.UserModel;
using NPOI.SS.UserModel;
using NPOI.SS.Util;namespace Util
{/// <summary>/// List导出到Excel文件/// </summary>/// <typeparam name="T"></typeparam>public class ExcelHelper<T> where T : new(){#region List导出到Excel文件/// <summary>/// List导出到Excel文件/// </summary>/// <param name="sFileName"></param>/// <param name="sHeaderText"></param>/// <param name="list"></param>public string ExportToExcel(string sFileName, string sHeaderText, List<T> list, string[] columns){sFileName = string.Format("{0}_{1}", SecurityHelper.GetGuid(), sFileName);string sRoot = GlobalContext.HostingEnvironment.ContentRootPath;string partDirectory = string.Format("Resource{0}Export{0}Excel", Path.DirectorySeparatorChar);string sDirectory = Path.Combine(sRoot, partDirectory);string sFilePath = Path.Combine(sDirectory, sFileName);if (!Directory.Exists(sDirectory)){Directory.CreateDirectory(sDirectory);}using (MemoryStream ms = CreateExportMemoryStream(list, sHeaderText, columns)){using (FileStream fs = new FileStream(sFilePath, FileMode.Create, FileAccess.Write)){byte[] data = ms.ToArray();fs.Write(data, 0, data.Length);fs.Flush();}}return partDirectory + Path.DirectorySeparatorChar + sFileName;}/// <summary> /// List导出到Excel的MemoryStream /// </summary> /// <param name="list">数据源</param> /// <param name="sHeaderText">表头文本</param> /// <param name="columns">需要导出的属性</param> private MemoryStream CreateExportMemoryStream(List<T> list, string sHeaderText, string[] columns){HSSFWorkbook workbook = new HSSFWorkbook();ISheet sheet = workbook.CreateSheet();Type type = typeof(T);PropertyInfo[] properties = ReflectionHelper.GetProperties(type, columns);ICellStyle dateStyle = workbook.CreateCellStyle();IDataFormat format = workbook.CreateDataFormat();dateStyle.DataFormat = format.GetFormat("yyyy-MM-dd");//单元格填充循环外设定单元格格式,避免4000行异常ICellStyle contentStyle = workbook.CreateCellStyle();contentStyle.Alignment = HorizontalAlignment.Left;contentStyle.WrapText = true;contentStyle.VerticalAlignment = VerticalAlignment.Center;#region 取得每列的列宽(最大宽度)int[] arrColWidth = new int[properties.Length];for (int columnIndex = 0; columnIndex < properties.Length; columnIndex++){//GBK对应的code page是CP936arrColWidth[columnIndex] = properties[columnIndex].Name.Length;}#endregionfor (int rowIndex = 0; rowIndex < list.Count; rowIndex++){#region 新建表,填充表头,填充列头,样式if (rowIndex == 65535 || rowIndex == 0){if (rowIndex != 0){sheet = workbook.CreateSheet();}#region 表头及样式{IRow headerRow = sheet.CreateRow(0);headerRow.HeightInPoints = 25;headerRow.CreateCell(0).SetCellValue(sHeaderText);ICellStyle headStyle = workbook.CreateCellStyle();headStyle.Alignment = HorizontalAlignment.Center;IFont font = workbook.CreateFont();font.FontHeightInPoints = 20;font.Boldweight = 700;headStyle.SetFont(font);headerRow.GetCell(0).CellStyle = headStyle;sheet.AddMergedRegion(new CellRangeAddress(0, 0, 0, properties.Length - 1));}#endregion#region 列头及样式{IRow headerRow = sheet.CreateRow(1);ICellStyle headStyle = workbook.CreateCellStyle();headStyle.Alignment = HorizontalAlignment.Center;IFont font = workbook.CreateFont();font.FontHeightInPoints = 10;font.Boldweight = 700;headStyle.SetFont(font);for (int columnIndex = 0; columnIndex < properties.Length; columnIndex++){// 类属性如果有Description就用Description当做列名DescriptionAttribute customAttribute = (DescriptionAttribute)Attribute.GetCustomAttribute(properties[columnIndex], typeof(DescriptionAttribute));string description = properties[columnIndex].Name;if (customAttribute != null){description = customAttribute.Description;}headerRow.CreateCell(columnIndex).SetCellValue(description);headerRow.GetCell(columnIndex).CellStyle = headStyle;//根据表头设置列宽 sheet.SetColumnWidth(columnIndex, (arrColWidth[columnIndex] + 1) * 256);}}#endregion}#endregion#region 填充内容IRow dataRow = sheet.CreateRow(rowIndex + 2); // 前面2行已被占用for (int columnIndex = 0; columnIndex < properties.Length; columnIndex++){ICell newCell = dataRow.CreateCell(columnIndex);newCell.CellStyle = contentStyle;string drValue = properties[columnIndex].GetValue(list[rowIndex], null).ParseToString();//根据单元格内容设定列宽int length = (System.Text.Encoding.UTF8.GetBytes(drValue).Length + 1) * 256;//超出固定宽度,按固定宽度显示(上面已设置自动换行)(注意:POI 把 列宽 > 255 视为非法值,会抛异常;)if (length > 120 * 256){length = 120 * 256;}if (sheet.GetColumnWidth(columnIndex) < length && !drValue.IsEmpty()){sheet.SetColumnWidth(columnIndex, length);}switch (properties[columnIndex].PropertyType.ToString()){case "System.String":newCell.SetCellValue(drValue);break;case "System.DateTime":case "System.Nullable`1[System.DateTime]":newCell.SetCellValue(drValue.ParseToDateTime());newCell.CellStyle = dateStyle; //格式化显示 break;case "System.Boolean":case "System.Nullable`1[System.Boolean]":newCell.SetCellValue(drValue.ParseToBool());break;case "System.Byte":case "System.Nullable`1[System.Byte]":case "System.Int16":case "System.Nullable`1[System.Int16]":case "System.Int32":case "System.Nullable`1[System.Int32]":newCell.SetCellValue(drValue.ParseToInt());break;case "System.Int64":case "System.Nullable`1[System.Int64]":newCell.SetCellValue(drValue.ParseToString());break;case "System.Double":case "System.Nullable`1[System.Double]":newCell.SetCellValue(drValue.ParseToDouble());break;case "System.Single":case "System.Nullable`1[System.Single]":newCell.SetCellValue(drValue.ParseToDouble());break;case "System.Decimal":case "System.Nullable`1[System.Decimal]":newCell.SetCellValue(drValue.ParseToDouble());break;case "System.DBNull":newCell.SetCellValue(string.Empty);break;default:newCell.SetCellValue(string.Empty);break;}}#endregion}using (MemoryStream ms = new MemoryStream()){workbook.Write(ms);workbook.Close();ms.Flush();ms.Position = 0;return ms;}}#endregion}
}