基于MiniExcel的三种常用导出Excel方法(固定列导出、动态列导出、按模板导出)

news/2024/7/21 6:08:27 标签: .net, c#, excel

为了方便代码编写和测试,把很多代码都放在一个class里面,实际开发根据需要放到对应的目录下即可。

excel_1">1.使用nuget下载安装miniexcel

2.编写对应的测试接口,具体代码如下:

using Microsoft.AspNetCore.Authorization;
using Microsoft.AspNetCore.Mvc;
using System.Collections.Generic;
using System.IO;
using System.Threading.Tasks;
using System;
using AutoMapper;
using MiniExcelLibs.Attributes;
using MiniExcelLibs;
using MiniExcelLibs.OpenXml;
using System.Linq;

namespace YY.Webapi.Controllers
{
    /// <summary>
    /// miniexcel测试
    /// </summary>
    [Route("api/[controller]")]
    [ApiController]
    [Produces("application/json")]
    [AllowAnonymous]
    public class MiniExcelController : ControllerBase
    {
        private readonly IMapper _mapper;

        public MiniExcelController(
            IMapper mapper
            )
        {
            _mapper = mapper;
        }

        /// <summary>
        /// 固定列导出
        /// </summary>
        /// <param name="input"></param>
        /// <returns></returns>
        /// <exception cref="Exception"></exception>
        [HttpPost("Export")]
        public async Task<IActionResult> Export()
        {
            try
            {
                var models = new Custome().GetProducts();
                var exportDtos = _mapper.Map<List<CustomeExportDto>>(models);
                var memoryStream = new MemoryStream();
                memoryStream.SaveAs(exportDtos);
                memoryStream.Seek(0, SeekOrigin.Begin);
                return new FileStreamResult(memoryStream, "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet")
                {
                    FileDownloadName = $"固定列报表导出-{DateTime.Now.ToString("yyyyMMddHHmmss")}.xlsx"
                };
            }
            catch (Exception ex)
            {
                throw new Exception($"固定列报表导出出现错误:{ex.Message}");
            }
        }

        /// <summary>
        /// 动态列导出(指定列导出)
        /// </summary>
        /// <param name="columnParams"></param>
        /// <returns></returns>
        /// <exception cref="Exception"></exception>
        [HttpPost("ExportByAssignColumn")]
        [AllowAnonymous]
        public async Task<IActionResult> ExportByAssignColumn(List<CustomeParam> columnParams)
        {
            try
            {
                if (columnParams == null || !columnParams.Any()) throw new Exception("请选择需要导出的列!");
                var dtos = new Custome().GetProducts();

                #region 配置
                var config = new OpenXmlConfiguration { };
                List<DynamicExcelColumn> objs = new List<DynamicExcelColumn>();
                int index = 0;
                foreach (var columnParam in columnParams)
                {
                    objs.Add(new DynamicExcelColumn(columnParam.ColumnDisplayName) { Index = index++, Width = columnParam.ColumnWidth });
                }
                config.DynamicColumns = objs.ToArray();
                #endregion

                #region 获取值
                var values = new List<Dictionary<string, object>>();
                foreach (var dto in dtos)
                {
                    var dic = new Dictionary<string, object>();
                    foreach (var columnParam in columnParams)
                    {
                        dic.Add(columnParam.ColumnDisplayName, GetModelValue(columnParam.ColumnName, dto));
                    }
                    values.Add(dic);
                }
                #endregion

                var memoryStream = new MemoryStream();
                memoryStream.SaveAs(values, configuration: config);
                memoryStream.Seek(0, SeekOrigin.Begin);
                return new FileStreamResult(memoryStream, "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet")
                {
                    FileDownloadName = $"动态列报表导出-{DateTime.Now.ToString("yyyyMMddHHmmss")}.xlsx"
                };
            }
            catch (Exception ex)
            {
                throw new Exception($"动态列报表导出错误:{ex.Message}");
            }
        }

        /// <summary>
        /// 按模板导出
        /// </summary>
        /// <param name="id"></param>
        /// <returns></returns>
        /// <exception cref="Exception"></exception>
        [HttpPost("{id}/ExportByTemplate")]
        public async Task<IActionResult> ExportByTemplate([FromRoute] int id)
        {
            try
            {
                var entity = new Custome() { Id = 1, Code = "Code", Name = "Test", Price = 12, CreateTime = DateTime.Now };

                string templatePath = $@"C:\Users\Administrator\Desktop\报表模板.xlsx";
                var value = new
                {
                    Code = entity.Code,
                    Name = entity.Name
                };

                byte[] bytes = System.IO.File.ReadAllBytes(templatePath);
                var memoryStream = new MemoryStream();
                await memoryStream.SaveAsByTemplateAsync(bytes, value);
                memoryStream.Seek(0, SeekOrigin.Begin);
                return new FileStreamResult(memoryStream, "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet")
                {
                    FileDownloadName = $"按模板报表导出-{DateTime.Now.ToString("yyyyMMddHHmmss")}.xlsx"
                };
            }
            catch (Exception ex)
            {
                throw new Exception($"按模板报表导出错误:{ex.Message}");
            }
        }

        #region 私有方法
        /// <summary>
        /// 根据字段名获取对应的值
        /// </summary>
        /// <param name="fieldName"></param>
        /// <param name="obj"></param>
        /// <returns></returns>
        private string GetModelValue(string fieldName, object obj)
        {
            try
            {
                object o = obj.GetType().GetProperty(fieldName).GetValue(obj, null);
                string Value = Convert.ToString(o);
                if (string.IsNullOrEmpty(Value)) return "";
                return Value;
            }
            catch
            {
                return "";
            }
        }
        #endregion
    }


