Michael - Hannover: Dateien -> gleichzeitiges lesen/schreiben verhindern

Hallo !

ich möchte innerhalb eines PHP Scriptes ein Fehlerprotokoll erstellen/speichern

um user aborts zu ignorieren, geschieht dies vorerst vor jeglicher Ausgabe an den Client

mein Problem/Frage

Wie kann ich effektiv und unter Berücksichtigung von XXXXX Prozessen eine "sichere" und korrekte Speicherung der Daten gewährleisten ?

meine eigenen Ansätze dazu (Umsetzung in PHP-Befehle später)

Datei öffnen
 Datei versuchen zu sperren (exkl.Lock + LOCK_NB)
 WENN erfolgreich
    schreiben
    Datei schließen
 SONST
   SOLANGE Sperren nicht erfolgreich (idealerweise max.5 Sekunden(?))
     Versuchen zu sperren
     WENN erfolgreich
       schreiben
       Datei schließen
     ENDE
   ENDE
   --> falls das auch nicht geklappt hat, randomized temp.file
       anlegen, wobei hier dann wieder zu Beginn des Codings
       die Existenz eines solchen Files abgefragt werden müßte
       (unique Datei-Endung vorausgesetzt)
       dieses wird dann exklusiv geöffnet(fopen($temp.file,"r+"))
       /gesperrt (Wartezeit einkalkulieren) Inhalt ins richtige
       File portiert,temp.file gelöscht
 ENDE

geht das auch effizienter ? und vor allem schneller ?

...wahrscheinlich ist es ab einer best. Menge der laufenden Prozesse nicht mehr möglich, die Datei-Änderung ohne korruption vorzunehmen oder ?

oder GENERELL ein randomized temp.file anlegen und per Cronjobs zusammenführen und danach löschen

  1. Hello,

    Du hast ja LOCK_NB schon entdeckt. Das bedeutet also, dass die Lock-Funktion das Locking versucht und wenn sie nicht erfolgreich war, einen Fehler zurückgibt. Du gerätst also nicht ins Timeout des Scriptes.

    Wenn man das Locking auf diese Weise durchführt, sollte man es in eine Schleife packen und nach einem erfolglosen Lockversuch 5ms warten. Fünf Versuche dürften reichen, da die Funktion auf LowLevelEbene selber nochmals fünf Versuche in sehr kurzen Abständen vornimmt. Damit es keine Deadlocks gibt, kann man die Wartezeit auch mit jedem Zyklus etwas zufällig verändern. Aber das ist dann schon höhere Mathematik.

    Das Öffnen der Datei sollte man jedenfalls nondestructive vornehmen, also mit dem Modus "r+" oder wenn man sich sein kann, dass die Datei vorhanden ist, mit "a+".

    Liebe Grüße aus http://www.braunschweig.de

    Tom

    --
    Fortschritt entsteht nur durch die Auseinandersetzung der Kreativen
    1. ich hab vielleicht eine noch effizientere Lösung gefunden

      1. Teil

      versuchen die (richtige) Error-Datei zu öffnen/sperren
      WENN erfolgreich
        alle aktuellen randomized.temp lesen, und am Ende der
        Error-Datei einfügen
        alle aktuellen randomized.temp löschen
      ENDE

      2. Teil

      erzeugen einer Datei mit zufallsgeneriertem Namen randomized.temp
      Fehler reinschreiben
      fertig

      ....meiner Meinung nach, müßte das recht performant sein und es
      ist gewährleistet, dass immer nur EIN Prozess die originale
      Error_Datei bearbeitet
      ...die Menge der randomized.temp dürfte immer recht gering sein
      ...keine unnötigen Wartezeiten des Prozesses wegen bestehender Locks

      was meint ihr dazu ?

      die LOCK_NB Option ist nicht unbedingt das Wahre, wenn ich (fiktiv) zigtausende Prozesse annehme...alle warten...dann macht der Server doch irgendwann dicht (öhh all-inkl.com, wieviele Prozesse erlauben die ? *grins)

      1. Hello,

        die eigentliche Bearbeitung einer Datei kann bis zu einer Größe von 1-2MB in weniger als einer Millisekunde stattfinden. Der gesamte Vorgang wird dann mit Allokationszeit auf einem vernüftigen System vielleicht 8ms benötigen. Das bedeutet also, dass rechnerisch ca. 125 Prozesse pro Sekunde abgewickelt werden können.

        Für wichtig halte ich eigentlich nur, dass kein Handlewwechsel zwischen fopen und flock und fread und fwrite stattfindet, dass direkt vor jedem Schreibvorgang nochmals gelesen wird und ggf. geprüft, ob es sich noch um die erwarteten Daten handelt (Conflict Counter).

        Und dann sofort wieder freigeben.

        Liebe Grüße aus http://www.braunschweig.de

        Tom

        --
        Fortschritt entsteht nur durch die Auseinandersetzung der Kreativen