导出数据表时如何删除导出到Excel的警告

我有以下代码,数据表已经有了数据,我想将其导出到Excel。 不过,我得到以下警告,我试过xlsx,它不工作。 我也试过csv,数据不会打开成列,因为我需要。

public static void ExportDatatabletoExcel(DataTable dt, List<string> columnNames) { try { const string attachment = "attachment; filename=elreport.xls"; HttpContext.Current.Response.ClearContent(); HttpContext.Current.Response.AddHeader("content-disposition", attachment); HttpContext.Current.Response.ContentType = "application/vnd.ms-excel"; string tab = ""; foreach (DataColumn dc in dt.Columns) { if (!columnNames.Contains(dc.ColumnName)) continue; HttpContext.Current.Response.Write(tab + dc.ColumnName); tab = "\t"; } HttpContext.Current.Response.Write("\n"); int i; foreach (DataRow dr in dt.Rows) { tab = ""; for (i = 0; i < dt.Columns.Count; i++) { if(!columnNames.Contains(dt.Columns[i].ColumnName)) continue; HttpContext.Current.Response.Write(tab + dr[i].ToString()); tab = "\t"; } HttpContext.Current.Response.Write("\n"); } HttpContext.Current.Response.End(); } catch (Exception ex) { string errorMessage = String.Format("ExportToExcelError: {0}", ex.Message); LoggingService.LogError(LoggingCategory.General, ex, errorMessage); throw; } } 

错误是:

有两种确定的方法来删除警告。

  1. 使用OpenXML API或EPPlus API构build有效的.xlsx文件(EPPlus更简单,实际上支持OleDB导入)

  2. 使用.csv扩展名将该文件构build为.csv,但将内容types保留为Excel,以便使用Excel打开。 但是,您构build文件的方式可能会在Excel正确读取内容时遇到问题,需要解决:

如果Excel以特定方式格式化,则只能读取CSV。 此外,编码必须是Windows 1252假设您正在使用Excel的窗口,否则将不会处理外国人的字符。 还需要特别为Excel处理来自邮政编码等的前导零。

  public static class CSVExportUtility { /// <summary> /// Open a datatable in Excel /// </summary> /// <param name="dt"></param> /// <param name="fileName"></param> public static void OpenAsCSV(DataTable dt, string fileName) { CSVExportUtility.OpenAsCSV(DataTableToCSV(dt), fileName); // now open the file } // OpenAsCSV /// <summary> /// open the content in the browser as a CSV /// </summary> /// <param name="sbCSVFileData"></param> /// <param name="filename"></param> public static void OpenAsCSV(StringBuilder sbCSVFileData, string fileName) { if (HttpContext.Current == null || HttpContext.Current.Response == null) return; HttpContext.Current.Response.Clear(); HttpContext.Current.Response.AddHeader( "content-disposition", string.Format("attachment; filename={0}", fileName)); HttpContext.Current.Response.ContentType = "application/ms-excel"; // This is a little tricky. Would like to use utf-8 or unicode... but Excel on Windows uses 1252 by default so we need to keep the same so most users can read the file. // At some point, we may need to actually convert our text from whatever .NET uses to 1252, but at the moment they seem similar enough that it is okay HttpContext.Current.Response.ContentEncoding = Encoding.GetEncoding(1252); // render the htmlwriter into the response HttpContext.Current.Response.Write(sbCSVFileData.ToString()); HttpContext.Current.Response.End(); } static StringBuilder DataTableToCSV(DataTable dt) { StringBuilder sb = new StringBuilder(); foreach (DataColumn dc in dt.Columns) { if (dc == dt.Columns[dt.Columns.Count - 1]) CSVExportUtility.AddFieldForCSV(dc.ColumnName, sb, false, true); else CSVExportUtility.AddFieldForCSV(dc.ColumnName, sb, true, false); } foreach (DataRow dr in dt.Rows) { foreach (DataColumn dc in dt.Columns) { if (dc == dt.Columns[dt.Columns.Count - 1]) CSVExportUtility.AddFieldForCSV(FormatDataValue(dr[dc.ColumnName]), sb, false, true); else CSVExportUtility.AddFieldForCSV(FormatDataValue(dr[dc.ColumnName]), sb, true, false); } } return sb; } static string FormatDataValue(object dv) { if (dv == null) return null; if (dv is DateTime) return ((DateTime)dv).ToShortDateString(); else return dv.ToString(); } /// <summary> /// export text to a csv /// </summary> /// <param name="text"></param> /// <param name="sbCSV"></param> /// <param name="appendTrailingComma"></param> /// <param name="endOfRow"></param> public static void AddFieldForCSV(string text, StringBuilder sbCSV, bool appendTrailingComma, bool endOfRow) { // shouldn't start or end with whitespace, escape quotes if (text != null) text = text.Trim().Replace("\"", "\"\""); // quote field int testInt; if (text != null && text.Trim().Length > 1 && text.Trim()[0] == '0' && int.TryParse(text.Trim(), out testInt)) { // if text is numeric and starts with '0' tell excel to treat as string and not strip the zero. This ONLY works if it's numeric! Otherwise it fails, example ="a,b" will use 2 cells text = "=\"" + text.Trim() + "\""; } else { text = "\"" + text + "\""; } sbCSV.Append(text); if (appendTrailingComma) sbCSV.Append(","); if (endOfRow) sbCSV.AppendLine(); } } 

如果您要导出一个GridView而不是一个DataTable,那么这个解释是: http : //atakala.com/Browser/Item.aspx? user_id=amos&dict_id= 2325 ; 大部分代码是相似的(CSVExportUtility方法)

如何在Excel下载压缩文件损坏警告 这个答案 ? 解决了一些问题。 我build议检查一下其他的答案。

此警报是Excel 2007中的一项名为“扩展强化”的新安全function,可确保打开的文件内容与正试图打开文件的shell命令中指定的扩展types相匹配。

这个问题仍在调查中,但是在Office 14给定代码的复杂性的本质之前不可能修复,而且Excel不希望降低安全措施来解决IE打开行为,而没有充分理解其他浏览器用户的后果。

另外, 这个评论可能会有帮助。

我认为这只适用于使用CSV并保存为XLS的情况。 但是,如果你构build一个真正的Excel文件,那应该没问题。 CF9 cfspreadsheet将成为你的朋友。 🙂 – 亨利2009年6月25日在23:53

其他来源检查:

  • 如何在Excel中抑制扩展警告
  • 如何在ASP.NET中生成Excel 2007文件而不会收到警告消息?
  • 如何避免打开以编程方式生成的Excel文件的警告