| Autor |
Nachricht |
zwutz
Mitglied
Benutzerprofil
Anmeldungsdatum: 22.11.2007
Beiträge: 3411
|
zwutz Mitglied
21:04:02 04.03.2010 Titel: |
Änderungen mitverfolgen |
Zitieren |
Ich überleg gerade, wie man es am elegantesten löst, wenn man sämtliche Änderungen an einem Datensatz zeitlich zurückverfolgen können will und wollte euch fragen, ob ihr wisst, wie sowas in der Praxis gemacht wird?
Also ob differentiell oder inkrementell, ob alles in einer Tabelle (langsam, aber "sicherer") oder Endergebnis und Historie in getrennten Tabellen (schneller, dafür Gefahr der Dateninkonsistenz), oder auch völlig anders
Danke für eventuelle Denkanstöße |
_________________ Raise your glass if you are wrong
|
|
 |
noobLolo
Unregistrierter
|
noobLolo Unregistrierter
21:47:21 04.03.2010 Titel: |
|
Zitieren |
meinst du sowas wie undo/redo |
|
|
|
 |
zwutz
Mitglied
Benutzerprofil
Anmeldungsdatum: 22.11.2007
Beiträge: 3411
|
zwutz Mitglied
22:08:07 04.03.2010 Titel: |
|
Zitieren |
ich meine eher, einen Datensatz zu jedem beliebigen Zeitpunkt in der Vergangenheit zurückverfolgen zu können. Eine Historie eben
undo/redo könnte man darüber dann auch lösen, ist aber nicht der Grund, warum ich es machen will |
_________________ Raise your glass if you are wrong
|
|
 |
noobLolo
Unregistrierter
|
noobLolo Unregistrierter
22:15:23 04.03.2010 Titel: |
|
Zitieren |
| zwutz schrieb: | ich meine eher, einen Datensatz zu jedem beliebigen Zeitpunkt in der Vergangenheit zurückverfolgen zu können. Eine Historie eben
undo/redo könnte man darüber dann auch lösen, ist aber nicht der Grund, warum ich es machen will |
hab mal sowas gemacht, dazu hab ich einfach in einer zweiten tabelle alle INSERT, UPDATE und DELETE statements mit den counterparts gespeichert also so in der richtung
| Code: | redo undo
INSERT DELETE
DELETE INSERT
UPDATE UPDATE
| |
| Code: | redo undo
INSERT DELETE
DELETE INSERT
UPDATE UPDATE
| |
| Code: | redo undo
INSERT DELETE
DELETE INSERT
UPDATE UPDATE
| |
das problem ist aber um einen bestimmten zustand herzustellen mußte man immer alle querys wieder ausführen.
bin mittlerweile der meinung, das die db soetwas schon mitbringt? das sollte dann schon das schnellste sein |
|
|
|
 |
