2016-06-07 18 views
1

Ich habe eine MySql-Datenbank mit neun Tabellen darin. Ich muss zu sechs von ihnen dynamisch von einem asynchronen Auftrag innerhalb C# hochladen. Um jedoch den Upload zu beschleunigen, verwenden vier von ihnen MySqlBulkLoader, während die anderen beiden eine manuelle Upload-Methode verwenden. Um Nebenläufigkeit zu unterstützen und Fehler in der Datenbank zu vermeiden, muss ich sie alle gleichzeitig hochladen. Um dies zu tun, habe ich beschlossen, Transaktionen zu verwenden, um sicherzustellen, dass ein "Alles oder nichts" -Typ hochgeladen wird.MySqlBulkLoader mit MySqlCommand In der Transaktion

Darin liegt das Problem: die MySqlCommand Klasse für Transaktionsunterstützung über die MySqlTransaction Klasse ermöglicht es innerhalb seiner Transaction Eigenschaft und die MySqlBulkLoader ermöglicht Atom Upload (ich benutze INNODB für den Motor, siehe mysql - Can MySqlBulkLoader be used with a transaction?). Die MySqlBulkLoader erstellt jedoch eine eigene Transaktion für den atomaren Upload, während eine andere separate Transaktion für die MySqlCommand 's ausgeführt wird, die ich ausführen werde. Dies unterstützt die Serialisierung nicht und kann immer noch zu Fehlern führen, wenn ein Bulk Loader seinen Job abschließt. Die Anwendung wird jedoch geschlossen, bevor eine andere beendet werden kann. Dies wäre lösbar, wenn Transaktionen verschachtelt werden könnten; sie können jedoch nicht: php - Mysql transactions within transactions.

Meine Fragen ist wie folgt: Gibt es eine Möglichkeit in dem C# Anschluss der MySqlBulkLoader wird in Verbindung mit einem MySqlTransaction, und wenn nicht zu erlauben, wenn es eine Möglichkeit ist, um automatisch Änderungen von früheren MySqlBulkLoader s gemacht Rollback. Ich habe in der API von Connector.NET 6.9 geschaut, und es scheint, dass dies möglicherweise über die MySqlConnection.BeginTransaction() Methode möglich ist, aber eine Frage von Werner Wolf schlägt anders vor.

EDIT

fand ich this question von Saravanan. Ich glaube jedoch nicht, dass sich diese Frage auf den Faktor MySqlBulkLoader mit der MySqlCommand bezieht.

Antwort

1

Die ursprüngliche Frage stellt:

ist es eine Möglichkeit, in dem C# Anschluss der MySqlBulkLoader wird in Verbindung mit einem MySqlTransaction
Zu diesem Zweck zu ermöglichen, es scheint, gibt es nicht. Nur zwei Transaktionen zusammen zu schlagen, funktionierte auch nicht, da es die Serialisierung nicht unterstützt (wie ich dachte, würde es nicht). Die alternative Frage fragt jedoch:
, wenn es eine Möglichkeit gibt, Änderungen von vorherigen MySqlBulkLoader s automatisch zu Rollback.
Und wieder scheint es, es gibt keine einfache Möglichkeit, die Änderungen rückgängig zu machen. Natürlich konnte ich die Tabellenzustände vorher und nachher überprüfen, die Einträge löschen, die vorher nicht vorhanden waren; Aber diese Lösung ist nicht optimal. Eine Lösung kann sich jedoch in Form einer Frage ergeben. Die Antwort auf die ursprüngliche Frage postulierte, dass es keine Möglichkeit gab, eine separate Transaktion mit einer MySqlBulkLoader zu verknüpfen; hat jedoch nicht spezifiziert, dass wir einen selbst erstellen könnten (a.k.a., Erweitern der MySqlBulkLoader Klasse, um einen Transaction Instanzparameter einzuschließen). Dies scheint die Lösung des Problems zu sein, ebenso wie die Lösung der gestellten Frage Werner Wolf.

Dies war jedoch nicht die Lösung überhaupt. Da die MySqlBulkLoader ein einfacher Wrapper für die LOAD DATA INFILE Syntax von SQL ist, handelt es sich genau wie die SQL-Abfrage. Und aus der MySQL Reference Manual erhalten wir unsere Antwort:

Die Anweisungen in diesem Abschnitt (und alle Synonyme für sie) enden implizit jede Transaktion aktiv in der aktuellen Sitzung, als ob Sie ein COMMIT vor dem Ausführen der Anweisung getan hätte.
Eine Aussage unten im Abschnitt der Webseite ist LOAD DATA INFILE.Dies ist die wahre Antwort auf unsere Frage: Es ist unmöglich, eine MySqlBulkLoader mit einer MySqlTransaction zu verknüpfen, zumindest dahingehend, dass es so funktioniert, wie wir es vorhaben. Wie oben erwähnt, kann eine Lösung für das Problem jedoch darin bestehen, die Indizes der Primärschlüssel jeder Tabelle zu überprüfen, die Tabelle zu sperren, ihre Position zu speichern und nach einem fehlgeschlagenen Upload ein manuelles "Rollback" durchzuführen.