[Gelöst] Löschfunktion SQLite3

Für Themen zu Datenbanken und Zugriff auf diese. Auch für Datenbankkomponenten.
Antworten
BerlinerBaer
Beiträge: 16
Registriert: Sa 9. Jan 2021, 15:07
OS, Lazarus, FPC: Windows (L 2.0.10 FPC 3.2.0)
CPU-Target: 32/64Bit

[Gelöst] Löschfunktion SQLite3

Beitrag von BerlinerBaer »

Hallo, Freunde von Lazarus.

Der Befehl

Code: Alles auswählen

DELETE FROM tbl WHERE col_1 = :id
löscht bekanntlich die ganze Spalte mit der entsprechenden ID.

Ich habe eine SQLite3 Datenbank mit 2 Tabellen und einem Fremdschlüssel (ON DELETE CASCADE ON UPDATE CASCADE). Mittels o. g. Befehl lösche/bearbeite ich nun in der Haupttabelle die entsprechende und ausgewählte Zeile. Im DB Browser funktioniert es problemlos. Führe ich den o. g. Befehl nun in Lazarus aus, passiert nur eins. Die Zeile in der Haupttabelle wird gelöscht. Die mitzulöschenden Zeilen in der Untertabelle bleibt bestehen.

Hier die Struktur meiner beiden Tabellen

Code: Alles auswählen

CREATE TABLE "gruppen" (
	"gruppenID"	INTEGER NOT NULL,
	"gruppenName"	TEXT,
	"gruppenBeschreibung"	TEXT,
	"gruppenDatum"	NUMERIC,
	PRIMARY KEY("gruppenID" AUTOINCREMENT)
);

Code: Alles auswählen

CREATE TABLE "personen" (
	"personenID"	INTEGER NOT NULL,
	"gruppenID"	INTEGER NOT NULL,
	"personenName"	TEXT,
	FOREIGN KEY("katID") REFERENCES "gruppen"(gruppenID") ON DELETE CASCADE ON UPDATE CASCADE,
	PRIMARY KEY("personenID" AUTOINCREMENT)
);
Mit

Code: Alles auswählen

var
  gID : Integer;
begin
  ZQuery.Params.Clear;
  ZQuery.Params.CreateParam(ftInteger, 'gruppenID', ptinput);
  ZQuery.ParamByName('gruppenID').Value:=gID;
  ZQuery.SQL.Text:='DELETE FROM gruppen WHERE gruppenID = :gID';
  ZQuery.ExecSQL;
end;
führe ich die Löschung durch. Nur die, wie bereits erwähnt, betroffenen Zeilen in der Tabelle "personen" bleiben weiterhin existent.
Kann mir jemand sagen, warum das so ist?

Benutzen tu ich:
Lazarus: 2.0.10
ZEOS: 7.2.8
DB Browser 3.12.1
SQLite3 3.33.0

Liebe Grüße
BerlinerBaer
Zuletzt geändert von BerlinerBaer am Di 12. Jan 2021, 21:43, insgesamt 2-mal geändert.
Die deutsche Rechtschreibung ist Freeware. Man darf sie kostenlos nutzen. Allerdings ist sie nicht Open Source. Das heißt, sie darf weder verändert, noch in veränderter Form veröffentlicht werden.

TraumTaenzerDieter
Beiträge: 25
Registriert: So 14. Aug 2011, 09:11

Re: Löschfunktion SQLite3

Beitrag von TraumTaenzerDieter »

Hallo BerlinerBaer,
versuch mal
ZConnection.Properties.add('foreign_keys=TRUE');

BerlinerBaer
Beiträge: 16
Registriert: Sa 9. Jan 2021, 15:07
OS, Lazarus, FPC: Windows (L 2.0.10 FPC 3.2.0)
CPU-Target: 32/64Bit

Re: Löschfunktion SQLite3

Beitrag von BerlinerBaer »

Ja, hätte ich vielleicht erwähnen sollen. Foreign_keys habe ich als SQL-Befehl bereits nach dem Verbinden mit der Datenbank aktiviert.

Code: Alles auswählen

SQL.Text:='PRAGMA foreign_keys = ON';
Dennoch probiere ich es gleich mal aus.
Die deutsche Rechtschreibung ist Freeware. Man darf sie kostenlos nutzen. Allerdings ist sie nicht Open Source. Das heißt, sie darf weder verändert, noch in veränderter Form veröffentlicht werden.

BerlinerBaer
Beiträge: 16
Registriert: Sa 9. Jan 2021, 15:07
OS, Lazarus, FPC: Windows (L 2.0.10 FPC 3.2.0)
CPU-Target: 32/64Bit

Re: Löschfunktion SQLite3

Beitrag von BerlinerBaer »

TraumTaenzerDieter hat geschrieben:
Mo 11. Jan 2021, 12:41
ZConnection.Properties.add('foreign_keys=TRUE');
Vielen lieben Dank. Damit klappt es. :)
Die deutsche Rechtschreibung ist Freeware. Man darf sie kostenlos nutzen. Allerdings ist sie nicht Open Source. Das heißt, sie darf weder verändert, noch in veränderter Form veröffentlicht werden.

