Pomoc - Szukaj - Użytkownicy - Kalendarz
Pełna wersja: Zrzucanie wyjątku w modelu z PDO
Forum PHP.pl > Forum > PHP > Object-oriented programming
Piotrbaz
Witajcie,

Mam problem ze zrzuceniem wyjątku. W modelu mam funkcję save, oto jej ciało:

  1. public function save($task, advertisement $advert, $id = null) {
  2.  
  3. (...)
  4. if ($task == "insert") {
  5. $result = $this->db->prepare("INSERT INTO ads_advertisement
  6. VALUES('',:title, :description, :content, :miniature, :date, :type_id, :category_id)");
  7.  
  8. }
  9.  
  10. $result->bindValue(':title', $advert->getProperty('title'), PDO::PARAM_STR);
  11. //reszta wywołań bindValue (...)
  12.  
  13.  
  14. $result->execute();
  15.  
  16. }


Chcę zrzucić wyjątek, gdy podczas zapisywania wystąpi naruszenie unikalności jakiegoś pola w tabeli, np title.
No i nie wiem gdzie wrzucić throw new Exception('wiadomosc'); Próbowałem sprawdzenie, czy $result->execute() zwróci coś innego niż true, ale nie działa. Wciąż przy wyłapywaniu wyjątku dostaję wiadomość, jakbym w ogóle throw new Exception nie umieśił w Modelu.
Cytat
SQLSTATE[23000]: Integrity constraint violation: 1062 Duplicate entry 'mmmmmmmmmmm' for key 'title'


Kod w kontrolerze:
  1. try {
  2.  
  3. $this->model->save("insert", $new_advert);
  4.  
  5. }
  6. catch (Exception $e) {
  7.  
  8. $this->view->set_Exception($e->getMessage());
  9.  
  10. }


W widoku, wiadomo, wyświetlam komunikat wyjątku.

edit:

Teraz już nie wiem, czy w ogóle mogę własny komunikat wysłać, w manualu znalazłem, że nie powinno się jawnie zrzucać wyjątków klasy PDOException sciana.gif
Ale nie wychodziło nawet z Exception.
dzastin
Cytat
SQLSTATE[23000]: Integrity constraint violation: 1062 Duplicate entry 'mmmmmmmmmmm' for key 'title'

A to czasem nie jest php'owy fatal? Jeśli tak, to żeby to przechwycić musiałbyś zrobić swój error_handler
Piotrbaz
Ok, doszedłem do tego, że miałem w połączeniu z bazą ustawione zrzucanie wyjątków klasy PDOException, a nie mogę ich jawnie zrzucać.

Po usunięciu
  1. setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION)

mogę normalnie zrzucać wyjątki Exception. Tylko nie bardzo rozumiem sens PDOException, skoro nie mogę wpisać tam własnego komunikatu.
Crozin
1. Powinieneś samodzielnie sprawdzać czy w bazie nie istnieje już dany rekord (unikalna wartość), a nie oczekiwać na wyjątek.
2.
Cytat
Tylko nie bardzo rozumiem sens PDOException, skoro nie mogę wpisać tam własnego komunikatu.
Co to znaczy wrzucić własny komunikat? Jeżeli chcesz jakoś rozbudować zawartość rzucanego wyjątku przechwyć rzucony wyjątek PDO i "opakuj go" we własny wyjątek:
  1. try {
  2. ...
  3. } catch (PDOException $e) {
  4. throw new RuntimeException('Blah blah blah', 0, $e);
  5. }
Piotrbaz
Cytat(Crozin @ 24.03.2013, 14:37:31 ) *
1. Powinieneś samodzielnie sprawdzać czy w bazie nie istnieje już dany rekord (unikalna wartość), a nie oczekiwać na wyjątek.

Rozwiązanie z UNIQUE jest prostsze, ale skoro to napisałeś, znaczy że gorsze. Dlaczego ?

Cytat(Crozin @ 24.03.2013, 14:37:31 ) *
2. Co to znaczy wrzucić własny komunikat?


Myślałem, że mogę po prostu zrobić jak ze zwykłą klasą Exception
  1. throw new PDOException("Blah Blah");
Crozin
Cytat
Rozwiązanie z UNIQUE jest prostsze, ale skoro to napisałeś, znaczy że gorsze. Dlaczego ?
Chyba źle zrozumiałeś. Klucz typu UNIQUE ma nadal pozostać . Po prostu zamiast:
  1. <?
  2.  
  3. try {
  4. // próba dodania rekordu i operowanie jakgdyby był on unikalny
  5. } catch (... $e) {
  6. // sprawdzenie czy wyjątek dotyczy duplikatu
  7. // jeśli tak: zrób coś
  8. // jeśli nie: throw $e; // rethrow
  9. }
  10.  
  11. Powinieneś zrobić
  12.  
  13. // próba pobrania dupliaktu
  14. // jeśli nie ma: operujesz na unikalnym rekordzie
  15. // jeśli jest: zrób coś z duplikatem
Cytat
Myślałem, że mogę po prostu zrobić jak ze zwykłą klasą Exception
  1. throw new PDOException("Blah Blah");
Wyjątki PDO mają sobą reprezentować jakieś problemy z samym połączeniem z bazą danych i właściwie tylko "wnętrzności" PDO powinny rzucać wyjątek tego typu. Twoje wyjątki nie mają z tym nic wspólnego.
To jest wersja lo-fi głównej zawartości. Aby zobaczyć pełną wersję z większą zawartością, obrazkami i formatowaniem proszę kliknij tutaj.
Invision Power Board © 2001-2025 Invision Power Services, Inc.