read open net example cargar asp asp.net vb.net file-io csv

asp.net - open - read csv file c# example



¿Cómo puedo generar un archivo CSV(archivo de texto delimitado por comas) para descargar con ASP.NET? (8)

Esto es lo que tengo. Funciona. Pero, ¿hay una manera más simple o mejor?

Una página ASPX, tengo el enlace de descarga ...

<asp:HyperLink ID="HyperLinkDownload" runat="server" NavigateUrl="~/Download.aspx">Download as CSV file</asp:HyperLink>

Y luego tengo el código Download.aspx.vb detrás ...

Public Partial Class Download Inherits System.Web.UI.Page Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load ''set header Response.Clear() Response.ContentType = "text/csv" Dim FileName As String = "books.csv" Response.AppendHeader("Content-Disposition", "attachment;filename=" + FileName) ''generate file content Dim db As New bookDevelopmentDataContext Dim Allbooks = From b In db.books _ Order By b.Added _ Select b Dim CsvFile As New StringBuilder CsvFile.AppendLine(CsvHeader()) For Each b As Book In Allbooks CsvFile.AppendLine(bookString(b)) Next ''write the file Response.Write(CsvFile.ToString) Response.End() End Sub Function CsvHeader() As String Dim CsvLine As New StringBuilder CsvLine.Append("Published,") CsvLine.Append("Title,") CsvLine.Append("Author,") CsvLine.Append("Price") Return CsvLine.ToString End Function Function bookString(ByVal b As Book) As String Dim CsvLine As New StringBuilder CsvLine.Append(b.Published.ToShortDateString + ",") CsvLine.Append(b.Title.Replace(",", "") + ",") CsvLine.Append(b.Author.Replace(",", "") + ",") CsvLine.Append(Format(b.Price, "c").Replace(",", "")) Return CsvLine.ToString End Function End Class


Además de lo que Simon dijo, es posible que desee leer la guía práctica de CSV y asegurarse de que su salida no se encuentre con ninguno de los errores.

Para aclarar algo, Simon dijo:

Luego rodee esto con citas si quiere

Los campos que contienen comillas dobles dobladas ("") necesitarán estar completamente rodeadas por comillas dobles. No debería haber ningún daño al simplemente envolver todos los campos con comillas dobles, a menos que específicamente desee que el analizador elimine espacios en blanco iniciales y finales (en lugar de recortarlo usted mismo).


Si desea un convertidor de valores delimitado por dos puntos, existe una fuente abierta de terceros llamada FileHelpers . No estoy seguro de la licencia de código abierto que tiene, pero me ha ayudado bastante.


Hay una gran cantidad de sobrecarga asociada con la clase Page. Dado que solo está escupiendo un archivo CSV y no necesita la devolución de datos, los controles del servidor, el almacenamiento en caché ni el resto, debe convertirlo en un controlador con la extensión .ashx. Mira aquí .


Puede crear el equivalente de bookString () en la consulta en sí. Esto es lo que creo que sería una manera más simple.

protected void Page_Load(object sender, EventArgs e) { using (var db = new bookDevelopmentDataContext()) { string fileName = "book.csv"; var q = from b in db.books select string.Format("{0:d},/"{1}/",/"{2}/",{3:F2}", b.Published, b.Title.Replace("/"", "/"/""), b.Author.Replace("/"", "/"/""), t.price); string outstring = string.Join(",", q.ToArray()); Response.Clear(); Response.ClearHeaders(); Response.ContentType = "text/csv"; Response.AppendHeader("Content-Disposition", string.Format("attachment;filename={0}", fileName)); Response.Write("Published,Title,Author,Price," + outstring); Response.End(); } }


El formato CSV tiene algunos errores. ¿Te has hecho estas preguntas?

  • ¿Alguno de mis datos tiene comas incrustadas?
  • ¿Alguno de mis datos tiene comillas dobles incrustadas?
  • ¿Alguno de mis datos tiene líneas nuevas?
  • ¿Debo admitir cadenas Unicode?

Veo varios problemas en su código anterior. Lo de la coma, en primer lugar ... estás quitando comas:

CsvLine.Append(Format(b.Price, "c").Replace(",", ""))

¿Por qué? En CSV, debe rodear cualquier cosa que tenga comas con comillas:

CsvLine.Append(String.Format("/"{0:c}/"", b.Price))

(o algo así ... mi VB no es muy bueno). Si no está seguro de que haya comas, coloque comillas alrededor. Si hay comillas en la cadena, debe escapar de ellas duplicándolas. " convierte en "" .

