Announcement

Collapse
No announcement yet.

Datensätze sperren

Collapse
X
  • Filter
  • Time
  • Show
Clear All
new posts

  • Datensätze sperren

    Hallo zusammen,

    ich habe eine Anwendung derren Datenbank auf einem SQL Server läuft. Manchmal passiert es das die Benutzer sich gegenseitig die Daten verhauen, wenn zwei Benutzer den selben Datensatz öffnen.

    Beim Speichern kommt dann eine Exception. Diese hab ich schon angefangen. Aber ich möchte das schon beim Ausführen von Edit(); eine Exeception ausgelöst wird. Ich hab es bisher mit dbSeeChance und dbPessimistic versucht. Aber geht aber auch nicht. Hat jemand ein Tipp ?


    Zb. : if (rgTabelle->ItemIndex==2)qAdmin->SQL->Add("select * from MeldebuchDaten dbPessimistic;");
    ( qAdmin ist ein SQLQuery)

    Danke,

  • #2
    Hallo,
    Originally posted by Brian79rh View Post
    ...Aber geht aber auch nicht.
    Das ist KEINE qualifizierte Fehlerbeschreibung! WAS geht nicht? WELCHER Fehler tritt auf?
    Originally posted by Brian79rh View Post
    ...Hat jemand ein Tipp ?
    Wofür? Was ist die Frage?

    Gruß Falk
    Wenn du denkst du hast alle Bugs gefunden, dann ist das ein Bug in deiner Denksoftware.

    Quellcode ohne ein Mindestmaß an Formatierung sehe ich mir nicht an! Ich leiste keinen Privatsupport per Mail oder PN!

    Comment


    • #3
      In vielen Fällen ist ein manuelles Sperrkennzeichen im Datensatz auch sinnvoll.
      User A: prüft, updatet spalte "gesperrt", ruft Daten ab
      User B: prüft, gibt Fehlermeldung zurück
      User A: updatet und setzt spalte "gesperrt" zurück
      User B: prüft, updatet spalte "gesperrt", ruft Daten ab
      ...

      Comment


      • #4
        Hallo,
        Originally posted by CLL View Post
        In vielen Fällen ist ein manuelles Sperrkennzeichen im Datensatz auch sinnvoll....
        Man sollte sich aber über die Nachteile eines solchen Verfahrens im Klaren sein! Erstens ist es nicht Multiuserfähig und beseitigt die vom TE genannten Probleme NICHT! Zum Anderen muss man sich Strategien für den Fall überlegen, dass User A NIE speichert, weil er z.B. seinen Rechner einfach ausschaltet, oder in einer browserbasierten Anwendung einfach zu einer anderen Seite surft.
        Klassische Sperrverfahren sind hingegen nur bei persistenten Datenbankverbindungen sinnvoll realisier- und einsetzbar. Bei browserbasierten Anwendungen müssen diese mit anderen Mechanismen kombiniert werden. Denkbar wäre z.B. ein zusätzliches Feld mit einem Hash der Daten oder der Einfachheit halber auch ein Timestamp der letzten Änderung. Dieses "Kontrollfeld" wird zusammen mit den Daten gelesen und unmittelbar vor dem eigenen Speichervorgang in der DB überprüft. Hat sich das Feld geändert, wurden die Daten zwischenzeitlich von einer anderen Session geändert und man kann darauf reagieren, z.B. den User entscheiden lassen ob er trotzdem Speichern will. Das Prüfen des "Kontrollfeldes" und das Update sollten dann in jedem Fall mit einem herkömmlichen Sperrverfahren auf DB-Ebene abgesichert werden.

        Gruß Falk
        Wenn du denkst du hast alle Bugs gefunden, dann ist das ein Bug in deiner Denksoftware.

        Quellcode ohne ein Mindestmaß an Formatierung sehe ich mir nicht an! Ich leiste keinen Privatsupport per Mail oder PN!

        Comment


        • #5
          Originally posted by Falk Prüfer View Post
          Hallo,

          Das ist KEINE qualifizierte Fehlerbeschreibung! WAS geht nicht? WELCHER Fehler tritt auf?

          Wofür? Was ist die Frage?

          Gruß Falk


          Servus zusammen,

          Zurzeit ist es so das wenn zwei Benutzer den selben Datensatz bearbeiten wollen, werden auch bei beiden Benutzer Edit(); Fehlerfrei ausgeführt. Speichert nun User B kommt die Fehlermeldung "Die zu aktualliesierende Zeile wurde nicht gefunden".
          Diese Exception habe ich abgefangen um den User eine eigene Fehlermeldung anzuzeigen.

          Ich möchte es gerne das aber schon das wenn User A Edit(); ausführt und dann noch User B Edit(); ausführen will eine Exception ausgelöst wird. So das ich dem User B eine Meldung zeigen kann das der Datensatz gerade wo anders bearbeitet wird und er es später noch mal versuchen soll.

          Die Frage ist nun, wie kann ich es erreichen das der SQL Server schon bei Edit eine Exception auslöst und nicht erst bei Post(); Unser EDV Mensch (der u.a. auch diesen Server betreibt) Sagte nur versuch es mal mit DBSeeChange oder DBPessimistic. Dies gibt allesdings nicht das erwünschte Ergebniss. Weiter sagte er das es schon in der Grundeinstellung so gehen müsste. Macht es aber nicht.


          Habt ihr ein Tipp dazu ? Die Anwendung selbst läuft in einem Lokalen Netzwerk. Die Lösung von CLL wäre denke ich machbar.

          Comment


          • #6
            Hallo,
            Originally posted by Brian79rh View Post
            ...Speichert nun User B kommt die Fehlermeldung "Die zu aktualliesierende Zeile wurde nicht gefunden".
            Diese Exception habe ich abgefangen um den User eine eigene Fehlermeldung anzuzeigen.
            Das ist ein Problem, bzw. eine Exception deiner DB-Zugriffsschicht und hat primär nichts mit MySQL zu tun.

            Originally posted by Brian79rh View Post
            ... Unser EDV Mensch (der u.a. auch diesen Server betreibt) Sagte nur versuch es mal mit DBSeeChange oder DBPessimistic. Dies gibt allesdings nicht das erwünschte Ergebniss.
            Wundert mich nicht, DBSeeChange oder DBPessimistic kenne ich nicht im Zshg. mit MySQL und schon gar nicht in der Form in der du es in deine Abfrage eingebaut hast. Auch dies sind sicherlich Parameter deiner DB-Zugriffsschicht oder für die Aufrufe von "Edit();" bzw. "Post();"

            Originally posted by Brian79rh View Post
            ...Die Lösung von CLL wäre denke ich machbar.
            Bedenke aber, dass diese Lösung ohne weitere Absicherung durch echtes Locking dein Problem nicht wirklich beseitigt sondern nur "unwahrscheinlicher" macht! Da zwischen "prüft" und "updatet spalte "gesperrt"" eine gewisse Zeit vergeht, ist es durchaus möglich, dass zwei zeitgleiche Transaktionen den Datensatz als "frei" gemeldet bekommen! Besser wäre hier mit einer zentralen "Sperrtabelle" zu arbeiten, statt einer "gesperrt"-Spalte in der Tabelle. In dieser Sperrtabelle könnte dann ein passender UNIQUE-KEY liegen, der doppelte Einträge verhindert. Das "prüft" entfällt dann. Es wird sofort versucht den "Sperrdatensatz" zu erstellen. Scheitert dies mit einer UNIQUE-KEY-Verletzung, ist die Sperre bereits gesetzt. Aber auch jetzt bleibt immer noch das Problem der "hängenden Sperren". Wenn z.B. die Client-Anwendung abschmiert oder User A nach dem Edit(); in die Mittagspause geht. Die DB selbst hat hier keine Möglichkeit solche Sperren zu erkennen und diese ggfs. aufzuheben. Dies erreicht man dann nur durch Verwendung der Sperrmechanismen der DB.

            Gruß Falk
            Wenn du denkst du hast alle Bugs gefunden, dann ist das ein Bug in deiner Denksoftware.

            Quellcode ohne ein Mindestmaß an Formatierung sehe ich mir nicht an! Ich leiste keinen Privatsupport per Mail oder PN!

            Comment

            Working...
            X