zwutz
Mitglied
Benutzerprofil
Anmeldungsdatum: 22.11.2007
Beiträge: 3411
|
zwutz Mitglied
22:27:55 04.03.2010 Titel: |
|
Zitieren |
ich hatte an sowas gedacht:
inkrementell, alles in einer Tabelle:
| Code: | id aennr wert1 wert2 wert3 zeit
--------------------------------------------------------
0 0 eins zwei drei 0
0 1 vier NULL NULL 1
0 2 NULL fünf NULL 2
0 3 NULL NULL sechs 3 | |
| Code: | id aennr wert1 wert2 wert3 zeit
--------------------------------------------------------
0 0 eins zwei drei 0
0 1 vier NULL NULL 1
0 2 NULL fünf NULL 2
0 3 NULL NULL sechs 3 | |
| Code: | id aennr wert1 wert2 wert3 zeit
--------------------------------------------------------
0 0 eins zwei drei 0
0 1 vier NULL NULL 1
0 2 NULL fünf NULL 2
0 3 NULL NULL sechs 3 | |
differentiell, alles in einer Tabelle:
| Code: | id aennr wert1 wert2 wert3 zeit
--------------------------------------------------------
0 0 eins zwei drei 0
0 1 vier NULL NULL 1
0 2 vier fünf NULL 2
0 3 vier fünf sechs 3 | |
| Code: | id aennr wert1 wert2 wert3 zeit
--------------------------------------------------------
0 0 eins zwei drei 0
0 1 vier NULL NULL 1
0 2 vier fünf NULL 2
0 3 vier fünf sechs 3 | |
| Code: | id aennr wert1 wert2 wert3 zeit
--------------------------------------------------------
0 0 eins zwei drei 0
0 1 vier NULL NULL 1
0 2 vier fünf NULL 2
0 3 vier fünf sechs 3 | |
als Ergebnis jeweils zum Zeitpunkt 3:
| Code: | id wert1 wert2 wert3
--------------------------------------
0 vier fünf sechs | |
| Code: | id wert1 wert2 wert3
--------------------------------------
0 vier fünf sechs | |
| Code: | id wert1 wert2 wert3
--------------------------------------
0 vier fünf sechs | |
jetzt besteht natürlich noch die Möglichkeit, das Ergebnis separat abzulegen, was vorteilhaft sein dürfte, wenn man oft den neuesten haben will
aber ok, ich denke, da gibts keine Patentlösung. Ich werd mal die Zwei-Tabellenlösung versuchen... mit Transaktionen sollte ich die Gefahr der Inkonsistenz eigentlich in den Griff bekommen |
_________________ Raise your glass if you are wrong
|
|
 |
Killer-Kobold
Mitglied
Benutzerprofil
Anmeldungsdatum: 16.03.2009
Beiträge: 180
|
Killer-Kobold Mitglied
23:19:48 04.03.2010 Titel: |
|
Zitieren |
| zwutz schrieb: | | aber ok, ich denke, da gibts keine Patentlösung. Ich werd mal die Zwei-Tabellenlösung versuchen... mit Transaktionen sollte ich die Gefahr der Inkonsistenz eigentlich in den Griff bekommen |
So macht es auch die SAP in ihrer BS1-Lösung. Es gibt die Originaltabelle mit dem aktuellen Datensatz und eine Historientabelle, in der der komplette alte Datensatz noch mal liegt, respektive eine einstellbare Anzahl dieser. Der einzige Unterschied im Tabellenaufbau ist eine mitlaufende ID (jeweils von 1 bis x für die alten Datensätze), so dass man die chronologische Reihenfolge sieht. Wenn der x+1 Historiensatz geschrieben werden soll, wird der älteste Datensatz gelöscht. Das wird dort aber wirklich nur zum Nachsehen angeboten, nicht zum Wiederherstellen.
Gruß KK |
|
|
|
 |
hustbaer
Mitglied
Benutzerprofil
Anmeldungsdatum: 27.10.2006
Beiträge: 13509
|
hustbaer Mitglied
00:13:16 05.03.2010 Titel: |
|
Zitieren |
| zwutz schrieb: |
differentiell, alles in einer Tabelle:
| Code: | id aennr wert1 wert2 wert3 zeit
--------------------------------------------------------
0 0 eins zwei drei 0
0 1 vier NULL NULL 1
0 2 vier fünf NULL 2
0 3 vier fünf sechs 3 | |
| Code: | id aennr wert1 wert2 wert3 zeit
--------------------------------------------------------
0 0 eins zwei drei 0
0 1 vier NULL NULL 1
0 2 vier fünf NULL 2
0 3 vier fünf sechs 3 | |
| Code: | id aennr wert1 wert2 wert3 zeit
--------------------------------------------------------
0 0 eins zwei drei 0
0 1 vier NULL NULL 1
0 2 vier fünf NULL 2
0 3 vier fünf sechs 3 | |
|
wenn dann würde ich es genau so machen, nur würde ich es nicht "differenziell" nennen. ich verstehe glaube ich wie du auf den namen kommst, aber irgendwie finde ich ihn trotzdem nicht passend.
und auf jeden fall alles in einer tabelle.
wenn irgendwas zu langsam wird, kann man ja - je nach datenbank - einen filtered index oder eine indexed view verwenden, die dann nur die jeweils aktuellen datensätze enthält.
wird dadurch nicht wesentlich grösser als die version wo history und current getrennte tables haben, ist schnell abzufragen, und die konsistenz garantiert dir das DBMS.
p.S.: mir fällt gerade auf: ich bin mir gar nicht 100% sicher ob das mit MSSQL (dem einzigen DBMS was ich wirklich gut kenne) mit indexed views und/oder filtered indexes gehen würde...
müsste ich mal ausprobieren... |
_________________ "Let there be Licht..." http://lichttools.sourceforge.net/
Sehr cooles ASCII Spiel (leider nicht von mir): ASCII-Scramble - http://www.roskakori.at/ascii/
Zuletzt bearbeitet von hustbaer am 00:14:42 05.03.2010, insgesamt 2-mal bearbeitet |
|
 |
