Entwickler-Ecke
Datenbanken - [FIBDataSet] - Refresh vs. FullRefresh
Der Jan - Do 01.12.05 12:36
Titel: [FIBDataSet] - Refresh vs. FullRefresh
Hallo,
ich schon wieder :roll:
Ich habe eine kleine Personal-Verwaltung geschrieben, die soweit auch gut funktioniert, allerdings habe ich ein Problem beim Refreshen von FIBDataset.
Es wird in die Tabelle PERSONAL ein neuer Record mit Append eingefügt.
nachdem im Formular die Daten eigegeben wurde, schreibe ich den Record in die Tabelle
Delphi-Quelltext
1: 2:
| dsetPers.Post; dsetPers.Refresh; |
Es gibt in der Tabelle ein Feld PERSONALID, welches mittels Trigger/Generator automatisch erzeugt wird. Das funktioniert auch alles wunderbar, die Werte stehen in der Tabelle (Kontrolliert mit IBExpert)
Jetzt kann man dem Record noch Dokumente hinzufügen (Passbild etc.), die in einer anderen Tabelle BLOBS gespeichert werden. Das mach ich über einen FIBQuery.
Delphi-Quelltext
1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11:
| with qryPhoto do begin SQL.Clear; SQL.Add('INSERT INTO "BLOBS" (DATA, PERSONALID, PHOTO, ORIGNAME, ORIGSIZE)'); SQL.Add('VALUES (:DATA, :PERSONALID, :PHOTO, :ORIGNAME, :ORIGSIZE)'); ParamByName('DATA').LoadFromStream(ms); ParamByName('PERSONALID').AsInteger := dsetPers.FieldValues['PERSONALID']; ParamByName('PHOTO').AsString := '1'; ParamByName('ORIGNAME').AsString := ExtractFileName(sName); ParamByName('ORIGSIZE').AsInteger := ms.Size; ExecQuery; end; |
Das funktioniert soweit auch noch, es sei denn, man versucht, ein Dokument einem neu eingefügten Record zuzuweisen. In diesem Fall ist der Wert das Feldes PERSONALID Null. Trotz Refresh.(siehe oben) Mache ich statt dessen dsetPers.FullRefresh, funktioniert es. Nur FullRefresh tut das für alle Records, was ab einer gewissen Anzahl nicht mehr wirklich akzeptabel ist.
Wo könnte hier der Fehler liegen?
alex517 - Do 01.12.05 13:12
Hi Der Jan,
du hast die Möglichkeit die die neue ID noch vor dem Append des neuen Pers-Datensatzes geben zu lassen.
Damit ist diese ID sofort auch für die abhängigen Daten verfügbar.
Das kann man auf zwei Wegen erreichen.
1) in dsetPersNewRecord oder dsetPersBeforePost:
Delphi-Quelltext
1: 2: 3:
| if dsetPersPERSONID.AsInteger = 0 then dsetPersPERSONID.AsInteger := dsetPers.Database.Gen_Id('GEN_PERS', 1); |
oder
2) mit Hilfe der FIBDataSet.AutoUpdateOptions mit GeneratorName, GeneratorStep und WhenGetGenID.
alex
Der Jan - Do 01.12.05 15:06
Hallo,
erstmal Danke für den Tip. Das wars im Wesentlichen. :idea:
Ich habe in Beforepost oder OnNewRecord geschrieben:
Delphi-Quelltext
1: 2: 3:
| with dmodMain.dsetPers do if(FieldByName('PERSONALID').AsInteger = 0) then FieldByName('PERSONALID').AsInteger := Database.Gen_Id('GEN_PERSONAL_ID', 1); |
Bei OnNewRecord hat man noch den Vorteil, das man z.B. das Bild einfügen kann, bevor der Datenssatz in der Tabelle PERSONAL steht.
Funktioniert soweit. Man muß aber in der DB den Trigger für die automatische ID-Generation ausschalten sonst gibts einen Fehler. Siehe Anhang
Besten Dank nochmal!
Der Jan - Do 01.12.05 15:08
Irgendwie krieg ich den Screenshot nicht mitgeschickt.... :(
Er meckert wegen einer ForeignKey-Constraint-Verletzung
alex517 - Do 01.12.05 15:25
Der Jan hat folgendes geschrieben: |
. Man muß aber in der DB den Trigger für die automatische ID-Generation ausschalten sonst gibts einen Fehler. Siehe Anhang
|
Auschalten muß nicht sein:
SQL-Anweisung
1:
| IF (NEW.ID IS NULL) THEN NEW.ID = GEN_ID(GEN_PERS_ID,1); |
Das Problem mit der ForeignKey-Constraint-Verletzung liegt evt. daran, dass der neue Pers-Datensatz
noch nicht commited ist. Damit ist er für andere nicht sichtbar.
alex
Der Jan - Do 01.12.05 17:34
Hm, komisch, genau so sah mein Trigger eigentlich aus... :?
Naja, wer weiß... Es funktioniert jetzt jedenfalls....
Entwickler-Ecke.de based on phpBB
Copyright 2002 - 2011 by Tino Teuber, Copyright 2011 - 2026 by Christian Stelzmann Alle Rechte vorbehalten.
Alle Beiträge stammen von dritten Personen und dürfen geltendes Recht nicht verletzen.
Entwickler-Ecke und die zugehörigen Webseiten distanzieren sich ausdrücklich von Fremdinhalten jeglicher Art!