Excel不下载

时间:2017-03-10 06:59:24

标签: asp.net asp.net-mvc excel

我想在excel中填充数据并下载excel .. 以下是代码..

 public void DownloadExcel(int acid, int GroupId)
    {
        // Working Code
        #region DownloadExcel
        // string sConnectionString = ConfigurationManager.ConnectionStrings["TrainingMVCContext"].ConnectionString;
        string sConnectionString = string.Empty;
        LoginUserDetails objLoginUserDetails = (LoginUserDetails)InsiderTrading.Common.Common.GetSessionValue((string)ConstEnum.SessionValue.UserDetails);
        sConnectionString = objLoginUserDetails.CompanyDBConnectionString;
        SqlConnection con = new SqlConnection(sConnectionString);
        SqlCommand cmd = new SqlCommand();
        con.Open();
        DataTable dt = new DataTable();
        cmd = new SqlCommand("st_tra_NSEDownloadGroupWiseExcel", con);
        cmd.Parameters.AddWithValue("@GroupId", GroupId);
        cmd.CommandType = CommandType.StoredProcedure;
        SqlDataAdapter adp = new SqlDataAdapter(cmd);
        //  ds = new DataSet(); 

        adp.Fill(dt);


        Microsoft.Office.Interop.Excel.Range oRng;
        Microsoft.Office.Interop.Excel.Workbook mWorkBook;
        Microsoft.Office.Interop.Excel.Sheets mWorkSheets;
        Microsoft.Office.Interop.Excel.Worksheet mWSheet1;
        Microsoft.Office.Interop.Excel.Application oXL;
        object misValue = System.Reflection.Missing.Value;

        string directory = ConfigurationManager.AppSettings["Document"];

        string path = "Z:\\For Excel Demo\\Application\\InsiderTrading\\Document" + "\\" + "Stock Exchange Submission.xlsx";
        oXL = new Microsoft.Office.Interop.Excel.Application();
        oXL.Visible = true;
        oXL.DisplayAlerts = false;
        mWorkBook = oXL.Workbooks.Open(path, 0, false, 5, "", "", false, Microsoft.Office.Interop.Excel.XlPlatform.xlWindows, "", true, false, 0, true, false, false);
        mWorkSheets = mWorkBook.Worksheets;
        mWSheet1 = (Microsoft.Office.Interop.Excel.Worksheet)mWorkSheets.get_Item("Sheet1");
        Microsoft.Office.Interop.Excel.Range range = mWSheet1.UsedRange;

        for (var row = 4; row <= dt.Rows.Count; row++)
        {
            for (var col = 0; col < dt.Columns.Count; col++)
            {
                mWSheet1.Cells[row + 1, col + 1].Value = dt.Rows[row - 1][col];
            }
        }

        string Filename = "Testing.xlsx";
        string pathTosave = (Path.Combine(directory, Filename));
        mWorkBook.SaveAs(pathTosave);

        using (var memoryStream = new MemoryStream())
        {
            HttpContext.Response.Clear();
            HttpContext.Response.Charset = "";
            HttpContext.Response.ContentType = "application/vnd.ms-excel";

            HttpContext.Response.AddHeader("Content-Disposition", "inline;filename=" + pathTosave);
            System.Text.StringBuilder strHTMLContent = new System.Text.StringBuilder();
            //strHTMLContent.Append(LetterHTMLContent);
            HttpContext.Response.Write(strHTMLContent);
            HttpContext.Response.End();
            HttpContext.Response.Flush();


        }
        mWorkBook.Close();
        mWSheet1 = null;
        mWorkBook = null;
        oXL.Quit();
        GC.WaitForPendingFinalizers();
        GC.Collect();
        GC.WaitForPendingFinalizers();
        GC.Collect();





        #endregion DownloadExcel
    }

但它给出了行

的错误
 mWorkBook = oXL.Workbooks.Open(path, 0, false, 5, "", "", false, Microsoft.Office.Interop.Excel.XlPlatform.xlWindows, "", true, false, 0, true, false, false);