b.Title.Replace("/"", "/"/"")

Luego rodee esto con comillas si lo desea. Si hay nuevas líneas en su cadena, debe rodear la cadena con comillas ... sí, se permiten nuevas líneas literales en los archivos CSV. Se ve raro para los humanos, pero está todo bien.

Un buen escritor de CSV requiere algo de reflexión. Un buen lector de CSV (analizador) es simplemente difícil (y no, la expresión regular no es lo suficientemente buena para analizar el CSV ... solo obtendrá un 95% del camino hasta allí).

Y luego está Unicode ... o más generalmente I18N (Internacionalización). Por ejemplo, está quitando comas de un precio formateado. Pero eso supone que el precio está formateado como lo espera en los EE. UU. En Francia, el formato del número se invierte (períodos usados ​​en lugar de comas, y viceversa ). En pocas palabras, use el formato agnóstico de la cultura siempre que sea posible.

Si bien el problema aquí es generar CSV, inevitablemente tendrá que analizar CSV. En .NET, el mejor analizador que he encontrado (gratis) es Fast CSV Reader en CodeProject . Lo he usado en el código de producción y es realmente muy rápido y muy fácil de usar.


Paso todos mis datos CSV a través de una función como esta:

Function PrepForCSV(ByVal value As String) As String return String.Format("""{0}""", Value.Replace("""", """""")) End Function

Además, si no está publicando html, probablemente desee un manejador de http (archivo .as h x) en lugar de una página web completa. Si creas un nuevo controlador en Visual Studio, lo más probable es que puedas copiar el código existente en el método principal y simplemente funcionará, con un pequeño aumento en el rendimiento de tus esfuerzos.


Uso el siguiente método cuando construyo un archivo CSV desde una DataTable. ControllerContext es solo el objeto de flujo de respuesta donde se escribe el archivo. Para ti, solo va a ser el objeto de Respuesta.

public override void ExecuteResult(ControllerContext context) { StringBuilder csv = new StringBuilder(10 * Table.Rows.Count * Table.Columns.Count); for (int c = 0; c < Table.Columns.Count; c++) { if (c > 0) csv.Append(","); DataColumn dc = Table.Columns[c]; string columnTitleCleaned = CleanCSVString(dc.ColumnName); csv.Append(columnTitleCleaned); } csv.Append(Environment.NewLine); foreach (DataRow dr in Table.Rows) { StringBuilder csvRow = new StringBuilder(); for(int c = 0; c < Table.Columns.Count; c++) { if(c != 0) csvRow.Append(","); object columnValue = dr[c]; if (columnValue == null) csvRow.Append(""); else { string columnStringValue = columnValue.ToString(); string cleanedColumnValue = CleanCSVString(columnStringValue); if (columnValue.GetType() == typeof(string) && !columnStringValue.Contains(",")) { cleanedColumnValue = "=" + cleanedColumnValue; // Prevents a number stored in a string from being shown as 8888E+24 in Excel. Example use is the AccountNum field in CI that looks like a number but is really a string. } csvRow.Append(cleanedColumnValue); } } csv.AppendLine(csvRow.ToString()); } HttpResponseBase response = context.HttpContext.Response; response.ContentType = "text/csv"; response.AppendHeader("Content-Disposition", "attachment;filename=" + this.FileName); response.Write(csv.ToString()); } protected string CleanCSVString(string input) { string output = "/"" + input.Replace("/"", "/"/"").Replace("/r/n", " ").Replace("/r", " ").Replace("/n", "") + "/""; return output; }


En general, se ve bien, excepto en su función "BookString ()". Primero debe pasar todas esas cadenas a través de una pequeña función como esta:

Private Function formatForCSV(stringToProcess As String) As String If stringToProcess.Contains("""") Or stringToProcess.Contains(",") Then stringToProcess = String.Format("""{0}""", stringToProcess.Replace("""", """""")) End If Return stringToProcess End Function ''So, lines like this: CsvLine.Append(b.Title.Replace(",", "") + ",") ''would be lines like this instead: CsvLine.Append(formatForCSV(b.Title)) + ",")

La función formateará bien sus cadenas para CSV. Reemplaza las comillas con comillas dobles y agrega comillas alrededor de la cadena si hay comillas o comas en la cadena.

Tenga en cuenta que no tiene en cuenta las nuevas líneas, pero solo puede garantizar una buena salida de CSV para aquellas cadenas que usted sabe que están libres de líneas nuevas (entradas de formularios simples de texto de una línea, etc.).