Hauptmenü

Untermenü

Advanced SQL - Praxistutorial 3 - Tauschangebote zurückziehen oder ablehnen

1. Die Abschnitte

2. Die Fehlerbehandlung

So! Endlich kommt sie. Dafür muss die entsprechende Anweisung in unserem if-Monster in der index.php so angepasst werden.


else if ($_POST['do'] == 'transactswapoffers') {
  try {
    $swap -> transactSwapoffer();
  }
  catch (SwapofferException $e) {
    $html   '<p class="error">'.$e -> getMessage().'</p>';
  }
}

Und im case-Anbschnitt verwenden wir den Verknüpfungsoperator, damit sowohl die Fehlermeldungen als auch die offenen Tauschangebote angezeigt werden.


case 'swapoffers' $html .= $swap -> listSwapOffers();

3. Die Steuerung

Der Übersichtlichkeit halber wollen wir die folgenden Möglichkeiten ein wenig aufdröseln, damit es nicht zu unübersichtlich wird. Zunächst mal legen wir in der Swapoffer.class.php folgende Methode an.


public function transactSwapoffer() {
  $message '';
  $error   = array();
  if ($_POST['cancel']) {
    $error array_merge($error$this -> cancelOffer());
  }
  if ($_POST['decline']) {
    $error array_merge($error$this -> declineOffer());
  }
  if ($_POST['accept']) {
    $error array_merge($error$this -> acceptOffer());
  }
  if ($error) {
    for ($i 0$i count($error); $i++) {
      $message .= $error[$i].'<br />';
    }
    throw new SwapofferException ($message);
  }
}

Erläuterung

Der Einfachheit halber nehmen wir für die drei Möglichkeiten "Zurückziehen" (cancel), "Ablehnen" (decline) und "Annehmen" (accept) drei verschiedene Methoden, die uns im Falle eines Fehlers Meldungen als Array zurückgibt. Die werden dann jeweils über array_merge zusammengeführt, so dass wir am Ende ein Array mit allen Fehlermeldungen haben. Aus denen bauen wir dann den String $message und geben ihn als Exceptions zurück an die index.php, wo er letztendlich ausgegeben wird.

Mui importante!

Wenn alles klappt, so fliegt euch bei korrektem error_reporting ein Warning um die Ohren! Den Fehler habe ich jetzt einfach mal mit Absicht(!) eingebaut, da viele von euch immer noch nicht in der Lage sind, vernünftig Fehler zu finden. Und diesen behebt ihr mal schön selber! Tipp: im Lösungscode ist es schon richtig.

4. Angebot zurückziehen

Das Prinzip ist eigentlich recht einfach.


private function cancelOffer() {
  for ($i 0$i count($_POST['cancel']); $i++) {
    $query 'DELETE 
                t, a
              FROM
                tausch t,
                angebot a
              WHERE a.id = '.$_POST['cancel'][$i].'
                AND t.angebot = '.$_POST['cancel'][$i];
    $num $this -> db -> change($query);
    if (!$num) {
      $error[] = 'Angebot mit der ID '.$_POST['cancel'][$i].
                 ' kann nicht mehr zurückgezogen werden';
    }        
  }
  return $error;
}

Erläuterung

Für jedes Angebot, dass man zurückziehen kann, bauen wir uns einen Query. Der wird dann über die (eigentlich überflüssige) Methode change ausgeführt. Und was macht die? Nun, die gibt das Ergebnis von exec zurück. Und das liefert die Anzahl der betroffenen Datensätze. Wurde also zum Beispiel ein Tauschangebot unsererseits schon abgelehnt oder angenommen, so ist es aus der Datenbank verschwunden und wir bekommen eine 0 (oder auch false als Ergebnis.

In dem Fall legen wir eine entsprechende Fehlermeldung im Array $error an und weisen darauf hin, dass das Angebot nicht mehr zurückgezogen werden kann. OK, eigentlich sollte man das viel präziser machen (also bereits angenommen oder abgelehnt) aber dafür dürften wir das Angebot nicht löschen sondern müssten bei jedem Angebot ein zusätzliches Feld à la status in der entsprechenden Tabelle haben. Aber das würde den Rahmen dieses Tutorials sprengen. Außerdem möchte ich euch ja auch auf Fehler beim Datenbankdesign hinweisen.

Darum merke

In so einem Fall wie diesen sollte man niemals(!) die Angebote löschen, sondern statt dessen in einer weiteren Spalte den Status abspeichern, damit man dezidiert auf die verschiedenen Möglichkeiten hinweisen kann.

Ein Hinweis

Zum Testen des bisherigen Codes solltet ihr einfach mal eure Tauschangebote im Browser mit "zurückziehen" markieren, dann die Angebot mit der ID 3 und 4 löschen und danach das Formular abschicken. Dann seht ihr das Ergebnis. Und wer sich jetzt fragt, was mit den Einträgen in der tausch passiert, der sollte da mal reinschauen. Die sind nämlich ebenfalls weg. Und wieso? Stichwort ON DELETE CASCADE. Damit haben wir uns ja bei der Modellierung beschäftigt. OK, ist lange her.

5. Angebot ablehnen

Ist dasselbe wie beim Zurückziehen. Idealerweise hätte man das zusammen mit obiger Methode zu einer zusammengefasst und mit Parametern gearbeitet.


private function declineOffer() {
  for ($i 0$i count($_POST['decline']); $i++) {
    $query 'DELETE 
                t, a
              FROM
                tausch t,
                angebot a
              WHERE a.id = '.$_POST['decline'][$i].'
                AND t.angebot = '.$_POST['decline'][$i];
    $num $this -> db -> change($query);
    if (!$num) {
      $error[] = 'Angebot mit der ID '.$_POST['decline'][$i].' kann nicht mehr abgelehnt werden';
    }        
  }
  return $error;
}

zurück zum vorherigen Abschnitt weiter zum nächsten Abschnitt