Bestätigen Sie vor dem Löschen / Aktualisieren in SQL Management Studio?

8

So hat jemand am zweiten Tag hintereinander eine ganze Datentabelle ausgelöscht, im Gegensatz zu der einen Zeile, die sie löschen wollten, weil sie nicht die qualifizierte where-Klausel hatten.

Ich habe die mgmt Studio-Optionen alle auf und ab, aber ich kann keine Bestätigungsoption finden. Ich weiß, andere Tools für andere Datenbanken haben es.

    
Greg J 11.11.2008, 16:13
quelle

10 Antworten

14

Ich schlage vor, dass Sie immer zuerst die SELECT-Anweisung mit der WHERE-Klausel schreiben und dann ausführen, um zu sehen, welche Zeilen Ihr DELETE-Befehl löschen soll. Führen Sie dann DELETE mit derselben WHERE-Klausel aus. Gleiches gilt für UPDATEs.

    
Rockcoder 11.11.2008 16:33
quelle
13

Unter Extras & gt; Optionen & gt; Abfrageausführung & gt; SQL Server & gt; ANSI können Sie die Option Implizite Transaktionen aktivieren, was bedeutet, dass Sie den Befehl Begin Transaction nicht explizit einfügen müssen.

Der offensichtliche Nachteil dabei ist, dass Sie vielleicht vergessen, am Ende ein Commit (oder Rollback) hinzuzufügen, oder schlimmer noch, Ihre Kollegen fügen Commit standardmäßig am Ende jedes Skripts hinzu.

Du kannst das Pferd zum Wasser führen ...

Sie können vorschlagen, dass sie immer eine Ad-hoc-Sicherung machen, bevor sie irgendetwas (je nach Größe Ihrer Datenbank) nur für den Fall machen.

    
CJM 11.11.2008 16:24
quelle
4

Versuchen Sie es mit BEGIN TRANSACTION , bevor Sie Ihre DELETE -Anweisung ausführen.

Dann können Sie COMMIT oder ROLLBACK selbe auswählen.

    
Galwegian 11.11.2008 16:15
quelle
3

In SSMS 2005 können Sie diese Option unter Extras | Optionen | Abfrageausführung | SQL Server | ANSI ... aktivieren SET IMPLICIT_TRANSACTIONS . Dies erfordert ein Commit, um das Aktualisieren / Löschen von Abfragen für zukünftige Verbindungen zu bewirken.

Wechseln Sie für die aktuelle Abfrage zu Abfrage | Abfrageoptionen | Ausführung | ANSI und aktivieren Sie das gleiche Kontrollkästchen.

Diese Seite enthält auch Anweisungen für SSMS 2000, falls Sie das verwenden.

Wie andere darauf hingewiesen haben, wird hier nicht auf die Ursache eingegangen: Es ist fast so einfach, am Ende jeder neuen Abfrage, die Sie erstellen, ein COMMIT einzufügen, um überhaupt eine Abfrage auszulösen.

    
Dave DuPlantis 11.11.2008 16:29
quelle
3

Erstens sind dies Audit-Tabellen. Wenn Sie wissen, wer alle Datensätze gelöscht hat, können Sie entweder ihre Datenbankberechtigungen einschränken oder sich mit ihnen aus einer Leistungsperspektive befassen. Die letzte Person, die das in meinem Büro getan hat, ist derzeit auf Bewährung. Wenn sie es wieder tut, wird sie losgelassen werden. Sie haben die Verantwortung, wenn Sie Zugriff auf Produktionsdaten haben und sicherstellen, dass Sie keinen Schaden anrichten. Dies ist ein Leistungsproblem ebenso wie ein technisches Problem. Sie werden nie einen Weg finden, Menschen daran zu hindern, dumme Fehler zu machen (die Datenbank hat keine Möglichkeit zu wissen, ob Sie Tabelle a löschen oder Tabelle a löschen möchten, wobei id = 100 und eine Bestätigung von den meisten Leuten automatisch getroffen wird). Sie können nur versuchen, sie zu reduzieren, indem Sie sicherstellen, dass die Personen, die diesen Code ausführen, verantwortlich sind und Richtlinien einführen, die ihnen helfen, sich zu erinnern, was zu tun ist. Mitarbeiter, die sich unverantwortlich mit Ihren Geschäftsdaten verhalten (insbesondere nachdem sie eine Warnung erhalten haben) sollten gefeuert werden.

Andere haben die Art von Dingen vorgeschlagen, die wir tun, um dies zu verhindern. Ich bette immer eine Auswahl in eine Löschung, die ich aus einem Abfragefenster ausführen, um sicherzustellen, dass es nur die Datensätze löscht, die ich beabsichtige. Unser gesamter Produktionscode, der Daten ändert, einfügt oder löscht, muss in einer Transaktion enthalten sein. Wenn es manuell ausgeführt wird, führen Sie das Zurücksetzen oder Festschreiben nicht aus, bis die Anzahl der betroffenen Datensätze angezeigt wird.

Beispiel für das Löschen mit eingebetteter Auswahl

%Vor%

