*Markus: Wie Abfrage logisch richtig gestalten.

Hallo,

ich wollte eigentlich eine simple logische Verknüpfung verwenden, aber im Endeffekt scheint die Sache doch nicht so trivial zu sein. a_id und h_id sind Primärschlüssel.

+------+------+------+------+--------------+------+-----------+----------+
| a_id | h_id | g_id | t_id | beschreibung | bild | artikelnr | style    |
+------+------+------+------+--------------+------+-----------+----------+
|    1 |   11 |    3 |    1 | test2        |      | 89768978  | XD/3D    |
+------+------+------+------+--------------+------+-----------+----------+

Ich möchte verhindern, dass neue Einträge dann nicht gespeichert werden, wenn folgendes zutrifft:

Die Parameter des zu speichernden Eintrags dürfen nicht die selben Werte haben wie h_id, g_id, t_id und style zusammen als ein Tupel. Die Artikelnummer darf überhaupt nur einmal in allen Einträgen vorkommen, ist aber kein Pflichtfeld. Müsste ich hier mit 2 SELECT-Anweisungen arbeiten indem ich zuerst prüfe ob artikelnr schon mal vorkommt, und dann prüfe, ob die 4 Parameter einem Tupel entsprechen, oder geht das irgendwie eleganter?

Die Artikelnummer kann nicht als PK definiert werden, da

1.) a_id auto_increment ist
2.) a_id nicht weggelassen werden kann, da h_id öfter als ein Mal vorkommen darf. Somit ist man auf a_id angewiesen.
3.) die Artikelnummer kein Pflichtfeld ist. Somit kann die Artikelnummer kein Schlüssel sein.

Markus

  1. Hi!

    Die Parameter des zu speichernden Eintrags dürfen nicht die selben Werte haben wie h_id, g_id, t_id und style zusammen als ein Tupel.

    Leg einen Unique Index über diese Felder. (Einen über alle, nicht einen pro Feld.)

    Die Artikelnummer darf überhaupt nur einmal in allen Einträgen vorkommen, ist aber kein Pflichtfeld.

    Lösbar mit einem Unique Index und die Spalte darf NULL-Werte enthalten.

    Müsste ich hier mit 2 SELECT-Anweisungen arbeiten indem ich zuerst prüfe ob artikelnr schon mal vorkommt, und dann prüfe, ob die 4 Parameter einem Tupel entsprechen, oder geht das irgendwie eleganter?

    Das händische Prüfen mit vorherigem SELECT ist so ohne weiteres nicht empfehlenswert, da zwischen Prüfung und Insert jemand anderes bereits ebenfalls etwas eingefügt haben könnte.

    Die Artikelnummer kann nicht als PK definiert werden, da
    2.) a_id nicht weggelassen werden kann, da h_id öfter als ein Mal vorkommen darf. Somit ist man auf a_id angewiesen.

    Nicht unbedingt. Wenn die Eindeutigkeit mit den vier anderen Feldern gegeben ist, könnten diese zusammen den Primärschlüssel ergeben. Das ist jedoch umständlicher zu handhaben, braucht man doch dazu alle vier Felder, um einen Datensatz individuell anzusprechen. Das a_id dient hier eigentlich nur der besseren Handhabbarkeit.

    3.) die Artikelnummer kein Pflichtfeld ist. Somit kann die Artikelnummer kein Schlüssel sein.

    Doch, aber eben nullable und kein primärer.

    Lo!

    1. Hallo,

      danke für deine Hilfe. So klappt es.

      Das händische Prüfen mit vorherigem SELECT ist so ohne weiteres nicht empfehlenswert, da zwischen Prüfung und Insert jemand anderes bereits ebenfalls etwas eingefügt haben könnte.

      Hierbei würde ich mir mit Transaktionen Abhilfe verschaffen.

      Viele Grüße,
      Markus

      1. yo,

        Das händische Prüfen mit vorherigem SELECT ist so ohne weiteres nicht empfehlenswert, da zwischen Prüfung und Insert jemand anderes bereits ebenfalls etwas eingefügt haben könnte.

        Hierbei würde ich mir mit Transaktionen Abhilfe verschaffen.

        unnötig, die vorgeschlagenen UNIQUE constraints sind der bessere weg. schon alleine deshalb, weil du dann das sicherstellen dieser restriktion in die datenbank lagerst und nicht in ein programm.

        Ilja

        1. Hallo,

          unnötig, die vorgeschlagenen UNIQUE constraints sind der bessere weg. schon alleine deshalb, weil du dann das sicherstellen dieser restriktion in die datenbank lagerst und nicht in ein programm.

          Richtig. Deswegen habe ich delfix' Vorschlag auch umgesetzt.

          Markus.

      2. Hi!

        Das händische Prüfen mit vorherigem SELECT ist so ohne weiteres nicht empfehlenswert, da zwischen Prüfung und Insert jemand anderes bereits ebenfalls etwas eingefügt haben könnte.
        Hierbei würde ich mir mit Transaktionen Abhilfe verschaffen.

        Achja, ich wollte eigentlich noch dazuschreiben, dass man das mit Locking und Transaktionen zwar sicherstellen und mit einer stored Procedure kapseln kann, aber das ist alles zusätzlicher Aufwand, den du stets beim Arbeiten mit den Daten berücksichtigen musst. Ein Unique-Index hingegen kann nicht umgangen werden.

        Lo!