MmVisual
Beiträge: 1150
Registriert: Fr 10. Okt 2008, 23:54
OS, Lazarus, FPC: Winuxarm (L 2.0.10 FPC 3.2)
CPU-Target: 32/64Bit

Re: Löschfunktion SQLite3

Beitrag von MmVisual »

Wegen deinem Code:

Code: Alles auswählen

var
  gID : Integer;
begin
  ZQuery.Params.Clear;
  ZQuery.Params.CreateParam(ftInteger, 'gruppenID', ptinput);
  ZQuery.ParamByName('gruppenID').Value:=gID;
  ZQuery.SQL.Text:='DELETE FROM gruppen WHERE gruppenID = :gID';
  ZQuery.ExecSQL;
end;
Das geht mit Zeos anders:

Code: Alles auswählen

var
  gID : Integer;
begin
  ZQuery.SQL.Text:='DELETE FROM gruppen WHERE gruppenID = :gID ';
  ZQuery.Params.ParamValues['gID'] :=gID;
  ZQuery.ExecSQL;
end;
Also man braucht da nichts mit Clear und CreateParam. Das macht Zeos alleine, man muss nur im Objektinspektor den "ParamCheck" auf TRUE belassen. Damit ist automatisch der Parameter mit dem Name so wie man den im SQL Text stehen hat verfügbar.
Wichtig: Der Parameter beginnt immer mit ":", gefolgt von Buchstaben/Zahlen, vor dem ":" und nach dem letzten Buchstabe muss immer ein Leerzeichen stehen. Wenn man das nicht einhält findet Zeos nicht von alleine den Parametername.
Auch muss man natürlich zu erst den SQL Befehl in die Query geben, dann erst den Parameter schreiben.

Hat jetzt zwar nicht wirklich was mit dem eigentlichen Problem zu tun, hilft dennoch in der Programmierung.

BerlinerBaer
Beiträge: 16
Registriert: Sa 9. Jan 2021, 15:07
OS, Lazarus, FPC: Windows (L 2.0.10 FPC 3.2.0)
CPU-Target: 32/64Bit

Re: Löschfunktion SQLite3

Beitrag von BerlinerBaer »

Danke MmVisual.

bisher hat das immer so funktioniert, wie in meinem Code-Beispiel. Ich habe mich schin gewundert, warum hier im Forum alles anders geschrieben wird.
Demzufolge werde ich mal meine ganzen Quelltexte anpassen. Ich danke dir.

Was mich jedoch stutzig macht, ist das von dir erwähnte Leerzeichen beim generieren der Parameter.
Die deutsche Rechtschreibung ist Freeware. Man darf sie kostenlos nutzen. Allerdings ist sie nicht Open Source. Das heißt, sie darf weder verändert, noch in veränderter Form veröffentlicht werden.

MmVisual
Beiträge: 1150
Registriert: Fr 10. Okt 2008, 23:54
OS, Lazarus, FPC: Winuxarm (L 2.0.10 FPC 3.2)
CPU-Target: 32/64Bit

Re: Löschfunktion SQLite3

Beitrag von MmVisual »

Das kann probleme machen:

Code: Alles auswählen

'....(:Param)...'

Code: Alles auswählen

ZQuery.SQL.Text:='....:Param';
ZQuery.SQL.Add('ZweiteZeile...');
Das hingegen nicht:

