105 votes

A reçu une longueur de colonne non valide du client bcp pour colid 6

Je veux télécharger en masse les données d'un fichier csv vers sql server 2005 à partir du code c# mais je rencontre l'erreur suivante -

Reçu une longueur de colonne invalide de la part du client bcp pour colid 6.

lorsque l'écriture en vrac se fait sur le serveur de base de données

246voto

b_stil Points 2275

Je sais que ce message est vieux mais j'ai rencontré le même problème et j'ai finalement trouvé une solution pour déterminer quelle colonne posait problème et le signaler si nécessaire. J'ai découvert que colid retourné dans SqlException n'est pas basé à zéro, donc vous devez lui soustraire 1 pour obtenir la valeur. Ensuite, il est utilisé comme indice de la ArrayList _sortedColumnMappings de l'instance SqlBulkCopy, et non comme l'indice des correspondances de colonnes qui ont été ajoutées à l'instance SqlBulkCopy. Une chose à noter est que SqlBulkCopy s'arrêtera à la première erreur reçue, donc ce n'est peut-être pas le seul problème, mais au moins cela aide à le résoudre.

essaie
{
    bulkCopy.WriteToServer(importTable);
    sqlTran.Commit();
}    
attraper (SqlException ex)
{
    if (ex.Message.Contains("Received an invalid column length from the bcp client for colid"))
    {
        string motif = @"\d+";
        Match correspondance = Regex.Match(ex.Message.ToString(), motif);
        var index = Convert.ToInt32(correspondance.Value) -1;

        FieldInfo fi = typeof(SqlBulkCopy).GetField("_sortedColumnMappings", BindingFlags.NonPublic | BindingFlags.Instance);
        var colonnesTriees = fi.GetValue(bulkCopy);
        var éléments = (Objet[])colonnesTriees.GetType().GetField("_items", BindingFlags.NonPublic | BindingFlags.Instance).GetValue(colonnesTriees);

        FieldInfo donnéesElément = éléments[index].GetType().GetField("_metadata", BindingFlags.NonPublic | BindingFlags | BindingFlags.Instance);
        var métadonnées = donnéesElément.GetValue(éléments[index]);

        var colonne = métadonnées.GetType().GetField("colonne", BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance).GetValue(métadonnées);
        var longueur = métadonnées.GetType().GetField("longueur", BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance).GetValue(métadonnées);
        jeter un nouveau DataFormatException(String.Format("La colonne: {0} contient des données d'une longueur supérieure à: {1}", colonne, longueur));
    }

    throw;
}

73voto

Dinesh Points 1372

Une des colonnes de données dans le fichier excel (Colonne Id 6) a une ou plusieurs données de cellules qui dépassent la longueur du type de données de colonne de la base de données.

Vérifiez les données dans excel. Vérifiez également que les données dans le fichier excel respectent le format du schéma de table de la base de données.

Pour éviter cela, essayez de dépasser la longueur des données de type chaîne dans la table de la base de données.

J'espère que cela vous aidera.

5voto

Liji Chandran Points 41

J'ai rencontré un problème similaire en passant une chaîne de caractères à une table de base de données en utilisant l'option SQL BulkCopy. La chaîne que je passais comportait 3 caractères alors que la longueur de la colonne de destination était varchar(20). J'ai essayé de tronquer la chaîne avant de l'insérer dans la base de données en utilisant la fonction Trim() pour vérifier si le problème était dû à des espaces (initiaux et finaux) dans la chaîne. Après avoir tronqué la chaîne, cela a fonctionné correctement.

Vous pouvez essayer text.Trim()

2voto

Nalan M Points 834

Vérifiez la taille des colonnes dans la table pour laquelle vous effectuez une insertion/copie en masse. Les colonnes varchar ou autres colonnes de type chaîne peuvent avoir besoin d'être étendues ou la valeur que vous insérez doit être tronquée. L'ordre des colonnes doit également être le même que dans la table.

par exemple, augmentez la taille de la colonne varchar de 30 à 50 =>

ALTER TABLE [dbo].[NomTable] ALTER COLUMN [NomColonne] Varchar(50)

2voto

kkerns Points 11

J'ai utilisé SqlBulkCopy pour transférer une base de données Access vers SQL. En gros, je crée chaque table en SQL, charge la table Access correspondante dans un DataTable, puis j'utilise SqlBulkCopy pour transférer le DataTable dans la table SQL correspondante. Comme j'ai utilisé une fonction standardisée pour le faire, je n'ai pas configuré de ColumnMappings. Lorsqu'il n'y a pas de ColumnMappings, SqlBulkCopy semble simplement mapper la colonne 0 à la colonne 0, la colonne 1 à la colonne 1, etc.

Dans mon cas, j'ai dû m'assurer que l'ordre des colonnes dans ma table Access correspondait exactement à l'ordre des colonnes dans ma nouvelle table SQL. Une fois cela fait, tout s'est passé comme prévu.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X