    public class Custome
    {
        /// <summary>
        /// 产品Id
        /// </summary>
        public int Id { get; set; }
        /// <summary>
        /// 产品编码
        /// </summary>
        public string Code { get; set; }
        /// <summary>
        /// 产品名称
        /// </summary>
        public string Name { get; set; }
        /// <summary>
        /// 价格
        /// </summary>
        public int Price { get; set; }
        /// <summary>
        /// 创建时间
        /// </summary>
        public DateTime CreateTime { get; set; }
        public List<Custome> GetProducts()
        {
            var products = new List<Custome>();
            for (int i = 0; i < 1000; i++)
            {
                products.Add(new Custome
                {
                    Id = i + 1,
                    Code = $"Code-{(i + 1).ToString()}",
                    Name = $"Name-{(i + 1).ToString()}",
                    Price = Random.Shared.Next(10, 100),
                    CreateTime = DateTime.Now
                });
            }
            return products;
        }
    }

    public class CustomeExportDto
    {
        /// <summary>
        /// 产品编码
        /// </summary>
        [ExcelColumn(Name = "产品编码", Width = 12)]
        public string Code { get; set; }
        /// <summary>
        /// 产品名称
        /// </summary>
        [ExcelColumn(Name = "产品名称", Width = 12)]
        public string Name { get; set; }
        /// <summary>
        /// 价格
        /// </summary>
        [ExcelColumn(Name = "价格", Width = 12)]
        public int Price { get; set; }
        /// <summary>
        /// 创建时间
        /// </summary>
        [ExcelColumn(Name = "创建时间", Width = 12, Format = "yyyy-MM-dd HH:mm:ss")]
        public DateTime CreateTime { get; set; }
    }


    public class CustomeParam
    {
        /// <summary>
        /// 列名
        /// </summary>
        public string ColumnName { get; set; }
        /// <summary>
        /// 列显示名
        /// </summary>
        public string ColumnDisplayName { get; set; }
        /// <summary>
        /// 列宽
        /// </summary>
        public double ColumnWidth { get; set; }
    }
}

3.固定列和按模板导出Excel都比较常规,,其中的动态列导出是根据前端传进来的参数进行选择性的动态列导出,swagger测试效果如下:

在这里插入图片描述
在这里插入图片描述
导出的文件如下:
在这里插入图片描述


http://www.niftyadmin.cn/n/5466245.html

相关文章

InterliJ IDEA基本设置

安装好idea后&#xff0c;将软件打开&#xff0c;可以进行基础设置 1.打开软件&#xff0c;先安装插件-汉化包&#xff08;不推荐&#xff0c;最好使用英文版&#xff09;&#xff0c;本次我们使用汉化版本完成基本设置&#xff0c;后期希望大家适应英文版的开发环境。&#x…

mysql 字段类型为json,后端用list接收

数据库 board json DEFAULT NULL COMMENT 信息,格式[{"name":"net","chip":"esp32","hdVer":1}] 接收-List Mybatis <resultMap id"productDeviceAndBrand" type"com.charg.product.domain.vo.Product…

笔记本电脑win7 Wireless-AC 7265连不上wifi6

1.背景介绍 旧路由器连接人数有限&#xff0c;老旧&#xff0c;信号不稳定更换了新路由器&#xff0c;如 TL-XDR5430易展版用户电脑连不上新的WIFI网络了&#xff0c;比较着急 核心问题&#xff1a;有效解决笔记本连接wifi上网问题&#xff0c;方法不限 2.环境信息 Windows…

全量知识系统 程序详细设计之“ AI操作系统” (百度搜索的QA)

Q1. 今天讨论的题目是&#xff1a;全量知识系统 程序详细设计之“ AI操作系统”..本篇是基于前面的文章给出的系统核心&#xff08;一个恰当的组织&#xff09;之上的一个扩展&#xff0c;并在此基础上给出整个全量知识系统 &#xff08;以下简称“全知系统”&#xff09;程序详…

系统IO函数接口

目录 前言 一. man手册 1.1 man手册如何查询 1.2 man手册基础 二.系统IO函数接口 三.open打开文件夹 3.1 例1 open打开文件 3.2 open打开文件代码 3.3 例2 创建文件 四.write写文件 4.1 write写文件 五. read读文件 5.1 read读文件与偏移 5.2 偏移细节 5.3 read读文件代码 六.复…

vue 加 websocket 聊天

<template><div style="height: 100%; width: 100%; background-color: #fff"><div class="wrap"><!-- 头部 --><div class="titleBox"><imgsrc="@/assets/image/avatar.png"style="argin: 10p…

Flutter应用发布流程详解:从开发到上架一站式指南

引言 Flutter是一款由Google推出的跨平台移动应用开发框架&#xff0c;其强大的性能和流畅的用户体验使其备受开发者青睐。然而&#xff0c;开发一款应用只是第一步&#xff0c;将其成功上架到苹果商店才是实现商业目标的关键一步。本文将详细介绍如何使用Flutter将应用程序上…

Vue2(完结):replace属性、编程式路由导航、缓存路由组件、两个新钩子、路由守卫、history与hash

一、router-link的replace属性 1、作用&#xff1a;控制路由跳转时操作浏览器历史记录的模式 2、浏览器的历史记录有两种写入方式&#xff1a;分别为push和replace&#xff0c;push是追加历史记录&#xff0c;replace是替换当前记录。路由跳转时候默认为push 3、如何开启repla…