Hi -
Ich habe eine Auftragsverwaltung in MySQL. Wenn Client A nun
einen Datensatz ausliest und bearbeitet in PHP, dies evtl.
jedoch ne Weile dauert, kann es ja sein, daß sich inzwischen
ein Client B über den Datensatz hermacht und diesen ändert.
…
Das ist das klassische Problem eines „dirty reads“ - Das Themengebiet dieser Problematik heißt Transaktionssicherheit. Es gibt hier mehrere mögliche Lösungen, die jeweils mehr oder weniger Benutzer- bzw. Performancefreundlich sind.
Einen Einstiegsartikel (bzgl. MySql) habe ich auf die schnelle hier gefunden: http://www.linux-magazin.de/Artikel/ausgabe/2001/08/…
Ein Lock der Tabelle während der gesamten Transaktion (holen des Datensatzes, editieren, zurückschreiben), ist natürlich nicht praktikabel - Während der Zeit kann kein anderer auf die Tabelle zugreifen und muß warten bzw. läuft in einen Timeout.
Eine mögliche Lösung wäre diese:
Du ergänzt die fragliche Tabelle um ein TIMESTAMP Feld - Dieses wird von MySql jedesmal auf die aktuelle Systemzeit geupdatet, wenn der Datensatz geschrieben (insert, update) wird.
Jeder Client darf jederzeit einen Datensatz holen.
Wenn ein Client allerdings einen editierten Datensatz speichern möchte, muß er das folgende tun:
-
Tabelle locken (Siehe Artikel)
-
Den Datensatz nochmals holen
-
Die Timestamps der beiden Datensätze vergleichen
-
Die Änderung nur dann schreiben, wenn die Timestamps übereinstimmen
-
Tabelle wieder freigeben
Wie du im Artikel lesen kannst, ist dies eine Transaktion - Du mußt auf jeden Fall sicherstellen, dass jede Anweisung durchlaufen wird - Sonst kannst du eine Menge Probleme bekommen. Wenn sich dein Code zB. beim nochmaligen holen des Datensatzes aufhängt, mußt du zB. unbedingt dafür sorgen, dass die Tabelle wieder freigegeben wird - Sonst hast du einen kapitalen Datenbankaussetzer.
Falls die Timestamps nicht übereinstimmen sollten (Dh. Ein anderer Client hat den Datensatz in der Zwischenzeit geändert), kann man mehrere Strategien fahren:
zB.:
-
Wer zuerst kommt, mahlt zuerst: Fehlermeldung, dass der Datensatz ncht geschrieben werden kann
-
Vergleichen, welche Attribute des Datensatzes verändert wurden - Wenn es keine Überschneidungen gibt, den geholten und den editierten Datensatz mergen und ungefragt in die Datenbank schreiben. VORSICHT: Das geht natürlich nicht immer - Es kommt auf den Datensatz an.
-
Datenbank unlocken und dem Client beide Datensätze präsentieren - Er soll dann beide abgleichen
-
usw.
mfG,
J.P.Jarolim