# Benachrichtigung wenn sich Datenbank ändert



## Saxony (30. Jan 2007)

Hallo,

ich lese mit meinem Java-Programm die MSSQL Datenbank einer anderen Anwendung aus.
Wie bekomme ich nun in meinem Programm aber mit, dass sich nach dem ersten Lesen etwas in der Datenbank geändert hat.

Ich möchte dafür nicht extra einen Thread laufen lassen, welcher permanent nach Änderungen sucht, dafür müsste es doch etwas eleganteres geben. Zum Beispiel, dass die DB sich bei meinem Programm meldet und mitteilt es hat sich was geändert.


vielen Dank
Saxony


----------



## KSG9|sebastian (30. Jan 2007)

Geht nicht. Die Datenbank ist grundsätzlich mal "doof" und gibt dir nur was du von ihr forderst. Listener oder ähnliches gibts nicht. Du könntest die DB vielleicht so "mißhandeln" dass du bei jedem Insert, Update oder Delete ne SP aufrufst welche in ner separaten Tabelle ein flag ändert. Aber dann kommst du trotzdem nicht drum rum diese Tabelle ständig abzufragen.


----------



## L-ectron-X (30. Jan 2007)

Schreib dir einen Server, der vor der Datenbank liegt und alle DB-Manipulationen macht. Dieser kann sich dann auch beim Client melden, wenn es Neues gibt.


----------



## AlArenal (30. Jan 2007)

L-ectron-X hat gesagt.:
			
		

> Schreib dir einen Server, der vor der Datenbank liegt und alle DB-Manipulationen macht. Dieser kann sich dann auch beim Client melden, wenn es Neues gibt.



Was das Problem ja lediglich in eine andere Schicht verlagert und nicht direkt löst.

Je nach DB hat man die Möglichkeit über Trigger Tabellen zu überwachen und beispielsweise in einer separaten Status-Tabelle entsprechende Flags zu setzen. Oder man setzt in allen Tabellen Timestamps und überprüft periodosch den neuesten Timestamp in der DB auf Gleichheit mit dem letzten eingeleesenen Stand in der Anwendung, oder oder oder... 

Zumindest bei Veränderung der Daten gilt es zuvor deren Gültigkeit zu überprüfen, ggf. Locks zu setzen, ...


----------



## abollm (30. Jan 2007)

Saxony hat gesagt.:
			
		

> [..]
> ich lese mit meinem Java-Programm die MSSQL Datenbank einer anderen Anwendung aus.
> Wie bekomme ich nun in meinem Programm aber mit, dass sich nach dem ersten Lesen etwas in der Datenbank geändert hat.
> 
> ...



Ich bin mir nicht sicher, ob ich dich richtig verstehe. Grundsätzlich kannst du jedes _professionelle_ RDBMS so programmieren, dass du bestimmte Änderungen (INSERT, UPDATE, DELETE) 1. erkennen und 2. darauf in geeigneter Weise reagieren kannst. Diese Dinge werden üblicherweise so realisiert, dass du mit einem geeigneten Trigger (z.B. INSERT-Trigger) auf das betreffende Ereignis entsprechend reagierst. Günstig ist in einem derartigen Fall, sich eine so genannte SP (Stored Procedure) zu schreiben, die die gewünschten Aktionen auf ein INSERT, UPDATE oder DELETE direkt in der DB-Engine ausführt.

Leider kenne ich mich mit dem MS SQL-Server zu wenig aus, dass ich dir konkretere Hinweise geben kann. Trigger sind aber möglich und SPs auch. Allerdings sind die Trigger-Möglichkeiten bei weitem nicht so umfangreich und vielfältig wie bei dem Oracle-RDBMS.

Grundsätzlich und damit auch weitestgehend unabhängig vom verwendeten RDBMS kann man das Problem auch mit einer ganz anderen Technik versuchen zu lösen. Stichworte hierzu: J2EE, JMS etc. Das wäre aber hier im Forum nur sehr bedingt richtig aufgehoben.


----------



## culllmann (31. Jan 2007)

Servus abollm

Das würd mich aber auch intresieren wie man das mit J2EE lösen kann. Das mit den Trigger is klar,  nur wie man das dann mit J2EE oder JMS lösen kann verstehe ich net.

Könntest du mir vielleicht ein paar nähre informationen geben. Wäre dir sehr dankbar.

Cullmann


----------



## abollm (31. Jan 2007)

Hi cullmann,

mache ich gerne, aber nicht jetzt, weil ich dazu weiter ausholen muss. Vermutlich am späten Abend heute. Ich bin den Tag über unterwegs.