错误消息如下 -

类型&#39; System.Runtime.InteropServices.COMException&#39;的例外情况发生在InsiderTrading.dll中但未在用户代码中处理

我该怎么做..帮助

1 个答案:

答案 0 :(得分:0)

为什么不使用图书馆,“LinqToExcell”来做所有的管道工作?

https://www.codeproject.com/Articles/659643/Csharp-Query-Excel-and-CSV-Files-Using-LinqToExcel

只需使用控制器中的以下代码上传文件即可。请注意,您需要将文件保存在应用程序中,因为浏览器不允许您访问上传文件的位置(出于安全目的):

    #region ImportExcell

    public ActionResult ImportExcel()
    {
        return View();
    }

    [HttpPost]
    public ActionResult ImportExcel(HttpPostedFileBase upload, FormCollection fc)
    {
        var v = System.Web.HttpContext.Current.Request.Files["upload"];
        string contentType = upload.ContentType;

        FileInfo fInfo = new FileInfo(upload.FileName);

        //I am only allowing this kind of excel file. I got this from HttpPostedFileBase during debuging and checking content
        if (!contentType.Contains(@"application/vnd.openxmlformats-officedocument.spreadsheetml.sheet"))
        {
            ModelState.AddModelError("", string.Format("This is not a valid file. This is '{0}'", contentType));
            return View();
        }

        var fileName = upload.FileName;

        //This is my temporary saving spot in my application
        var filePathSaveTo = Server.MapPath(@"/Upload/ExcelFile");
        string savedFileName = Path.Combine(filePathSaveTo, fileName);

        //Now we need to save the file in a temp spot so we can access it later
        upload.SaveAs(savedFileName);

        try
        {
            string returnMsg = _fileDocDAL.LoadFromExcel(savedFileName);
            ModelState.AddModelError("", string.Format("Done! " + returnMsg));

        }
        catch (Exception e)
        {
            string error = AliKuli.Utilities.ExceptionNS.ErrorMsgClass.GetInnerException(e);
            ModelState.AddModelError("", string.Format(error));

        } 

        return View();


    }

    #endregion

你的观点......

@model ModelsClassLibrary.Models.Documents.FilesNS.FilesDocImportVM


@using (Html.BeginForm("ImportExcel", "FileDocs", null, FormMethod.Post, new { enctype = "multipart/form-data" }))
{
    @Html.AntiForgeryToken()


    <div class="form-horizontal">

        @Html.ValidationSummary(true, "", new { @class = "text-danger" })


        <div class="panel panel-info">
            <div class="panel-heading">
                Required Fields
            </div>
            <div class="panel-body">

                <div class="form-group">
                    @Html.Label("Excel File", new { @class = "control-label col-md-2" })

                    <div class="col-md-10">
                        <input type="file" multiple="multiple" name="upload" id="front"  />
                    </div>

                </div>

                <div class="form-group">
                    <div class="col-md-10">
                        <input type="submit" value="Upload" class="btn btn-success" /> |
                        @Html.ActionLink("Back to List", "Index")
                    </div>
                </div>
            </div>
        </div>
    </div>
}

我的模型如下所示,但您需要使您的模型与Excel工作表中的数据一样。这些都在LinqToExcell的文档中进行了解释

namespace ModelsClassLibrary.Models.Documents.FilesNS
{
    //[NotMapped]
    public class FilesDocImportVM
    {
        public FilesDocImportVM()
        {
           FileId = -1;
        }
#region Files
    /// <summary>
    /// The file number's ID
    /// </summary>
    public int FileId { get; set; }

    /// <summary>
    /// This is the file number that the user sees.
    /// </summary>
    public string FileNo { get; set; }

    /// <summary>
    /// This is the name of the file
    /// </summary>
    public string Description { get; set; }


    /// <summary>
    /// This is the parent's ID. 0 means no ID
    /// </summary>
    public int ParentId { get; set; }

#endregion

