Pregunta

Necesito importar un archivo CSV grande a un servidor SQL.Estoy usando esto:

BULK 
INSERT CSVTest
        FROM 'c:\csvfile.txt'
            WITH
    (
                FIELDTERMINATOR = ',',
                ROWTERMINATOR = '\n'
    )
GO

El problema es que todos mis campos están entre comillas (""), por lo que una fila realmente se ve así:

"1","","2","","sometimes with comma , inside", "" 

¿Puedo importarlos de alguna manera de forma masiva y decirle a SQL que use las comillas como delimitadores de campo?

Editar:El problema con el uso de '","' como delimitador, como en los ejemplos sugeridos, es que:Lo que hacen la mayoría de los ejemplos es importar los datos, incluido el primero " en la primera columna y el último " en la última, luego continúan y los eliminan.Desgraciadamente, mi primera (y última) columna son de fecha y hora y no permitirán que se importe "20080902 como fecha y hora.

Por lo que he estado leyendo, creo que FORMATFILE es el camino a seguir, pero la documentación (incluido MSDN) es terriblemente inútil.

¿Fue útil?

Solución

Sé que esta no es una solución real, pero uso una tabla ficticia para la importación con nvarchar configurado para todo.Luego hago una inserción que elimina los caracteres " y realiza las conversiones.No es bonito pero cumple su función.

Otros consejos

Intentar FIELDTERMINATOR='","'

Aquí hay un excelente enlace para ayudar con la primera y la última cita... mira cómo usó la subcadena SP

http://www.sqlteam.com/article/using-bulk-insert-to-load-a-text-file

Otro truco que uso a veces es abrir el CSV en Excel y luego escribir su declaración SQL en una celda al final de cada fila.Por ejemplo:

=concatenate("insert into myTable (columnA,columnB) values ('",a1,"','",b1,"'")")

Un relleno puede completar esto en cada fila por usted.Luego simplemente copie y pegue el resultado en una nueva ventana de consulta.

Es de la vieja escuela, pero si solo necesita realizar importaciones de vez en cuando, le ahorrará perder el tiempo leyendo toda la documentación oscura sobre la forma "correcta" de hacerlo.

Intentar Conjunto de filas abiertas.Esto se puede utilizar para importar cosas de Excel.Excel puede abrir archivos CSV, por lo que solo necesita encontrar la [ConnectionString][2] correcta.

[2]:Controlador={Controlador de texto de Microsoft (*.txt;*.csv)};Dbq=c: xtFilesFolder\;Extensiones=asc,csv,tab,txt;

Yo diría que use FileHelpers, es una biblioteca de código abierto.

¿Necesita hacer esto mediante programación o es una oportunidad única?

Usando Enterprise Manager, haga clic con el botón derecho en Importar datos para seleccionar su delimitador.

Debe tener cuidado con BCP/BULK INSERT porque ni BSP ni Bulk Insert manejan esto bien si las citas no son consistentes, incluso con archivos de formato (incluso los archivos de formato XML no ofrecen la opción) y caracteres ficticios ["] al final. principio y fin y usando [","] como separador.Técnicamente, los archivos CSV no necesitan tener caracteres ["] si no hay caracteres [,] incrustados

Es por esta razón que los archivos delimitados por comas a veces se denominan archivos limitados por comedia.

OpenRowSet requerirá Excel en el servidor y podría ser problemático en entornos de 64 bits. Sé que es problemático usar Excel en Jet en 64 bits.

SSIS es realmente su mejor opción si es probable que el archivo varíe de sus expectativas en el futuro.

Puede probar este código que es muy dulce si lo desea, esto eliminará las semicolones no deseadas de su código.si por ejemplo tus datos son así:
"Kelly","Reynold","kelly@reynold.com"

Bulk insert test1
from 'c:\1.txt' with ( 
    fieldterminator ='","'
    ,rowterminator='\n')

update test1<br>
set name =Substring (name , 2,len(name))
where name like **' "% '**

update test1
set email=substring(email, 1,len(email)-1)
where email like **' %" '**

Primero necesita importar el archivo CSV a la tabla de datos

Luego puede insertar filas masivas usando SQLBulkCopy

using System;
using System.Data;
using System.Data.SqlClient;

namespace SqlBulkInsertExample
{
    class Program
    {
      static void Main(string[] args)
        {
            DataTable prodSalesData = new DataTable("ProductSalesData");

            // Create Column 1: SaleDate
            DataColumn dateColumn = new DataColumn();
            dateColumn.DataType = Type.GetType("System.DateTime");
            dateColumn.ColumnName = "SaleDate";

            // Create Column 2: ProductName
            DataColumn productNameColumn = new DataColumn();
            productNameColumn.ColumnName = "ProductName";

            // Create Column 3: TotalSales
            DataColumn totalSalesColumn = new DataColumn();
            totalSalesColumn.DataType = Type.GetType("System.Int32");
            totalSalesColumn.ColumnName = "TotalSales";

            // Add the columns to the ProductSalesData DataTable
            prodSalesData.Columns.Add(dateColumn);
            prodSalesData.Columns.Add(productNameColumn);
            prodSalesData.Columns.Add(totalSalesColumn);

            // Let's populate the datatable with our stats.
            // You can add as many rows as you want here!

            // Create a new row
            DataRow dailyProductSalesRow = prodSalesData.NewRow();
            dailyProductSalesRow["SaleDate"] = DateTime.Now.Date;
            dailyProductSalesRow["ProductName"] = "Nike";
            dailyProductSalesRow["TotalSales"] = 10;

            // Add the row to the ProductSalesData DataTable
            prodSalesData.Rows.Add(dailyProductSalesRow);

            // Copy the DataTable to SQL Server using SqlBulkCopy
            using (SqlConnection dbConnection = new SqlConnection("Data Source=ProductHost;Initial Catalog=dbProduct;Integrated Security=SSPI;Connection Timeout=60;Min Pool Size=2;Max Pool Size=20;"))
            {
                dbConnection.Open();
                using (SqlBulkCopy s = new SqlBulkCopy(dbConnection))
                {
                    s.DestinationTableName = prodSalesData.TableName;

                    foreach (var column in prodSalesData.Columns)
                        s.ColumnMappings.Add(column.ToString(), column.ToString());

                    s.WriteToServer(prodSalesData);
                }
            }
        }
    }
}

Sí, K Richard tiene razón: FIELDTERMINATOR = '","'

Ver http://www.sqlteam.com/article/using-bulk-insert-to-load-a-text-file para más información.

También puedes usar DTS o SSIS.

¿Tiene control sobre el formato de entrada?| (tuberías), y generalmente obtienen mejores terminadores de campo.

Si descubre cómo analizar el archivo en una tabla de datos, le sugeriría la clase SqlBulkInsert para insertarlo en SQL Server.

Esta es una vieja pregunta, así que la escribo para ayudar a cualquiera que se encuentre con ella.

SQL Server 2017 introduce el parámetro FIELDQUOTE que está destinado a este caso de uso exacto.

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top