Gruß


----------



## Saxony (31. Jan 2007)

Hallo,

Trigger und Stored Procedures sind ja alles schöne Dinge, leider reichen diese nicht für meinen Zweck aus.
Mein Programm muss ja wissen wenn sich was ändert, um zum Beispiel Inhalte in Tabllen aktuell zu halten.
Ichj habe das jetzt mal mit einem Trigger der auf INSERT, UPDATE und DELETE horcht, gemacht. Dieser Trigger setzt dann in ein Temp Table ein Falg, welches ich in einem Thread abfrage.
Dabei gefallen mir aber immer noch drei Dinge nicht:

1. Habe ich es nur geschafft, dass mein Trigger auf eine Tabelle aufpasst. Ich möchte aber, dass dieser auf ein komplettes Schema aufpasst, unter Annahme, dass ich die einzelnen Tabellennamen nicht weiß.

2. Werde ich im produktiven Einsatz nicht die Möglichkeit haben Relationen zu erstellen, d.h. die Sache mit Temp Table und Flag setzen fällt raus.

3. Habe ich einen Thread der permanent nach Änderungen sucht = inakzeptabel.

Gibt es nicht sowas wie bei RS232 oder Sockets wo ich ohne Polling arbeiten kann?
Obwohl hierbei eigentlich auch wieder ein Thread entsteht der am Port lauschen muss.
Aber das ist auf jeden Fall besser, dass mein Thread an einem Port auf Benachrichtigung wartet als permanent irgendwelche SELECTs zu generieren.

Kann ich mit Stored Procedures eigentlich Daten an einen Port schicken?

Eigentlich ist es schon komisch, dass es so etwas nicht gibt. Ich bin doch bestimmt nicht der erste der informiert werden will, wenn sich etwas in der Datenbank ändert.

bye
Saxony


----------



## AlArenal (31. Jan 2007)

Kurz und knapp: Nein!

Eine Datenbank wird dich genausowenig über irgendwas benachrichtigen wie auch ein Webserver dich nicht anrufen wird, wenn jemand ne neue Seite hochgeladen hat. Beides sind Client-Server-Systeme und ein Server *re*agiert nunmal nur auf Anfragen. Eine RDBMS ist kein Blackberry.

Entweder du baust dir eine von Electronics vorgeschlagene Zwischenschicht, oder du hast eben Pech gehabt. Wo dein Problem liegt eine Überwachungsthread zu bauen, verstehe ich nicht ganz. Lass den Client alle x Sekunden nachhaken, ob sich in der DB was getan hat und überprüfe deine Datensätze vor Schreiboperationen entsprechend auf Gültigkeit und gut iss.


----------



## DocRandom (31. Jan 2007)

AlArenal hat gesagt.:
			
		

> Kurz und knapp: Nein!


..eher Jein! 



			
				AlArenal hat gesagt.:
			
		

> Eine Datenbank wird dich genausowenig über irgendwas benachrichtigen wie auch ein Webserver dich nicht anrufen wird, wenn jemand ne neue Seite hochgeladen hat. Beides sind Client-Server-Systeme und ein Server *re*agiert nunmal nur auf Anfragen. Eine RDBMS ist kein Blackberry.


Stimme ich Dir im Grundprinzip zu.
Es gibt aber auch RDBMS wo ich per Trigger Events weiiterleiten kann.
MSSQL bietet z.B. die Möglichkeit per Mail weiter zu leiten
PostgresSQL hat sogar Messaging per Sockets im Programm und wird z.B. von mir genutzt, da ich damit meine Faximiles an den Asterisk - Server weiterleite.
Was ORACLE, etc. kann, weiß ich ned, da ich mit diesen Systemen kaum vertraut bin


			
				AlArenal hat gesagt.:
			
		

> Entweder du baust dir eine von Elektron vorgeschlagene Zwischenschicht...


Ist ohnehin der gängige Weg bei profesionellen Systemen

lg
DocRandom


----------



## KSG9|sebastian (31. Jan 2007)

Ich versteh schon den Problem, aber denk mal weiter was für einen Listener notwendig wäre den du gerne hättest. Das geht weit über eine Datenbank hinaus. Wie schon geschrieben, die Datenbank bzw. das DBMS gibt dir die Daten die du anforderst. Was du willst ist schon fast eine Kommunikation über verschiedene Schichten, und das von der Datenbank aus. Übertrieben gesagt würdest du teilweise die Datenbank vom Programm/Server abhängig machen, jenachdem was du für Listener willst.


----------