Code: Alles auswählen

'....( :Param )...'

Code: Alles auswählen

ZQuery.SQL.Text:='.... :Param ';
ZQuery.SQL.Add('ZweiteZeile...');
Zeos sucht nach Leerzeichen um den Anfang sowie das Ende des Parameters zu finden. Wenn da andere Zeichen drin stehen, wie Klammern, dann klappt das je nach SQL Syntax nicht immer richtig. Wenn man jedoch die Parameter mit Leerzeichen einschließt dann geht das immer.

Als Parameter sollte man alle Strings und TDateTime übergeben, Zeos wandelt das dann automatisch korrekt in das SQL Format wie der SQL Server das gerade haben möchte.
Beispiel: TDateTime kann bei manchen SQL Servern anhand Ländereinstellungen umgestellt werden.
Bei Strings gibt es je nach SQL Server unterschiedliche Quotings, mache wollen ', mache ", mache aber auch das ` oder ´. Damit man sich damit nicht rum ärgern muss übergibt man die Strings einfach ebenfalls per Parameter.

BerlinerBaer
Beiträge: 16
Registriert: Sa 9. Jan 2021, 15:07
OS, Lazarus, FPC: Windows (L 2.0.10 FPC 3.2.0)
CPU-Target: 32/64Bit

Re: Löschfunktion SQLite3

Beitrag von BerlinerBaer »

Dankeschön. :)
Die deutsche Rechtschreibung ist Freeware. Man darf sie kostenlos nutzen. Allerdings ist sie nicht Open Source. Das heißt, sie darf weder verändert, noch in veränderter Form veröffentlicht werden.

BerlinerBaer
Beiträge: 16
Registriert: Sa 9. Jan 2021, 15:07
OS, Lazarus, FPC: Windows (L 2.0.10 FPC 3.2.0)
CPU-Target: 32/64Bit

Re: Löschfunktion SQLite3

Beitrag von BerlinerBaer »

Hallo MmVisual,

in anderen Foren wird erwähnt, dass zuerst der Parameter erstellt werden muss.

https://forum.lazarus.freepascal.org/in ... l#msg57540

Wenn ich es richtig verstanden habe, dann ist es eigentlich egal, in welcher Reihenfolge. Oder sehe ich das falsch?

Gibt es irgendwo ein Hinweis seitens ZEOS wie das fabriziert werden sollte?
Die deutsche Rechtschreibung ist Freeware. Man darf sie kostenlos nutzen. Allerdings ist sie nicht Open Source. Das heißt, sie darf weder verändert, noch in veränderter Form veröffentlicht werden.

MmVisual
Beiträge: 1150
Registriert: Fr 10. Okt 2008, 23:54
OS, Lazarus, FPC: Winuxarm (L 2.0.10 FPC 3.2)
CPU-Target: 32/64Bit

Re: Löschfunktion SQLite3

Beitrag von MmVisual »

Nein, es gibt keinen Hinweis, man kann beide Varianten machen, die zweite ist jedoch eleganter, da man weniger tippen muss.

Abgesehen davon sollte man immer auf das Datum von Postings eines Forum Beitrags achten, der aus dem Link ist von 2010, also schon 11 Jahre alt und es ist immer schwierig heraus zu finden was denn nun die aktuellen (besseren) Möglichkeiten sind. Zum Teil funktionieren so alte Tipps einfach auch nicht mehr korrekt, da muss man ebenfalls aufpassen.

BerlinerBaer
Beiträge: 16
Registriert: Sa 9. Jan 2021, 15:07
OS, Lazarus, FPC: Windows (L 2.0.10 FPC 3.2.0)
CPU-Target: 32/64Bit

Re: Löschfunktion SQLite3

Beitrag von BerlinerBaer »

Gut, dann hätten wir das geklärt. Ich übernehme dein Vorschlag, da es wirklich eine ganze Menge arbeit erspart und vor allem übersichtlicher ist.

Auch hier sage ich noch mal Dankeschön.
Die deutsche Rechtschreibung ist Freeware. Man darf sie kostenlos nutzen. Allerdings ist sie nicht Open Source. Das heißt, sie darf weder verändert, noch in veränderter Form veröffentlicht werden.

Antworten