Aber selbst diese Techniken können nicht alle menschlichen Fehler verhindern. Ein Entwickler, der die Daten nicht versteht, kann die Auswahl ausführen und immer noch nicht verstehen, dass er zu viele Datensätze löscht. Das Ausführen einer Transaktion kann bedeuten, dass Sie andere Probleme haben, wenn die Benutzer vergessen, das System zu committen oder zurückzusetzen und das System zu sperren. Oder Leute können es in eine Transaktion einfügen und immer noch commit ohne nachzudenken, so wie sie bestätigen würden, in einem Meldungsfeld, wenn es eines gibt. Die beste Vorbeugung ist eine Möglichkeit, sich schnell von solchen Fehlern zu erholen. Die Wiederherstellung von einer Überwachungsprotokolltabelle ist in der Regel schneller als bei Sicherungen. Außerdem haben Sie den Vorteil, dass Sie erkennen können, wer den Fehler gemacht hat und welche Datensätze betroffen sind (vielleicht haben Sie nicht die gesamte Tabelle gelöscht, aber Ihre WHERE-Klausel war falsch und Sie haben ein paar falsche Datensätze gelöscht.)

In den meisten Fällen sollten Produktionsdaten nicht im laufenden Betrieb geändert werden. Sie sollten die Änderung Skript und überprüfen Sie es zuerst auf Dev. Dann müssen Sie nur noch das Skript ohne Änderungen ausführen, anstatt einzelne Teile einzeln hervorzuheben und zu bearbeiten. In der realen Welt ist dies nicht immer möglich, da Sie manchmal etwas reparieren, das nur auf Prod repariert wurde und jetzt repariert werden muss (zum Beispiel wenn sich keiner Ihrer Kunden anmelden kann, weil kritische Daten gelöscht wurden). In einem solchen Fall haben Sie möglicherweise nicht den Luxus, das Problem zuerst auf dev zu reproduzieren und dann den Fix zu schreiben. Wenn Sie diese Art von Problemen haben, müssen Sie möglicherweise direkt auf prod reparieren und Sie sollten nur DBAS oder Datenbank-Analysten, oder Konfigurations-Manager oder andere, die normalerweise für Daten auf dem Produkt verantwortlich sind, tun den Fix kein Entwickler. Entwickler im Allgemeinen sollten keinen Zugang zu Produkten haben.

    
HLGEM 11.11.2008 18:45
quelle
2

Deshalb glaube ich, dass Sie immer:

sollten

1 Verwenden Sie gespeicherte Prozeduren, die vor der Bereitstellung in der Produktion in einer Entwicklungsdatenbank getestet wurden

2 Wählen Sie die Daten vor dem Löschen

3 Screen-Entwickler, die einen Interview- und Leistungsbeurteilungsprozess verwenden:)

4 Basisleistungsbewertung, wie viele Datenbanktabellen sie löschen / nicht löschen

5 Behandle die Produktionsdaten so, als ob sie giftig wären und habe große Angst.

    
Dining Philanderer 11.11.2008 16:25
quelle
2

Für den zweiten Tag in Folge hat jemand eine ganze Datentabelle ausgelöscht, im Gegensatz zu der einen Zeile, die sie löschen wollten, weil sie nicht die qualifizierte where-Klausel

Wahrscheinlich ist die einzige Lösung, jemand durch jemand anderen zu ersetzen;). Andernfalls finden sie immer ihre Problemumgehung

Schließe schließlich den Datenbankzugriff für diese Person und stelle sie der gespeicherten Prozedur zur Verfügung, die den in der where-Klausel verwendeten Parameter akzeptiert und ihnen den Zugriff zum Ausführen dieser gespeicherten Prozedur gewährt.

    
kristof 11.11.2008 18:28
quelle
1

Ziehen Sie Ihr bestes Trogdor und Burninate an, bis sie lernen, die WHERE-Klausel einzufügen.

Der beste Rat ist, die Muckety-Mucks, die in der Datenbank herumfummeln, dazu zu bringen, beim Testen Transaktionen zu verwenden. Es ist ein langer Weg in Richtung "hoppla" Momente zu verhindern. Der Vorbehalt ist, dass Sie sie jetzt COMMIT oder ROLLBACK sagen müssen, weil sie Ihre DB sicher mindestens einmal sperren werden.

    
LeppyR64 11.11.2008 16:27
quelle
1

Sperren Sie es:

REVOKE löschen Sie die Rechte für alle Ihre Tabellen.

Fügen Sie einen Audit-Trigger und eine Audit-Tabelle ein.

Erstellen Sie parametrisierte Lösch-SPs und geben Sie nur die Rechte für die Ausführung nach Bedarf.

    
Cade Roux 11.11.2008 18:59
quelle
0

Gibt es keine Möglichkeit, Benutzern die gewünschten Ergebnisse zu liefern, ohne einen rohen SQL-Zugriff bereitzustellen? Wenn Sie mindestens ein separates Eingabefeld für "WHERE" hätten, könnten Sie es auf "WHERE 1 = 0" oder so einstellen.

Ich denke, es muss einen Weg geben, diese auch aus der Transaktionsprotokolle herauszuholen. Aber wahrscheinlich nicht, ohne alles zurückzurollen und dann selektiv nach dem fatalen Fehler wieder anzuziehen.

Eine weitere hässliche Option besteht darin, einen Trigger zu erstellen, um alle DELETEs (möglicherweise über eine minimale Anzahl von Datensätzen) in eine Protokolltabelle zu schreiben.

    
dkretz 11.11.2008 18:55
quelle

Tags und Links