MySQL Column Count stimmt nicht mit Value Count überein

  • VB.NET
  • .NET (FX) 4.0

Es gibt 19 Antworten in diesem Thema. Der letzte Beitrag () ist von Gunngir.

    MySQL Column Count stimmt nicht mit Value Count überein

    Hallo, Ich bin auf ein (scheinbar) simples Problem gestoßen, das nicht ganz so simpel zu lösen scheint...

    Bevor das Problem entstand, wurden Spalten zur Datenbank hinzugefügt.
    und dann für die Table im Dataset im Designer ein Update gemacht. Sources wurden richtig übernommen.

    Wieso wird der Fehler nun ausgeworfen?

    Rein von der Logik her macht es für mich keinen Sinn,
    da selbst bei einer Spalte bzw. übergebenen Variable der gleiche Fehler ausgeworfen wird.


    SQL Query:

    SQL-Abfrage

    1. INSERT INTO elemente
    2. (BaugrIndex, Komponente, KdNr)
    3. VALUES ('A00', '0', @KdNr)

    Zweiter Query, gleiches Problem:

    SQL-Abfrage

    1. INSERT INTO elemente
    2. (Ort, KompIndex, Komponente)
    3. VALUES (@Ort, @KompIndex, @Komp)

    Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von „Gunngir“ ()

    Naja die Fehlermeldung besagt, dass du beim Insert die Anzahl der angegebenen Spalten nicht mit der Anzahl der angegebenen Values übereinstimmt. Sind BaugrIndex Komponente usw Variablen? Sind die vll leer?
    Das ist meine Signatur und sie wird wunderbar sein!

    SQL-Abfrage

    1. INSERT INTO elemente
    2. (BaugrIndex, Komponente, KdNr)
    3. VALUES ('A00', '0', @KdNr)


    In dem Query muss ich doch nur die KdNr per Variable über den Tableadapter.InsertQueryXY("KdNrVariable") angeben.
    Was hat das mit den Spalten meiner Tabelle zu tun? Ich habe nur 3 Übergabeparameter und 2 sind bereits belegt von dem Query. Eine nur über eine Variable.

    Der gleiche Code hat vor dem hinzufügen der Spalten mehrere hundert male wunderbar funktioniert.
    Wo steht dieses Insert? Poste mal das drumherum im Code. Wie gesagt, die Fehlermeldung besagt das was ich dir oben geschrieben habe (ist ja auch eigentlich relativ eindeutig)
    Das ist meine Signatur und sie wird wunderbar sein!

    VB.NET-Quellcode

    1. Private Sub btnKomponente_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles btnKomponente.Click
    2. Call TreeViewNewEntries(DirectCast(MainForm.TreeView, TreeView), 4, txt_subPath.Text)
    3. Dim AbtIndex As Integer = CInt(frm_Komponente.AbteilungTableAdapter.ScalarQuery(Abteilung:="Konstruktion"))
    4. Dim cPath As String = txt_rootPath.Text & "~" & txt_subPath.Text
    5. 'Check if Komponente exists already
    6. If frm_Komponente.ElementeTableAdapter.ScalarQueryOrtCount(cPath) > 0 Then
    7. MsgBox("Hoppala, dieses Element gibt es schon... Abbruch!" & vbCr & _
    8. "Element: " & cPath & ".")
    9. Exit Sub
    10. End If
    11. 'Ort, Index und Komponente =wahr sind definiert
    12. 'MessageBox.Show(My.Settings.ProjektConnectionString.ToString)
    13. frm_Komponente.ElementeTableAdapter.Connection.ConnectionString = My.Settings.ProjektConnectionString.ToString
    14. AffectedLines = frm_Komponente.ElementeTableAdapter.InsertQueryKomp(cPath, "K0000", 1)
    15. AffectedLines = frm_Komponente.ElementeTableAdapter.Fill(frm_Komponente.ProjektDataSet.elemente)
    16. frm_Komponente.ElementeTableAdapter.InsertQueryBaugr("blubb")
    17. Dim FullPath As String = txt_rootPath.Text & "~" & txt_subPath.Text
    18. FullPath = Replace(FullPath, "~", "\")
    19. MainForm.Update()
    20. For Each n As TreeNode In MainForm.TreeView.Nodes
    21. SelectTNRecursive(n, FullPath)
    22. Next
    23. txt_subPath.Text = ""
    24. End Sub
    Sorry, wenn ich den Code sehe, dann kriege ich ein Bild von einem Code-Monstrum, was in absolute Unwartbarkeit ausufert.

    Der allerallerersten Schritt, die tausende Fehlerquellen zumindest auf hunderte zu reduzieren wäre Visual Studio - Empfohlene Einstellungen

    Und dann wären noch eine menge weiterer Schritte fällig, denn die Architektur geht auch überhaupt nicht auf. Also dass das eine Form munter ins andere grabscht - damit fährt man über kurz oder lang vor die Wand.
    Aber die Architektur anzugehen ist erst der zweite Schritt, und würde ich hier erst noch garnet diskutieren, bevor du nicht die Grund-Einstellungen korrigiert hast.

    /sorry - klar ist ganz offtopic, aber was nützt die schönste OnTopic-Hilfe, wenn sie letztlich nur den Zeitpunkt herauszögert, wo der TE das Projekt aufgibt (was mir sehr wahrscheinlich scheint)?
    fk it ... bin ungelernt. das war der letzte Post hier.
    Ich kriege in der Firma schon 0 Hilfe, sonst programmiert auch keiner dort. Meine Projekte haben jetzt alle Option Strict + Explcit drin.
    Ich weiß es eben verdammt noch mal nicht besser und habe auch keine Ahnung wie es besser gehen soll. bye
    Jo man lernt das auch nicht von heute auf morgen.
    Das ist ein längerer Prozess mit viel Geduld und viel "Gelese".

    Dir scheint ja zumindest Geduld zu fehlen. Aber ist deine Entscheidung. Keiner zwingt dich hier Fragen zu stellen genauso wie die Antworten nicht immer das sind was man erwartet.

    GL
    Das ist meine Signatur und sie wird wunderbar sein!
    Sorry - ich hab iwie was durcheinandergebracht.
    Mir war, als würde hier mit DataReadern und Kram umgegangen, aber das ist ja garnet der Fall - vmtl. hat mich die Sql-Diskussion durcheinandergebracht.

    Aber es gibt ja typisierte DataTables, und auch typisierte DataAdapter - ich find sie zwar nicht toll, aber wenn sie nicht verdaddelt sind, funktionieren sie.

    Und da frag ich mich nun, warum überhaupt die Sql-Diskussion?
    Weil man kann doch einfach mw der ElementeDataTable einen ElementRow-Datensatz zufügen, und wenn man dann ElementeTableAdapter.Update(ElementeDataTable) aufruft, dann kümmert der sich um das richtige Sql.

    Vorraussetzung ist natürlich, dass der ElementeTableAdapter nicht verdaddelt ist.
    Da müsste man dann genauer drauf schauen, wenn der vor der DB-Änderung korrekt abspeichern konnte, und hinterher nicht mehr.
    Danke für die Hilfe ;)
    Scheint so, als ob die maximale Spaltenanzahl für den Tableadapter erreicht war. Sobald eine Spalte gelöscht wurde, ging die Schose ...
    (es war egal, welche Spalte gelöscht wurde. Deshalb kann es nicht an den Spalten selbst liegen - da wenn eine andere gelöscht ist, alles wunderbar funktioniert.)

    Anscheinend hat der Tableadapter ein Spalten-Limit das irgend wo bei 60 ~ liegt. Genial.

    Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von „Gunngir“ ()

    Na, das wär ja ein super-blöd-Bug - wie kriegt man so einen Mist ühaupt hin?

    Kannst du das nochmal genauer untersuchen?
    Also mach mal eine Db-Tabelle mit 59 Spalten, generier Dataset davon, klicks auf den TableAdapter und kopier den CommandText des InsertCommands aus.
    Und dann dasselbe mit 61 Spalten, dass man wirklich sieht: Die ersten 60 Spalten hat er gemacht, die 61. aber vergessen.

    Ansonsten kannst du auch mal Dataset->Db probieren, ich zumindest hab da nix eingebaut, was ab 60 Spalten den Knüppel wirft.
    Wenn das genauso spinnt wäre somit der MySql-CommandBuilder als Übeltäter identifiziert.
    (Naja, ich müsste dann nochmal mit anderen DbProvidern probieren, wenn das alle haben, ist doch wieder Microsoft schuld.)
    wie kann man den InsertCommand auslesen, den Visual Studio für einen Aufruf des InsertCommands produziert?

    Würde dann die Tage mal machen... das Projekt muss erst so in den Test gehen,
    ist nicht überlebenswichtig für den 1. Testdurchlauf,
    wäre aber neugierig um zu sehen an was das jetzt genau liegt :)
    war ein Trigger, der mir die Historie erstellt in einer seperaten Tabelle.
    Da die Trigger nach Spaltenreihenfolge der "Ursprungstabelle" funktionierten, ist ein Hinzufügen von neuen Spalten mit Problemen verbunden.

    Nur schade, dass er mir keinen Hinweis auf Trigger gegeben hat, sondern nur einen Fehler in der Elemente-Tabelle ausgeworfen hatte (oder zumindest wurde der Fehler als das interpretiert...)


    nach diesem Vorbild wurde er erstellt:
    Link : stackoverflow.com/questions/12…ory-of-changes-to-records

    SQL-Abfrage

    1. DROP TRIGGER IF EXISTS MyDB.data__ai;
    2. DROP TRIGGER IF EXISTS MyDB.data__au;
    3. DROP TRIGGER IF EXISTS MyDB.data__bd;
    4. CREATE TRIGGER MyDB.data__ai AFTER INSERT ON MyDB.data FOR EACH ROW
    5. INSERT INTO MyDB.data_history SELECT 'insert', NULL, NOW(), d.*
    6. FROM MyDB.data AS d WHERE d.primary_key_column = NEW.primary_key_column;
    7. CREATE TRIGGER MyDB.data__au AFTER UPDATE ON MyDB.data FOR EACH ROW
    8. INSERT INTO MyDB.data_history SELECT 'update', NULL, NOW(), d.*
    9. FROM MyDB.data AS d WHERE d.primary_key_column = NEW.primary_key_column;
    10. CREATE TRIGGER MyDB.data__bd BEFORE DELETE ON MyDB.data FOR EACH ROW
    11. INSERT INTO MyDB.data_history SELECT 'delete', NULL, NOW(), d.*
    12. FROM MyDB.data AS d WHERE d.primary_key_column = OLD.primary_key_column;
    nein.

    In dem Fall erstellen die Trigger Einträge in den Spalten 1,2 und 3 (von der Basis1 ausgesehen)
    und danach die gleichen Einträge, wie die Tabelle Elemente - nacheinander.

    Wenn man etwas "verkackt" hat in der Spaltenstruktur von elemente zu elemente_history zu übertragen, dann geht der ganze Trigger in die Hose, da er nicht mehr folgendes tun kann:

    Spalte1(elemente) = Spalte4(elemente_history)
    Spalte2(elemente) = Spalte5(elemente_history)...

    somit stimmen die Spaltenanzahlen nicht mehr überein - und es kommt der Fehler.

    Nur schade, dass der so uneindeutig war ...

    Es war mir anfangs nicht bewusst, dass Trigger solche Probleme verursachen können, aber ist eigentlich logisch... Spalten können nur beschrieben werden, wenn sie existieren.
    Spalten, die es nicht gibt und man versucht zu schreiben, werfen einen Fehler aus: Spaltenanzahl stimmt nicht überein.
    Ja, Datenbanken sind halt ein externes System, und die Fehlermeldungen daher vergleichsweise erbärmlich.

    Eigentlich war die Fehlermeldung ja nicht so schlecht, nur hätte er gerne noch die Tabelle angeben können, wo die Spalte fehlte, oder?
    Das war ja aufgrund des Triggers eine andere, als die die du eiglich angesprochen hattest.

    Weiters sind Triggers für derlei Seiteneffekte bekannt und gefürchtet.
    Brauchst du das history-Dingens wirklich? sonst schmeiss es raus.