zwutz
Mitglied
Benutzerprofil
Anmeldungsdatum: 22.11.2007
Beiträge: 3411
|
zwutz Mitglied
08:28:14 05.03.2010 Titel: |
|
Zitieren |
| hustbaer schrieb: | | wenn dann würde ich es genau so machen, nur würde ich es nicht "differenziell" nennen. ich verstehe glaube ich wie du auf den namen kommst, aber irgendwie finde ich ihn trotzdem nicht passend. |
keine Ahnung, wie man es nenn würde, also hab ich es so genannt, wie man es bei Backups nennen würde
Aber danke euch, auf eine View bin ich auch gekommen, so kann ich Geschwindigkeit und Konsistenz denk ich gut unter einem Hut bringen |
_________________ Raise your glass if you are wrong
|
|
 |
Marc++us
Administrator
Benutzerprofil
Anmeldungsdatum: 05.04.2000
Beiträge: 17120
|
Marc++us Administrator
08:57:38 05.03.2010 Titel: |
|
Zitieren |
Wieso nennst Du es nicht "Versionierung"? Von jedem Datum wird doch eine neue Version angelegt. aennr entspricht der Version. |
_________________ Viele Grüße
Marc++us
C++.de
|
|
 |
witte
Mitglied
Benutzerprofil
Anmeldungsdatum: 08.01.2008
Beiträge: 1295
|
witte Mitglied
13:58:17 05.03.2010 Titel: |
|
Zitieren |
Welches DBS verwendest du überhaupt?
Ich hatte mal so ein Projekt bei dem in psychatrischen Einrichtungen auftretende Ereignisse gemeldet werden mussten, die Administratoren sollten diese Meldungen aus Datenschutzgründen anpassen können und das Original sollte jedoch erhalten bleiben weil sich der Staatsanwalt dafür mgl. interessierte. Also ein Original mit n Kopien die in einem Selfjoin auf das Original verwiesen. Ich hatte damals mit einem ORM gelöst: die Klassen haben ICloneable implementiert, die letzte Kopie geladen und mit Clone() neue Objekte erzeugt die dann wieder in den Tabellen eingefügt wurden.
Wenn du die Versionshistorie per Hand bauen willst kannst du mal prüfen wie weit du das mit Trigger/Rules automatisieren kannst damit die Fehleranfälligkeit durch das Implementieren im Client wegfällt. |
|
|
|
 |
zwutz
Mitglied
Benutzerprofil
Anmeldungsdatum: 22.11.2007
Beiträge: 3411
|
zwutz Mitglied
14:18:11 05.03.2010 Titel: |
|
Zitieren |
| witte schrieb: | | Welches DBS verwendest du überhaupt? |
Noch kein spezielles, zur Auswahl stehen aber MySQL und MSSQL.
Bin noch in der Konzeptphase und bau mir grad ein ERM zusammen, dabei kam mir eben der Gedanke, dass eine Änderungshistorie sinnvoll wäre |
_________________ Raise your glass if you are wrong
|
|
 |
