2012-01-06 3 views
1

Возьмут следующую функцию в качестве примера того, что я хочу сделать:PHP: Добавление к брошенному сообщению об исключении

public function save() { 
    $this->connect('wb'); 
    try { 
     if(!$this->lock()) 
      throw new Exception("Unable to acquire configuration locks"); 
     if (!$backup = $this->backup()) 
      throw new Exception("Failed to create configuration backup"); 
     try { 
      if(!fwrite($this->_pointer, $this->dump("string"))); 
       throw new Exception("Error occured while writing to configuration"); 
      $this->unlock(); 
      $this->disconnect(); 
     } catch (Exception $e) { 
      if(rename ($backup, $this->_file)) 
       $e .= PHP_EOL."Successfully restored configuration from backup"; 
      else 
       $e .= PHP_EOL."Failed to restore configuration from backup"; 
      $this->unlock(); 
      $this->disconnect(); 
      throw $e; 
     } 
    } catch (Exception $e) { 
     echo PHP_EOL, $e->getMessage(); 
    } 
} 

Я вложенный try() и catch() заявления. Исключение выбрано из самого внутреннего и поймано, я затем выполняю некоторые функции и выдаю другое исключение. Обратите внимание, где я пишу $e .=, я понимаю, что это неправильный синтаксис. Я хочу добавить строку в исключение $e->getMessage().

Как бы я это сделал?

ответ

7

Создайте свой собственный класс исключения и создайте метод добавления строки в сообщение.

<?php 
class SuperException extends Exception 
{ 
    public function AppendToMessage($msg) 
    { 
     // $this->message is inherited from Exception class, 
     // where it is protected field (member) of the class 
     $this->message .= $msg; 
    } 
} 
?> 
+1

+1 хорошо и намного чище, что мое предложение! – ManseUK

+1

Спасибо за обзор ManseUK. @Milad Naseri, в конце концов, код должен быть чистым настолько, насколько это возможно, и его легко найти и расширить для новых функций и функциональности. – Rolice

+0

Полностью согласовано. –

0

Почему бы не использовать отдельную переменную для сохранения сообщений?

public function save() { 
    $this->connect('wb'); 
    $exceptionMessage = ""; 
    try { 
     if(!$this->lock()) 
      throw new Exception("Unable to acquire configuration locks"); 
     if (!$backup = $this->backup()) 
      throw new Exception("Failed to create configuration backup"); 
     try { 
      if(!fwrite($this->_pointer, $this->dump("string"))); 
       throw new Exception("Error occured while writing to configuration"); 
      $this->unlock(); 
      $this->disconnect(); 
     } catch (Exception $e) { 
      if(rename ($backup, $this->_file)) 
       $exceptionMessage .= PHP_EOL."Successfully restored configuration from backup"; 
      else 
       $exceptionMessage .= PHP_EOL."Failed to restore configuration from backup"; 
      $this->unlock(); 
      $this->disconnect(); 
      throw $e; 
     } 
    } catch (Exception $e) { 
     echo PHP_EOL. $exceptionMessage . PHP_EOL . $e->getMessage(); 
    } 
} 
1

Большинство объектно-ориентированных языковых фреймворков, которые поддерживают обработку исключений, осознают необходимость в этой теме. Вы должны понимать, что Исключения не журналы того, что произошло. Скорее, они там, чтобы точно определить, где произошла ошибка.

Таким образом, не только этот синтаксис неверен, вся идея нарушает дюжину принципов OOD. Вам следует ввести класс регистратора, который собирает информацию об ошибках по ходу дела и использует исключения для точного определения событий , которые необходимо записать.

class ErrorLogger { 

    private $log; 

    public function __construct() { 
     $this->log = array(); 
    } 

    public function log(Exception $e) { 
     array_push($this->log, $e->getMessage()); 
    } 

} 

и далее в коде:

$logger = new ErrorLogger(); 
try { 
    : 
} catch (Exception $e) { 
    $logger->log($e); 
} 
+0

Спасибо за ваш ответ, я намерен отображать только сообщение пользователям и подробную информацию пользователям более высокого уровня, однако я должен не согласиться. Основной целью исключения для меня является выполнение конкретной логики ошибок. Я не верю, что это нарушает принципы OOD. Если бы один из моих пользователей увидел многословную ошибку, они были бы напуганы и ушли, если бы увидели, что произошла ошибка базы данных, тогда они с меньшей вероятностью будут такими же испуганными. –

+0

Здесь мой регистратор выполняет только логику образца. В вашей собственной реализации можно использовать интерфейс с двумя реализациями: один для пользователей более высокого уровня и один для конечных пользователей. –

+0

Не поймите меня неправильно Я не сбиваю ваш регистратор. Я думаю, это хорошая идея. Я собираюсь отобразить одно простое сообщение об исключении и использовать свой собственный класс исключения для входа в файл ошибки на сервере. –

Смежные вопросы