    public int GetFileNumberFromOldFileNumber()
    {
        if (FileNo.IsNullOrEmpty() || FileId == -1 || Description.IsNullOrEmpty())
            throw new Exception(string.Format("Proper Data not received. Record is {0}.FilesDocImportVM.GetFileNumberFromOldFileNumber ", this.ToString()));


        return new FileDoc().GetFileNumberFromOldFileNumber(FileNo);
    }

    public void SelfErrorCheck()
    {
        if(FileId == -1 || FileNo.IsNullOrEmpty() || Description.IsNullOrEmpty())
            throw new Exception(string.Format("Proper Data not received. Record is {0}. FilesDocImportVM.SelfErrorCheck", this.ToString()));

    }
#region Category
    /// <summary>
    /// This is the categories ID
    /// </summary>
    public int CategoryId { get; set; }


    /// <summary>
    /// This is the name of the category
    /// </summary>
    public string CategoryName { get; set; } 
#endregion

    public override string ToString()
    {
        return string.Format("FileId: {0}, FileNo: {1}, Description: {2}, ParentId: {3}, CategoryId: {4}, CategoryName: {5}",
            FileId,
            FileNo,
            Description,
            ParentId,
            CategoryId,
            CategoryName);
     }

    }
}

上传代码非常简单......这是使用的代码

    public string LoadFromExcel(string excelFileName)
    {
        int noOfFiles = 0;
//*** NOTE - The line below is the code to import from Excel. I have wrapped it a bit to make it simple... the wrapper is below. The code after this line is just for fixing and checking the data.
        var excelFile = AliKuli.Utilities.ExcellUtility.ImportFromExcelWithHeader(excelFileName, "AliKuliFiles");
        if (excelFile.IsNullOrEmpty())
            throw new Exception(string.Format("Utility Class failed to load. FileDocsDAL.LoadFromExcel"));

        string totalFilesMsg = string.Format("Total Orignal Files: {0}", excelFile.Count());

        var dataArray = excelFile.OrderBy(x => x.FileId).ToList();

        if (dataArray.IsNullOrEmpty())
            throw new Exception(string.Format("Data array failed to load. FileDocsDAL.LoadFromExcel"));

        CheckTheData(dataArray);

        //first make the categories
        User theUser = Get_User();

        string temp = "";
        if (noOfFiles == 324)
            temp = "Found";

        CreateCategories(dataArray, theUser);
        CreateAndSaveFile(ref noOfFiles, dataArray, theUser);

        //now add the parents
        SaveTheParents();

        totalFilesMsg += " Counted: " + noOfFiles;
        //CreateFileWithCategory(dataArray, admin);
        return totalFilesMsg;
    }

这是我编写的用于包装LinqToExcel

的包装器代码
public static class ExcellUtility
{

    /// <summary>
    /// This will read in the excel file such that it will stringify the cols of each row. 
    /// Example. If there are 3 cols, the the first 3 entries will be for col 0, then 1, then Col 2,
    /// then... the 4th entry will again be col1
    /// </summary>
    /// <param name="fileName"></param>
    /// <returns></returns>
    public static List<FilesDocImportVM> ImportFromExcelWithHeader(string excelFileName, string sheetName)
    {

        ExcelUtilityClass euc;
        ExcelQueryFactory excel;
        MakeExcelUtilityClass(excelFileName, out euc, out excel);

        //This creates a IQueriable<FilesDocImportVM>
        var data = from c in excel.Worksheet<FilesDocImportVM>(sheetName) select c;
        var colNames = excel.GetColumnNames(sheetName).ToArray();

        var datalist = data.ToList();

        return datalist;

    }

    private static void MakeExcelUtilityClass(string excelFileName, out ExcelUtilityClass euc, out ExcelQueryFactory excel)
    {
        if (excelFileName.IsNullOrEmpty())
            throw new Exception("No Excel File Name Passed");

        euc = new ExcelUtilityClass();
        excel = new ExcelQueryFactory(excelFileName);
    }
  }
}

看起来比它复杂......上传部分很简单 - 在编写包装器后只需要一行代码。

祝你好运。