Th69
Mitglied
Benutzerprofil
Anmeldungsdatum: 25.03.2008
Beiträge: 2256
|
Th69 Mitglied
15:51:46 05.03.2010 Titel: |
|
Zitieren |
Für eine PostGreSQL-Datenbank habe ich mal eine Historienverwaltung alleine über Trigger gelöst (die Historientabellen waren getrennte Tabellen und jede Tabelle verfügte über eine Datumsstempel-Spalte 'modified_date').
Es mußte dann in der Anwendungssoftware nichts dafür extra programmiert werden.
Nur der Zugriff auf die archivierten Daten (d.h. anhand eines bestimmten Datums) war eine etwas kompliziertere Stored-Procedure.
Da ich mir bei MySQL nicht sicher bin, ob diese schon Trigger unterstützen, würde ich dir dann zu MS-SQL raten (oder aber eben PostGreSQL). |
|
|
|
 |
witte
Mitglied
Benutzerprofil
Anmeldungsdatum: 08.01.2008
Beiträge: 1295
|
witte Mitglied
17:33:25 05.03.2010 Titel: |
|
Zitieren |
| Th69 schrieb: | | Für eine PostGreSQL-Datenbank habe ich mal eine Historienverwaltung alleine über Trigger gelöst (die Historientabellen waren getrennte Tabellen und jede Tabelle verfügte über eine Datumsstempel-Spalte 'modified_date'). | Wieso nimmst du dafür nicht RULES? Ist doch noch einfacher. |
|
|
|
 |
hustbaer
Mitglied
Benutzerprofil
Anmeldungsdatum: 27.10.2006
Beiträge: 13509
|
hustbaer Mitglied
20:27:52 05.03.2010 Titel: |
|
Zitieren |
Das schöne an INSERT-only Lösungen ist doch dass sie INSERT-only sind
D.h. man muss weder DELETE noch UPDATE Rechte vergeben.
D.h. man kann *sicher* sein, dass *nie* alte Daten vernichtet werden, egal was die Anwendung macht.
(Natürlich nur solange man davon ausgeht dass das DBMS keinen Bug hat, aber da mache ich mir weniger Sorgen)
Ich finde das immer äusserst beruhigend.
Und natürlich ist es toll für die Beweisbarkeit.
Und es ist eine IMO sehr einfache sowie elegante Lösung. |
_________________ "Let there be Licht..." http://lichttools.sourceforge.net/
Sehr cooles ASCII Spiel (leider nicht von mir): ASCII-Scramble - http://www.roskakori.at/ascii/
|
|
 |
BasicMan01
Mitglied
Benutzerprofil
Anmeldungsdatum: 18.02.2004
Beiträge: 646
|
BasicMan01 Mitglied
00:40:03 06.03.2010 Titel: |
|
Zitieren |
ich bevorzuge die Methode der 2 Tabellen. Die Tabelle mit den original-Datensaetzen und die Historie mit allen Vergangenen, identifiziert durch eine
steigende Versionsnummer. Je nach Struktur sind Trigger durchaus hilfreich.
Kommt halt drauf an, was bei einer Aenderung noch alles gemacht werden soll. Das
reine wegsichern der Datensaetze in eine Historientabelle mit Version und Datum
ist hier aber mit nem Trigger vorzuziehen. Dann vergisst man es wenigstens nicht
Durchaus kann man in die Historientabelle auch noch den aktuellen Datensatz mit auflisten. Gerade wenn man Versionsdatensaetze fuer einen Benutzer zur Uebersicht
anzeigen moechte, spart man sich hier das zusammenfrimeln aus zwei Tabellen.
Geschmackssache. |
_________________ Der Vorteil in der Klugheit besteht darin, dass man sich dumm stellen kann.
(Code::Blocks 10.5, mingw32 gcc 4.4.1)
|
|
 |
pferdefreund
Mitglied
Benutzerprofil
Anmeldungsdatum: 19.03.2009
Beiträge: 115
|
pferdefreund Mitglied
15:32:12 18.03.2010 Titel: |
|
Zitieren |
Ich hab sowas auch mit nem Trigger (Postgresql) gelöst.
Hat den Vorteil, daß egal, wie auf die DB zugegriffen wird. Tool,
Konsoleninterface, Anwendung - auf jeden Fall die Historie geschrieben wird. |
|
|
|
 |