如何读取Excel文件并在MVC中的Grid中填充其数据而不将Excel文件存储在任何地方?

Nay*_*_07 4 c# asp.net-mvc excel

我想通过浏览按钮控件上传Excel文件.我不需要保存它.然后,在单击按钮时,如何在Excel中读取数据并在网格视图中显示它.我需要使用MVC来完成这个任务.

请帮忙.

谢谢,Nayan

Dav*_*d P 9

这是我修改后的答案:

1)从Microsoft下载OpenXML SDK

2)创建一个空白的MVC 5项目,并将其命名为"MVCImportExcel"

3)通过浏览到SDK lib子目录添加对DocumentFormat.OpenXML的引用

4)添加对WindowsBase的引用

5)创建名为"MyViewModel"的新模型

using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Data.Entity;
using System.ComponentModel.DataAnnotations;


namespace MVCImportExcel.Models
{
    public class MyViewModel
    {
        [Required]
        public HttpPostedFileBase MyExcelFile { get; set; }

        public string MSExcelTable { get; set; }
    }
}
Run Code Online (Sandbox Code Playgroud)

6)创建一个名为"HomeController"的新控制器

using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.Mvc;
using MVCImportExcel.Models;
using System.Data;
using DocumentFormat.OpenXml.Packaging;
using DocumentFormat.OpenXml.Spreadsheet;
using System.IO;
namespace MVCImportExcel.Controllers
{
    public class HomeController : Controller
    {
        //
        // GET: /Home/
        public ActionResult Index()
        {
            var model = new MyViewModel();
            return View(model);
        }

        [HttpPost]
        public ActionResult Index(MyViewModel model)
        {
            if (!ModelState.IsValid)
            {
                return View(model);
            }
            DataTable dt = GetDataTableFromSpreadsheet(model.MyExcelFile.InputStream,false);
            string strContent = "<p>Thanks for uploading the file</p>" + ConvertDataTableToHTMLTable(dt);
            model.MSExcelTable = strContent;
            return View(model);
        }
        public static DataTable GetDataTableFromSpreadsheet(Stream MyExcelStream, bool ReadOnly)
        {
            DataTable dt = new DataTable();
            using (SpreadsheetDocument sDoc = SpreadsheetDocument.Open(MyExcelStream, ReadOnly))
            {
                WorkbookPart workbookPart = sDoc.WorkbookPart;
                IEnumerable<Sheet> sheets = sDoc.WorkbookPart.Workbook.GetFirstChild<Sheets>().Elements<Sheet>();
                string relationshipId = sheets.First().Id.Value;
                WorksheetPart worksheetPart = (WorksheetPart)sDoc.WorkbookPart.GetPartById(relationshipId);
                Worksheet workSheet = worksheetPart.Worksheet;
                SheetData sheetData = workSheet.GetFirstChild<SheetData>();
                IEnumerable<Row> rows = sheetData.Descendants<Row>();

                foreach (Cell cell in rows.ElementAt(0))
                {
                    dt.Columns.Add(GetCellValue(sDoc, cell));
                }

                foreach (Row row in rows) //this will also include your header row...
                {
                    DataRow tempRow = dt.NewRow();

                    for (int i = 0; i < row.Descendants<Cell>().Count(); i++)
                    {
                        tempRow[i] = GetCellValue(sDoc, row.Descendants<Cell>().ElementAt(i));
                    }

                    dt.Rows.Add(tempRow);
                }
            }
            dt.Rows.RemoveAt(0);
            return dt;
        }
        public static string GetCellValue(SpreadsheetDocument document, Cell cell)
        {
            SharedStringTablePart stringTablePart = document.WorkbookPart.SharedStringTablePart;
            string value = cell.CellValue.InnerXml;

            if (cell.DataType != null && cell.DataType.Value == CellValues.SharedString)
            {
                return stringTablePart.SharedStringTable.ChildElements[Int32.Parse(value)].InnerText;
            }
            else
            {
                return value;
            }
        }
        public static string ConvertDataTableToHTMLTable(DataTable dt)
        {
            string ret = "";
            ret = "<table id=" + (char)34 + "tblExcel" + (char)34 + ">";
            ret+= "<tr>";
            foreach (DataColumn col in dt.Columns)
            {
                ret += "<td class=" + (char)34 + "tdColumnHeader" + (char)34 + ">" + col.ColumnName + "</td>";
            }
            ret+= "</tr>";
            foreach (DataRow row in dt.Rows)
            {
                ret+="<tr>";
                for (int i = 0;i < dt.Columns.Count;i++)
                {
                    ret+= "<td class=" + (char)34 + "tdCellData" + (char)34 + ">" + row[i].ToString() + "</td>";
                }
                ret+= "</tr>";
            }
            ret+= "</table>";
            return ret;
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

7)在Home下创建一个新视图,并将其命名为"Index"

@model MVCImportExcel.Models.MyViewModel
@{
    Layout = null;
}

<!DOCTYPE html>

<html>
<head>
    <meta name="viewport" content="width=device-width" />
    <title></title>
    <style type="text/css">
        #tblExcel
        {
            width: 1000px;
            border: none;
        background-color: #000000;
    }
    .tdColumnHeader
    {
        padding: 2px 2px 2px 2px;
        text-align: center;
        font-family: Verdana;
        font-size: 12px;
        font-weight: bold;
        background-color: cornflowerblue;
        color: #FFFFFF;
    }
    .tdCellData
    {
        padding: 2px 2px 2px 2px;
        font-family: Verdana;
        font-size: 12px;
        background-color: aqua;
        color: #000000;
    }
</style>
</head>
<body>
    @using (Html.BeginForm(null,null,FormMethod.Post,new { enctype = "multipart/form-data" }))
    {
        <div>
            @Html.LabelFor(x => x.MyExcelFile)
            @Html.TextBoxFor(x => x.MyExcelFile, new { type = "file" })
            @Html.ValidationMessageFor(x => x.MyExcelFile)
        </div>
        <button type="submit">Upload</button>

        <br /><br />
        @Html.Raw(Model.MSExcelTable)
    }
</body>

</html>
Run Code Online (Sandbox Code Playgroud)

就像我在评论中所说,这只适用于XLSX文件.希望这可以帮助你或其他人在路上.

:) 大卫

  • 我只是发现代码更具可读性. (2认同)